多个DataAnnotation ForeignKeys循环或多个级联路径异常

时间:2017-02-22 23:54:52

标签: c# ef-code-first entity-framework-6

我正在努力理解和信任EF。 我有一个包含表格的数据库,我试图用EF Code-First技术复制大部分结构作为练习基础知识的练习。

我所有的课程都以'Hb'作为名字的前缀。 我想在其他类上编写对象引用,而不在属性名称上使用“Hb”。

我按照此site

的说明操作

第一个实现导致例外:

  

引入FOREIGN KEY约束   表'HbZipcode'上的'FK_Common.HbZipcode_Common.HbCountry_CountryId'   可能会导致循环或多个级联路径。指定ON DELETE NO   ACTION或ON UPDATE NO ACTION,或修改其他FOREIGN KEY   限制。无法创建约束或索引。见前   错误。

[Required, ForeignKey("Country")]
public int CountryId { get; set; }
public virtual HbCountry Country { get; set; }

[Required, ForeignKey("State")]
public int StateId { get; set; }
public virtual HbState State { get; set; }

[Required, ForeignKey("City")]
public int CityId { get; set; }
public virtual HbCity City { get; set; }

// This Foreignkey never throw exception
[ForeignKey("Neighborhood")]
public int? NeighborhoodId { get; set; }
public virtual HbNeighborhood Neighborhood { get; set; }

我做错了什么,我看不到。
如果有人能帮助我,那就太好了。

修改

应用 plushpuffin 传递的解决方案后,一切都按预期进行 这是代码:

var modelConfig = dbModelBuilder.Entity<HbZipcode>();
modelConfig
    .HasRequired(zc => zc.Country)
    .WithMany(c => c.Zipcodes)
    .HasForeignKey(zc => zc.CountryId)
    .WillCascadeOnDelete(false);

modelConfig
    .HasRequired(zc => zc.State)
    .WithMany(s => s.Zipcodes)
    .HasForeignKey(zc => zc.StateId)
    .WillCascadeOnDelete(false);

modelConfig
    .HasOptional(zc => zc.Neighborhood)
    .WithMany(n => n.Zipcodes)
    .HasForeignKey(zc => zc.NeighborhoodId)
    .WillCascadeOnDelete(false);
Delete cascade上的{p> HbZipcode现在仅在HbCity被删除时出现

1 个答案:

答案 0 :(得分:1)

这里发生的事情是HbZipCode有多个表的外键,你不能用ON CASCADE DELETE创建2+外键约束,它有多种方法可以从同一个表中删除相同的行。

您的实体类可能已设置为当删除HbZipCode时,它将删除级联到HbNeighborhood,然后是HbCity,然后是HbState,然后是HbCountry。如果您使用指向HbCity的ON CASCADE DELETE向HbZipCode添加了另一个外键,删除HbZipCode记录将导致直接级联删除HbNeighborhood并直接级联删除到HbCity,但被删除的HbNeighborhood也会 导致级联删除HbCity。

您需要做的是通过关闭大多数CASCADE DELETE来解析HbCity和其他实体类型的多个级联删除路径。

有关流畅配置的信息,请参阅this MSDN page

你可能想要这样的东西:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    modelBuilder.Entity<HbZipCode>() 
        .HasRequired(t => t.HbCity)
        .WithMany(t => t.HbZipCodes)
        .HasForeignKey(t => t.CityId)
        .WillCascadeOnDelete(false);
}