簡體   English   中英

實體框架的TPC映射導致錯誤

[英]Entity Framework's TPC mapping results in error

我有以下模型:

public class Person
{
    public int PersonId { get; set; }

    public string Name { get; set; }

    public int Age { get; set; }
}

public class Student : Person
{
    public int Payment { get; set; }
}

public class Teacher : Person
{
    public int Wage { get; set; }
}

在數據庫中,我有兩個表叫做TeachersStudents 我想使用實體框架的TPC映射。 我的上下文類是:

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.Entity<Person>()
        .Property(i => i.PersonId)
        .HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);

        modelBuilder.Entity<Teacher>().Map(m =>
        {
            m.MapInheritedProperties();
            m.ToTable("Teacher", "dbo");
        }); 

        modelBuilder.Entity<Student>().Map(m =>
        {
            m.MapInheritedProperties();
            m.ToTable("Student", "dbo");
        }); 
    }

但是當我想添加一名老師時,出現以下錯誤:

已成功提交對數據庫的更改,但是在更新對象上下文時發生錯誤。 ObjectContext可能處於不一致狀態。 內部異常消息:AcceptChanges無法繼續,因為對象的鍵值與ObjectStateManager中的另一個對象沖突。 在調用AcceptChanges之前,請確保鍵值是唯一的。

怎么了

看到這個鏈接

我們得到此異常的原因是因為DbContext.SaveChanges()在內部調用其內部ObjectContext的SaveChanges方法。 默認情況下,ObjectContext的SaveChanges方法在執行數據庫修改后默認調用AcceptAllChanges。

AcceptAllChanges方法僅迭代ObjectStateManager中的所有條目,並在每個條目上調用AcceptChanges。 由於實體處於“已添加”狀態,因此基於數據庫返回的主鍵值(即PersonId),AcceptChanges方法將它們的臨時EntityKey替換為常規EntityKey,這是發生問題的原因,因為兩個實體都被分配了相同的值對於數據庫的主鍵(即在兩個PersonId = 1上),問題是ObjectStateManager無法跟蹤具有相同EntityKey值的相同類型的對象,因此會拋出該異常。 如果您仔細查看上面的TPC的SQL模式,您將看到為什么數據庫為主鍵生成相同值的原因:Student和Teacher表中的PersonId列已被標記為身份。

嘗試這個:

public srting PersonId { get; set; }

並將您的配置更改為:

   modelBuilder.Entity<Person>()
        .Property(i => i.PersonId)
        .HasDatabaseGeneratedOption(DatabaseGeneratedOption.None);

並將您的班級更改為abstract /

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM