我有以下情况:
我将如何在EntityFramework中实现这样的东西?
我的问题是,当我将UI直接绑定到实体的属性时,每个更改都会被实例化地应用到该实体。我希望将此延迟到用户按OK并实体被成功验证的时刻。
我考虑过用NoTracking加载实体,并在分离的实体验证后调用ApplyPropertyChanges,但我不完全确定正确的方法。MSDN上的EntityFramework的docu非常稀疏。
我可以想到的另一种方法是使用Refresh使用StoreWins来重新设置实体,但我不喜欢在Cancel上重置更改,而不喜欢在Ok应用更改。
有谁有好的教程或样本吗?
发布于 2009-05-02 01:22:02
一个选项是你说的做一个没有跟踪的查询。
ctx.Customers.MergeOption = MergeOption.NoTracking;
var customer = ctx.Customers.First(c => c.ID == 232);然后,客户可以根据内存中的需要修改'customer',并且上下文中实际上没有发生任何事情。
现在,当您想要进行更改时,您可以这样做:
// get the value from the database
var original = ctx.Customers.First(c => c.ID == customer.ID);
// copy values from the changed entity onto the original.
ctx.ApplyPropertyChanges(customer); .
ctx.SaveChanges();现在,如果您出于性能或并发原因对查询感到不舒服,可以添加一个新的扩展方法AttachAsModified(.)敬ObjectContext。
看起来是这样的:
public static void AttachAsModified<T>(
this ObjectContext ctx,
string entitySet,
T entity)
{
ctx.AttachTo(entitySet, entity);
ObjectStateEntry entry =
ctx.ObjectStateManager.GetObjectStateEntry(entity);
// get all the property names
var propertyNames =
from s in entry.CurrentValues.DataRecordInfo.FieldMetadata
select s.FieldType.Name;
// mark every property as modified
foreach(var propertyName in propertyNames)
{
entry.SetModifiedProperty(propertyName);
}
}现在您可以编写如下代码:
ctx.Customers.MergeOption = MergeOption.NoTracking;
var customer = ctx.Customers.First();
// make changes to the customer in the form
ctx.AttachAsModified("Customers", customer);
ctx.SaveChanges();现在您没有并发查询或外部查询。
现在唯一的问题是处理FK属性。您可能应该在这里查看我的提示索引:http://blogs.msdn.com/alexj/archive/2009/03/26/index-of-tips.aspx
希望这能有所帮助
亚历克斯
https://stackoverflow.com/questions/803022
复制相似问题