2010-05-20 37 views
7

我正在开发使用实体框架(.NET 3.5)的WPF应用程序。它在整个地方访问实体。我担心贯穿整个应用程序的一致性。我是否应该在不同的视图中实例化单独的上下文,还是应该(并且是一个很好的方法)实例化一个可以在全局范围内访问的上下文?例如,我的实体模型包含三个部分:货件(包含子包和其他子内容),公司/联系人(包含子地址和电话)以及磁盘规格。 Shipments和EditShipment视图访问DiskSpecs,而OptionsView管理DiskSpecs(创建,编辑,删除)。如果我编辑一个DiskSpec,我必须在ShipmentsView中有一些东西来检索最新的规格,如果我有单独的上下文吗?WPF应用程序中的全局实体框架上下文

如果可以安全地从应用程序的其余部分获取一个总体上下文,那么我想这就是要走的路。如果是这样,该实例将放在哪里?我使用VB.NET,但我可以从C#翻译很好。任何帮助,将不胜感激。

我只是不希望其中的一个应用程序,用户不得不在应用程序的不同部分重新加载十几次以获取新数据。

更新:

  1. 所有上下文中使用块,他们不再需要后处理掉的创建:

    行,所以如下我已经改变了我的应用程序。

  2. 加载时,所有实体在处理前都从上下文中分离出来。
  3. MainViewModel(ContextUpdated)中的新属性引发了所有其他ViewModel预订的事件,该事件运行ViewModels RefreshEntities方法。
  4. 执行此操作后,我开始出现错误,指出某个实体一次只能由一个ChangeTracker引用。由于我无法弄清楚哪个上下文仍在引用该实体(不应该是任何上下文?),我将该对象作为IEntityWithChangeTracker转换,并将SetChangeTracker设置为空(Null)。

这让当前的问题: 当我null值,实体的changeTracker,然后将其连接到一个背景下,它失去了它的状态发生了改变,并没有更新到数据库中。但是,如果我不更改更改跟踪器,我无法附加。我有我自己的更改跟踪代码,所以这不是问题。

我的新问题是,你应该如何做到这一点。一个很好的示例实体查询和实体保存代码会被剪掉很长一段时间,因为我试图获得我曾经认为是一个简单的事务才能工作。

+0

如果你downvote,我很乐意解释。至少它会让我知道什么不该在路上进一步做。 – CodeWarrior 2012-12-03 19:20:10

回答

5

全局静态上下文很少是正确的答案。考虑如果在执行此应用程序期间重置数据库会发生什么情况 - 您的SQL连接消失,并且所有使用静态上下文的后续请求都将失败。

推荐你找到一个方法来对你的实体背景下更短的生命周期 - 打开它,做了一些工作,处理它,...

至于把你的不同对象在同一EDMX,这几乎肯定是正确的答案,如果他们在同一个EDMX中需要它们的对象之间有任何关系。

至于重新加载 - 用户不应该这样做。在幕后,您可以打开一个新的上下文,从数据库重新加载对象的当前版本,应用他们在UI中进行的更改并将其保存回去。

您也可能希望查看分离的实体,并且当您尝试保存更改并且其他人已更改数据库中的同一对象时,要小心乐观并发异常。

+0

好吧,如果我使用多个上下文,一个上下文将如何知道刷新的数据。我是否会监视由其他上下文设置的propertychanged事件? – CodeWarrior 2010-05-21 02:11:03

+0

当应用程序处于空闲状态时,上下文应该关闭并消失。你所拥有的只是在这种状态下的DTO或detatched实体。当有人点击你打开单个上下文的东西时,重新连接你的实体或重新加载它们并应用UI中的更改,然后调用savechanges处理它可能抛出的任何乐观并发异常,然后更新你的视图并最终处理上下文。将上下文想象为一个单一的工作单元。 – 2010-05-21 02:18:53

+0

这代表了我如何查看EF功能的根本性变化。我的印象是,上下文有望引用从数据创建的对象,直到视图模型处理它(处理视图时)。 目前我有我的ViewModels通过EF加载Shipment对象,这些对象被加载到自定义集合中并显示在视图中。对内存对象进行更改后,我调用保存更改并使用相同的上下文(对吗?)更新服务器。如果这是不正确的,当我保存更改时,它的工作方式是否有所不同? – CodeWarrior 2010-05-21 02:33:47

3

好问题,Cory。大拇指从我身上。

实体框架为您提供了一个自由选择 - 您可以实例化多个上下文或者只有一个静态实例。它在两种情况下都能很好地工作,是的,两种解决方案都是安全的。我可以给你的唯一有价值的建议是:试验两者,衡量表现,延误等,并为你选择最好的一个。这很有趣,相信我:)

如果这将是一个具有大量并发连接的真正巨大的应用程序,我会建议使用一个静态上下文或一个静态,核心上下文,只是为了支持主要的上下文。但是,由于我只写了几行以上 - 这取决于您的需求哪种解决方案更适合您。

我特别喜欢你的问题的这部分:

我只是不想当用户打 不同 部分应用程序的加载了十几次获得这些 应用之一新的数据。

WPF是一个非常非常强大的工具,基本上用户不得不按下按钮刷新数据的时间已经一去不复返了。 WPF为您提供了非常广泛的异步多线程工具,例如Dispatcher类或Background工作程序,以在后台轻松刷新所需的数据。这真的很棒,因为不仅您不必担心按下各种按钮,而且后台线程也不会阻止用户界面,所以从用户的角度来看,数据会以透明的方式刷新。

WPF和Entity Framework一起真的值得学习 - 请随时询问你是否有任何进一步的问题。

+0

Piotr,请参阅与Hightechrider的对话。我一直在教我自己WPF和EF。我的第一个应用程序非常丑陋而且非常笨拙,但随着我走,它们变得更加精致。任何管理ViewModel功能的好资源都会很棒。搜索时会看到很多结果,但大多数都是MVVM等的一般解释。 – CodeWarrior 2010-05-21 03:48:56

+0

嗨,IMo最适合初学者的MVVM文章就是这样:http://www.codeproject.com/KB/WPF/TreeViewWithViewModel.aspx这尽可能简单,为您提供尽可能多的信息,您需要自己做。请报告你的进度:) – 2010-05-21 06:20:29

+0

那篇文章根本不是关于Entity Framework的。它关于MVVM和TreeView控件。 – CodeWarrior 2011-07-13 15:44:46