2016-01-13 48 views
16

在實體框架7時,我嘗試應用遷移我的錯誤在Entity Framework 7中指定ON DELETE NO ACTION?

引進國外KEY約束「FK_ChangeOrder_User_CreatedByID」表「ChangeOrder」可能會導致循環或多個級聯路徑。指定ON DELETE NO ACTION或ON UPDATE NO ACTION,或修改其他FOREIGN KEY約束。
無法創建約束。查看以前的錯誤。

我知道在老版本的實體框架,你會處理這種通過增加

modelBuilder.Conventions.Remove<OneToManyCascadeDeleteConvention>(); 

到的DbContext但EF7 modelBuilder似乎並不有.Conventions它和谷歌只返回舊的EF 4通過EF 6結果。

如何特定實體框架7中的ON DELETE NO ACTION約束?

編輯: 由Oleg提供的答案顯然會做到每個外鍵,但我想全局做它,因爲它會更容易使用一行代碼來全局聲明這一點,然後必須指定代碼出來我將最終擁有的數百種關係中的每一種。

編輯2:代碼奧列格

public class ChangeOrder 
{ 
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)] 
    public int ID { get; set; } 

    public Int16? ApprovedByID { get; set; } 
    public Byte ApprovalStatusID { get; set; } 
    public Int16 AssignedToID { get; set; } 
    public Int16 CreatedByID { get; set; } 
    public Byte CurrentStatusID { get; set; } 
    public DateTime? DateApproved { get; set; } 
    public DateTime? EndDate { get; set; } 
    public Byte ImpactID { get; set; } 
    public Byte PriorityID { get; set; } 
    public DateTime? StartDate { get; set; } 
    public Byte TypeID { get; set; } 

    [Required] 
    public string Name { get; set; } 

    [Required] 
    public string ReasonForChange { get; set; } 

    [ForeignKey("ApprovedByID")] 
    public User ApprovedBy { get; set; } 

    [ForeignKey("ApprovalStatusID")] 
    public ChangeApprovalStatus ApprovalStatus { get; set; } 

    [ForeignKey("AssignedToID")] 
    public User AssignedTo { get; set; } 

    [ForeignKey("CreatedByID")] 
    public User CreatedBy { get; set; } 

    [ForeignKey("ImpactID")] 
    public ChangeImpact Impact { get; set; } 

    [ForeignKey("PriorityID")] 
    public ChangePriority Priority { get; set; } 

    [ForeignKey("TypeID")] 
    public ChangeType ChangeType { get; set; } 

    [ForeignKey("CurrentStatusID")] 
    public ChangeStatus CurrentStatus { get; set; } 
} 
public class JobSightDBContext : DbContext 
{ 
    protected override void OnModelCreating(ModelBuilder modelbuilder) 
    { 
     base.OnModelCreating(modelbuilder); 
    } 

    DbSet<ChangeApprovalStatus> ChangeApprovalStatus { get; set; } 
    DbSet<ChangeImpact> ChangeImapct { get; set; } 
    DbSet<ChangeOrder> ChangeOrders { get; set; } 
    DbSet<ChangePriority> ChangePriorities { get; set; } 
    DbSet<ChangeStatus> ChangeStatus { get; set; } 
    DbSet<ChangeType> ChangeTypes { get; set; } 
    DbSet<User> Users { get; set; } 
} 

回答

25

上GitHut周圍挖掘,並與工作後從MS GitHub上非常專利傢伙目前的解決辦法是把它添加到的DbContext

protected override void OnModelCreating(ModelBuilder modelbuilder) 
{ 
    foreach (var relationship in modelbuilder.Model.GetEntityTypes().SelectMany(e => e.GetForeignKeys())) 
    { 
     relationship.DeleteBehavior = DeleteBehavior.Restrict; 
    } 

    base.OnModelCreating(modelbuilder); 
} 
+0

這救了我一命!!!!!我得到了很多建模FK問題。太感謝了!!!!!!!!!!!!!! –

10

建設

