我有一个共同的存储库,其中添加,更新,删除。 我们将其命名为 CustomerRepository 。
我有一个名为客户的实体(POCO),它是一个聚合根,地址。
public class Customer
{
public Address Addresses { get; set; }
}
我处于一个独立的实体框架5场景中。
现在,让我们说在获得客户后,我选择删除客户地址。 我通过更新方法将客户聚合根提交到存储库。
如何保存对地址所做的修改?
我们可以说这个解决方案不完整且效率低下。
那么应该如何更新聚合根子项呢?
我是否必须使用 AddAddress , UpdateAddress , DeleteAddress 等方法完成 CustomerRepository ?
虽然它似乎有点打破了这种模式......
我是否在每个POCO上都设置了持久性状态:
public enum PersistanceState
{
Unchanged,
New,
Updated,
Deleted
}
然后我的 CustomerRepository 只有一种方法,保存?
在这种情况下,似乎我正在重新构建实体“非POCO”对象,并将数据访问相关属性添加到业务对象...
答案 0 :(得分:2)
首先,您应该使用Add,Update和Delete方法保存您的存储库,尽管我个人更喜欢Add,indexer set和Remove,以便存储库看起来像应用程序代码的内存集合。
其次,存储库应负责跟踪持久性状态。我甚至没有使用
混乱我的域对象object ID { get; }
像某些人一样。相反,我的存储库看起来像这样:
public class ConcreteRepository : List<AggregateRootDataModel>, IAggregateRootRepository
我使用AggregateRootDataModel类来跟踪内存中对象的ID以及跟踪任何持久性信息。在你的情况下,我会把一个属性
List<AddressDataModel> Addresses { get; }
在我的CustomerDataModel类上,该类还包含Customer域对象以及客户的数据库ID。然后,当客户更新时,我会得到如下代码:
public class ConcreteRepository : List<AggregateRootDataModel>, IAggregateRootRepository
{
public Customer this[int index]
{
set
{
//Lookup the data model
AggregateRootDataModel model = (from AggregateRootDataModel dm in this
where dm.Customer == value
select dm).SingleOrDefault();
//Inside the setter for this property, run your comparison
//and mark addresses as needing to be added, updated, or deleted.
model.Customer = value;
SaveModel(model); //Run your EF code to save the model back to the database.
}
}
}
这种方法的主要警告是您的域模型必须是引用类型,并且您不应该重写GetHashCode()。这样做的主要原因是当您对匹配数据模型执行查找时,哈希代码不能依赖于任何可更改属性的值,因为即使应用程序代码修改了值,它也需要保持不变。域模型实例上的属性。使用此方法,应用程序代码变为:
IAggregateRootRepository rep = new ConcreteRepository([arguments that load the repository from the db]);
Customer customer = rep[0]; //or however you choose to select your Customer.
customer.Addresses = newAddresses; //change the addresses
rep[0] = customer;
答案 1 :(得分:1)
简单的方法是使用自我跟踪实体What is the purpose of self tracking entities?(我不喜欢它,因为跟踪是不同的责任)。
很难,你拿原始收藏品进行比较: - /
Update relationships when saving changes of EF4 POCO objects
其他方式可能是,事件追踪?