简体   繁体   English

实体框架CTP5,代码优先。有多个级联删除

[英]Entity Framework CTP5, code-first. Many to many with cascade delete

I have two entities (Customer and CustomerRole) and would like to declare many-to-many relationship between them. 我有两个实体(Customer和CustomerRole),并希望声明它们之间的多对多关系。 I can do using the following code: 我可以使用以下代码:

modelBuilder.Entity<CustomerRole>()
        .HasMany(cr => cr.Customers) 
        .WithMany(c => c.CustomerRoles)
        .Map(m => m.ToTable("Customer_CustomerRole_Mapping"));

But it creates the relationship (and the third mapping table) with cascade delete switched off by default. 但它创建了关系(和第三个映射表),默认情况下关闭级联删除。 How can I tell EF to create the relationship with cascade delete switched on when using many-to-many? 如何在使用多对多时告诉EF创建与级联删除关系的关系?

As of CTP5, there seems to be no way to directly turn on cascade deletes on Many to Many associations by Fluent API. 从CTP5开始,似乎无法通过Fluent API直接启用多对多关联的级联删除。

That said, if your intention is to make sure that you can delete the principal (eg a Customer record) without having to worry about the dependent record in the join table (ie Customer_CustomerRole_Mapping) then you don't need to turn on cascades on the database since EF Code First will take care of the cascade deletes on the client side when it comes to Many to Many associations. 也就是说,如果您的目的是确保您可以删除主体(例如客户记录)而不必担心连接表中的依赖记录(即Customer_CustomerRole_Mapping),那么您不需要打开级联数据库,因为EF Code First将在多对多关联中处理客户端的级联删除。

For example, when you delete a Customer object, EF is smart enough to first send a delete statement to get rid of the dependent record in the join table and after that it will send another delete statement to delete the Customer record. 例如,当您删除Customer对象时,EF足够聪明,可以首先发送删除语句以除去连接表中的依赖记录,然后它将发送另一个删除语句来删除Customer记录。

Update: 更新:

Due to a bug in CTP5, you need to explicitly eager/Lazy load the navigation property and have it loaded on the context when you remove the dependent. 由于CTP5中的错误,您需要显式地急切/延迟加载导航属性,并在删除依赖项时将其加载到上下文中。 For example, consider this model: 例如,考虑这个模型:

public class User
{
 public int UserId { get; set; }
 public virtual ICollection Addresses { get; set; }
}

public class Address
{
 public int AddressID { get; set; } 
 public virtual ICollection Users { get; set; }
}

Assuming that we have a User with an address in the database, this code will throw: 假设我们在数据库中有一个具有地址的用户,则此代码将抛出:

using (EntityMappingContext context = new EntityMappingContext())
{
 User user = context.Users.Find(1); 
 context.Users.Remove(user);
 context.SaveChanges();
}

However, this one will perfectly work with removing the link table's record first: 但是,这个将完全适用于首先删除链接表的记录:

using (EntityMappingContext context = new EntityMappingContext())
{
 User user = context.Users.Find(1); 
((IObjectContextAdapter)context).ObjectContext
                                .LoadProperty(user, u => u.Addresses);
 context.Users.Remove(user);
 context.SaveChanges();
}

Please note that this is just a workaround and we will be able to (hopefully) remove a principal without loading its navigation property. 请注意,这只是一种解决方法,我们将能够(希望)删除主体而不加载其导航属性。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM