实体框架4.1:如何使用每个调用生命周期的数据上下文? [英] Entity Framework 4.1: how to work with per call life time data context?

查看:315
本文介绍了实体框架4.1:如何使用每个调用生命周期的数据上下文?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

根据此帖子,我每次调用都使用数据上下文,因此在我的WCF服务的每个方法中,我使用使用块创建一个新的数据上下文。

According to this post, I am using a data context per call, so in each method of my WCF service, I use a using block to create a new data context.

但是我有一些怀疑以这种方式工作。

But I have some doubts in the form to work in this way.

例如,我使用一个方法getAllCLients()从我的存储库获取所有的客户端的数据库,然后服务发送到客户端调用方法与所有客户端的列表。然后用户修改其中的一些信息,例如三个。

For example, I use a method getAllCLients() from my repository to get all the clients of the data base, then the service send to the client that call the method a list with all the clients. Then the user modify the information of some of them, three for example. The modify client perhaps I can add to a list that have the modified clients.

当我想更新这三个客户端时,我可以调用一个方法updateClients()接收修改的客户端的列表。我如何使用一个新的数据上下文每个方法,在updateCients()获取一个新的dataContext,没有实体,所以我认为我必须按照以下步骤:

When I want to update this three clients, I can call a method updateClients() which receive a list of modified clients. How I am use a new data context per each method, in updateCients() get a new dataContext, without entities, so I think that I have to follow this steps:

1.创建一个新的数据上下文,其中包含我要更新的客户端。所以我需要指定的条件。这是一个额外的操作(我使用getAllClients()方法获取客户端),所以我需要再次获得客户端。

1.- create a new data context which has the clients that I want to update. SO I need to specified the conditions for that. This is an extra operation (I get the clients before with the getAllClients() method), so I need to get again the clients.

收集DBSet(我使用EF 4.1)并更改信息。这使我去抛出我从客户端应用程序接收的列表。所以我必须去抛两个名单。这需要资源。

2.- go throw the clients collection of the DBSet (I use EF 4.1) and change the information. This makes me to go throw the list that I receive from the client application too. So I must to go throw two lists. This needs resources.

3.-保存更改。这是必要的,所以它不需要更多的工作。

3.- save the changes. This is needed anyway, so it has no required more work.

有任何方法使步骤2容易吗?在dataContext中存在一些方法以将值从我的修改的客户端传递到数据上下文中的客户端?我使用POCO实体,也许它存在一个简单的方法来做到这一点。

There is any way to make the step 2 easily? exist some method in dataContext to pass the values from my modified client to the client in the data context? I use POCO entities, perhaps it exists an easy way to do that.

其他问题是关于并发。如果我使用允许EF(使用时间戳字段)的易用性并发控制并发性,最好为每个客户端调用updateClient(),或者更好地为所有客户端传递一个列表?我的意思是,如果我使用列表作为参数,如果有一个客户端的并发问题,第二个例如,第一个客户端将正确更新,但第二个和第三个。如何通知用户某些客户有问题?

Other question is about concurrency. If I control the concurrency with pesimistic concurrency that allow EF (with a timestamp field for example), is it better to call the updateClient() one for each client or better to pass a list with all the clients? I mean that if I use a list as parameter, if there is a concurrency issue with one client,the second for example, the first client will be update correctly, but the second not and the third neither. How can I notify to the user that there is problems with some clients?

要恢复,我想知道在短期内进行更新的最佳方法数据报文。

To resume, I would like to know the best way to make updates when I have a short life datacontext.

谢谢。
Daimroc。

Thanks. Daimroc.

推荐答案

服务断开连接的情况,所以当您的客户端传回您只需要处理的修改记录作为修改。您不需要为数据库加载所有记录。

The service is disconnected scenario so when your client passes backs modified records you just need to process them as modified. You don't need to load all records from database for that.

public void SaveClients(List<Client> modifiedClients)
{
    using (var context = new Context())
    {
        modifiedClients.ForEach(c => 
           {
               context.Entry(c).State = EntityState.Modified;
           });
        context.SaveChanges(); 
    }
}

如果您使用的是每个呼叫服务和每个服务操作需要上下文你可以将你的上下文实例移动到服务构造函数,因为服务实例将只存在服务器单一服务调用=你不需要使用每个调用。如果你这样做,不要忘记在你的服务上实现 IDisposable 来处理上下文。

If you are using per call service and every service operation needs context you can move your context instancing to service constructor because service instance will live only to server single service call = you don't need using for every call. If you do that don't forget to implement IDisposable on your service to dispose context.


其他问题是关于并发。如果我使用
控制并发性,那么允许EF(带有
的时间戳字段)的并发性,最好为每个客户端调用updateClient()一个
或更好地传递列表与所有客户?

Other question is about concurrency. If I control the concurrency with pesimistic concurrency that allow EF (with a timestamp field for example), is it better to call the updateClient() one for each client or better to pass a list with all the clients?

EF不支持pesimistic并发开箱即用。使用时间戳是乐观并发,因为它允许其他人使用记录。 Pesimistic并发是应用程序逻辑,其中其他客户端不能选择锁定的记录进行更新。

EF doesn't support pesimistic concurrency out of the box. Using timestamp is optimistic concurrency because it allows others to use the record. Pesimistic concurrency is application logic where other client is not able to select locked record for update.

并发是每个记录解决,但是这种情况下的问题是事务。每次调用 SaveChanges 都会导致事务用于处理数据库中的所有更改。因此,如果您的任何修改的记录不是最新的,您将获得并发异常,整个事务被回滚=没有记录更新。

The concurrency is resolved per record but the problem in this case is transaction. Each call to SaveChanges results in transaction used to process all changes in the database. So if any of your modified records is not up to date you will get concurrency exception and whole transaction is rolled back = no record is updated.

您仍然可以通过将修改记录的列表传递到服务来解决这个问题(减少客户端和服务之间的往返是最佳做法),但您可以通过为每个记录调用 SaveChanges 。无论如何,这应该非常仔细地考虑,因为每个调用 SaveChanges 就像单独的工作单元 - 这是真的你想要什么?

You can still overcome the issue by passing list of modified records to the service (reducing roundtrips between client and service is a best practice) but you can process each record separately by calling SaveChanges for every single record. Anyway this should be very carefully considered because each call to SaveChanges is like separate unit of work - is it really what you want?

Btw。最佳做法是使您的服务无状态。你应该避免在服务调用之间保持数据,这个例子确实不需要它。

Btw. the best practice is to make your service statless. You should avoid maintaining data between service calls and this example really doesn't need it.

这篇关于实体框架4.1:如何使用每个调用生命周期的数据上下文?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