级联操作
当对一个实体的其关联属性或实体集属性进行修改时,Insert / Update 操作时也会将这些修改一起持久化到库里。
1、插入关联实体或实体集
如,在插入一个 Orders
对象时,可以同时在订单明细集合里添加 OrderDetails
对象。
[TestMethod]
public void TestInsertWithDetails()
{
var order = new Orders
{
OrderDate = DateTime.Now,
OrderDetailses = new EntitySet<OrderDetails>(),
};
//构造5条明细
for (var i = 0; i < 5; i++)
{
order.OrderDetailses.Add(new OrderDetails
{
ProductID = 1 + i,
UnitPrice = 0.3,
Quantity = 12,
Discount = 0.99,
});
}
using (var db = new DbContext())
{
db.Orders.Insert(order);
}
}
OrderDetails
对象的 OrderID 属性值是无法预知的,只有 Orders
对象新增后,自动赋给每一个 OrderDetails
对象。
2、更新关联实体
更新一个实体的同时,可以对其关联的实体进行更新。
如下例中,更新订单明细的同时,对订单的数据进行更新。
[TestMethod]
public void TestUpdateReference()
{
using (var db = new DbContext())
{
var detail = db.OrderDetails.FirstOrDefault();
detail.Orders.ShipName = "fireasy";
db.OrderDetails.Update(detail);
}
}
同理,Update 也可同时更新子实体集中的部分实体的属性。
[TestMethod]
public void TestUpdateChildCollection()
{
using (var db = new DbContext())
{
var order = db.Orders.FirstOrDefault();
if (order.OrderDetailses.Count > 0)
{
order.OrderDetailses[0].Products.UnitsInStock = 45;
}
db.Orders.Update(order);
}
}
3、更新实体集
更新一个实体的同时,可以对其子实体集进行更新。这些操作是在事务中完成的,所以你不必须担心数据的一致性问题。
比如下例中,在更新订单的同时,将订单明细中的第一项移除。在执行 Update 的同时,订单明细的第一条数据也会被删除。
[TestMethod]
public void TestRemoveDetail()
{
using (var db = new DbContext())
{
var order = db.Orders.Get(11092);
order.OrderDetailses.RemoveAt(0);
db.Orders.Update(order);
}
}
当然,也可以在移除订单明细的同时,往子实体集中添加新的订单明细,或对实体集中的某一实体进行修改,等同于上节中的更新。如下例:
[TestMethod]
public void TestRemoveAndAddDetail()
{
using (var db = new DbContext())
{
var order = db.Orders.Get(11092);
order.OrderDetailses.RemoveAt(0);
order.OrderDetailses.Add(new OrderDetails { ProductID = 1 });
db.Orders.Update(order);
}
}
如果对子实体集 Clear 或设为 null,那么将移除所有的订单明细。如下例:
[TestMethod]
public void TestClearDetail()
{
using (var db = new DbContext())
{
var order = db.Orders.Get(11092);
order.OrderDetailses = null;
db.Orders.Update(order);
}
}