modelBuilder.Entity("myNamespace.Models.ChangeOrder", b => 
    { 
     b.HasOne("myNamespace.Models.User") 
      .WithMany() 
      .HasForeignKey("CreatedByID") 
      .OnDelete(DeleteBehavior.Cascade); 
    }); 

將意味着創造FK_ChangeOrder_User_CreatedByIDREFERENCES [dbo].[User] ([CreatedByID]) ON DELETE CASCADE。它應該存在於遷移期間創建的protected override void BuildModel(ModelBuilder modelBuilder)YourContextModelSnapshot.cs。我不確定我是否完全理解了您的問題,但我認爲您應該將此構造添加到XXXModelSnapshot.cs或刪除此處已存在的不需要的構造。

更新:我看到你在模型中有問題。你有

public Int16? ApprovedByID { get; set; } 
public Int16 AssignedToID { get; set; } 
public Int16 CreatedByID { get; set; } 

// navigation properties 

[ForeignKey("ApprovedByID")] 
public User ApprovedBy { get; set; } 

[ForeignKey("AssignedToID")] 
public User AssignedTo { get; set; } 

[ForeignKey("CreatedByID")] 
public User CreatedBy { get; set; } 

下列屬性默認情況下遷移嘗試設置DeleteBehavior.Cascade上的所有屬性。

你可以通過改變OnModelCreating,其中規定無論是DeleteBehavior.Restrict行爲所有鍵或在一組唯一的關鍵的DeleteBehavior.CascadeDeleteBehavior.SetNull行爲覆蓋的行爲。例如,下面的代碼使用上CreatedByIDDeleteBehavior.Cascade(產生ON DELETE CASCADE的外鍵)上的其它外鍵(上外鍵沒有ON DELETE)和DeleteBehavior.Restrict

public class JobSightDBContext : DbContext 
{ 
    protected override void OnModelCreating(ModelBuilder modelbuilder) 
    { 
     base.OnModelCreating(modelbuilder); 

     modelbuilder.Entity(typeof (ChangeOrder)) 
      .HasOne(typeof (User), "ApprovedBy") 
      .WithMany() 
      .HasForeignKey("ApprovedByID") 
      .OnDelete(DeleteBehavior.Restrict); // no ON DELETE 
     modelbuilder.Entity(typeof (ChangeOrder)) 
      .HasOne(typeof (User), "AssignedTo") 
      .WithMany() 
      .HasForeignKey("AssignedToID") 
      .OnDelete(DeleteBehavior.Restrict); // no ON DELETE 
     modelbuilder.Entity(typeof (ChangeOrder)) 
      .HasOne(typeof (User), "CreatedBy") 
      .WithMany() 
      .HasForeignKey("CreatedByID") 
      .OnDelete(DeleteBehavior.Cascade); // set ON DELETE CASCADE 
    } 

    DbSet<ChangeApprovalStatus> ChangeApprovalStatus { get; set; } 
    DbSet<ChangeImpact> ChangeImapct { get; set; } 
    DbSet<ChangeOrder> ChangeOrders { get; set; } 
    DbSet<ChangePriority> ChangePriorities { get; set; } 
    DbSet<ChangeStatus> ChangeStatus { get; set; } 
    DbSet<ChangeType> ChangeTypes { get; set; } 
    DbSet<User> Users { get; set; } 
} 
+0

有沒有辦法在全球範圍內做到這一點還是我必須這樣做,每個數百關係我有嗎?這樣做會爲我創造許多額外的編碼,我寧願避免這樣做。 – Matthew

+0

@MatthewVerstraete:很難回答只有錯誤信息。我想你首先創建了一組具有許多數據符號的類,然後創建'DbContext'派生的'XXXContext',它具有許多屬性,如'public DbSet Users {get;組; }','public DbSet ChangeOrders {get;組; }'。我認爲'User','ChangeOrder'中的一些定義將被EF Migration以一種錯誤的方式解釋,但我無法猜測它到底是什麼。一位需要分析完整模型的人來找到原因。 – Oleg

+0

不知道你有什麼問題了解。我正在尋找'modelBuilder.Conventions.Remove ();'的EF7版本''但是我已經添加了DBContext和一個模型給你看看 – Matthew

相關問題