【问题标题】:Primary key value in Entity Framework实体框架中的主键值
【发布时间】:2020-01-13 17:02:58
【问题描述】:

实体布局包含场地的int值(VenueIdprop),自身的id等信息。

CONSTRAINT [FK_Venue_Layout] FOREIGN KEY ([VenueId]) REFERENCES [dbo].[Venue] ([Id])

当我尝试添加两个具有相同 VenueId 的布局时,我收到了这个错误

对数据库的更改已成功提交,但在更新对象上下文时出错。 ObjectContext 可能处于不一致的状态。内部异常消息:保存或接受更改失败,因为多个“DataAccess.Models.LayoutModel”类型的实体具有相同的主键值。确保显式设置的主键值是唯一的。确保在数据库和实体框架模型中正确配置了数据库生成的主键。使用实体设计器进行数据库优先/模型优先配置。使用“HasDatabaseGeneratedOption”流式 API 或“DatabaseGeneratedAttribute”进行 Code First 配置。”

我的实体代码:

[Table("Layout")]
public class LayoutModel
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    [Key]
    public int Id { get; set; }

    [DatabaseGenerated(DatabaseGeneratedOption.None)]
    public int VenueId { get; set; }

    public string Description { get; set; }
}

插入代码:

var layouts = new List<LayoutModel>
            {
                new LayoutModel { VenueId = 1, Description = "First layout" },
                new LayoutModel { VenueId = 1, Description = "Second layout" },
            };
            _context.Layouts.AddRange(layouts);
            _context.SaveChanges();

我不允许使用导航属性

【问题讨论】:

  • 您可能正在尝试添加 2 个 LayoutModel 和相同的 Id
  • 您可以尝试使用 [Column(Order = 0)] 为 Id 和 [Column(Order = 1)] 为 VenueId 来装饰属性。此外,使用 [ForeignKey("Venue")] 装饰 VenueId。另外,您能否粘贴 Id、venueId 组合的 INSERT 值?
  • @Magnetron 他们有不同的 id
  • @sam var layouts = new List&lt;LayoutModel&gt; { new LayoutModel { Id = 1, VenueId = 1, Description = "First layout" }, new LayoutModel { Id = 2, VenueId = 1, Description = "Second layout" }, }; _context.Layouts.AddRange(layouts); _context.SaveChanges(); 我有一个 ID 为 1 的场地。我无法使用 [ForeignKey("Venue")] 装饰 VenueId,因为我无法添加导航属性
  • @Nicefsf:请更新帖子而不是 cmets。当 Id 是标识列时,为什么要将 Id 显式设置为 1 和/或 2?请删除该赋值语句。

标签: c# entity-framework


【解决方案1】:

在 LayoutViewModel 的定义中,Id 列或属性被标记为标识列

[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
[Key]
public int Id { get; set; }

因此,无需显式分配它,因为在将行插入布局表后,它将由数据库自动填充。请按以下方式更新您的布局人口以删除 Id 分配:

var layouts = new List<LayoutModel> { 
    new LayoutModel { /*Id = 1,*/ VenueId = 1, Description = "First layout" }, 
    new LayoutModel { /*Id = 2, */ VenueId = 1, Description = "Second layout" }
};
// code smell
foreach(var layout in layouts)
{
     context.Entry(layout).State = EntityState.Added;
}
_context.Layouts.AddRange(layouts);
_context.SaveChanges();

另外,请更新您的 LayoutModel 如下:

public class LayoutModel
{
     [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
     [Key]
     [Column(Order = 0)]
     public int Id { get; set; }

     [Key]
     [Column(Order = 1)]
     //[ForeignKey("Venue")]
     [DatabaseGenerated(DatabaseGeneratedOption.None)]
     public int VenueId { get; set; }

     //public virtual VenueModel Venue { get; set; } //Please correct Venue property type
}

另外,请确认 Venue 是否加载到 _context.Layouts 中。

【讨论】:

  • 我在粘贴此代码之前添加了 id 的分配
  • @Nicefsf,您能否更新您的帖子以描述实际引发异常的代码。提前谢谢你。
  • @Nicefsf 你能用 ForeignKey 属性装饰 VenueId 吗?
  • 要使用 [ForeignKey] 我需要有 Venue 导航属性,但我不能(任务要求)如前所述
  • @Nicefsf 您能否尝试手动更新 EntityState,如我的帖子中所示。
猜你喜欢
  • 2011-07-20
  • 2010-11-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多