强制实体框架返回新实例

时间:2012-02-21 10:01:46

标签: entity-framework orm identity-map

我们的代码中有一个场景,只允许更改实体的一些属性。为了保证这一点,我们有类似的代码:

public void SaveCustomer(Customer customer)
{
    var originalCustomer = dbContext.GetCustomerById(customer.Id);

    if (customer.Name != originalCustomer.Name)
    {
        throw new Exception("Customer name may not be changed.");
    }

    originalCustomer.Address = customer.Address;
    originalCustomer.City = customer.City;

    dbContext.SaveChanges();
}

此代码的问题在于对dbContext.GetCustomerById的调用并不总是为我提供Customer类的新实例。如果客户已经从数据库中获取,则实体框架会将实例保留在内存中,并在每次后续调用时将其返回。

这导致我们遇到实际问题 - customeroriginalCustomer可能会引用相同的实例。在这种情况下,customer.Name将等于originalCustomer.Name,我们将无法检测它是否与数据库不同。

我猜大多数其他ORM也存在同样的问题,因为身份图设计模式。

任何想法如何解决这个问题?我可以以某种方式强制EF总是给我一个新的客户类实例吗?

或者我们应该重构代码吗?有没有人知道这种情况的任何好的设计模式?

1 个答案:

答案 0 :(得分:1)

您可以尝试从上下文中分离实体,这将删除对上下文的所有引用(以及identitymap行为)。 因此,在将客户传递给您的方法之前,您可以将其分离:

yourContext.Detach(customer);