【问题标题】:Entity framework - Updating list when updating object实体框架 - 更新对象时更新列表
【发布时间】:2014-12-24 12:48:53
【问题描述】:

假设我有一个独立包中的类,并且可以被多个对象使用,例如:

public class TimeSlot 
{
    [Required]
    public int Id { get; set; }

    [Required]
    public DateTime StartTime { get; set; }

    [Required]
    public DateTime EndTime { get; set; }
} 

不是这个 TimeSlot 可以从以下两个类中引用:

public class Business
{
    public int Id { get; set; }

    public virtual IList<TimeSlot> OpeningHours { get; set; }
}

和

public class Delivery
{
    public int Id { get; set; }

    public virtual IList<TimeSlot> DeliveryHours { get; set; }
}

使用实体框架代码优先,这将产生一个TimeSlot 表,其中包含Business 和Delivery 对象的外键。

假设我修改了一个Business 对象(清除OpeningHours 的列表并在代码中添加新的)并更新它;更新后,旧的TimeSlot 记录会将BusinessId 外键设置为NULL,而不是被删除。 什么是正确的实现来删除这些记录,因为它们不再需要(最好不污染TimeSlot 对象)?

【问题讨论】:

    标签: c# asp.net entity-framework ef-code-first code-first


    【解决方案1】:

    在您的 DbContext 类中更改 OnModelCreating。将 willCascadeOnDelete 添加为 true。

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();
    
         modelBuilder.Entity<Business>()
          .HasOptional(a => a.OpeningHours)
          .WithOptionalDependent()
          .WillCascadeOnDelete(true);
    
        base.OnModelCreating(modelBuilder);
    }
    

    【讨论】:

    • 您好,感谢您的回答。但是,这不起作用。我找不到 WithMany;我找到了 HasMany 并尝试使用它,但随后无法在链式调用中调用 WillCascadeOnDelete。
    • 请立即查看。我更新了答案。希望这次能成功。
    • 现在我得到:无法将“System.Collections.Generic.List`1[ZMvcHelpers.Models.Time.TimeSlot]”类型的对象转换为“ZMvcHelpers.Models.Time.TimeSlot”类型。
    • 很抱歉,它仍然无法正常工作...我在更新数据库时向您显示了错误消息。您的解决方案不能解决问题:(
    • 'modelBuilder.Entity().HasOptional(e => e.OpeningHours).WithOptionalPrincipal().WillCascadeOnDelete(true);' @zahikaram
    【解决方案2】:

    使用 EF 删除子集合元素非常复杂。当您清除集合或从中删除项目时,EF 会很安全,不会假定您要删除对象,而只是想破坏关联。

    所以你必须明确删除子项:

    db.TimeSlots.RemoveRange(business.OpeningHours);
    db.SaveChanges();
    

    (RemoveRange 是 EF 6,在早期版本中,您必须遍历 business.OpeningHours 并执行 db.TimeSlots.Remove())。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-05-19
      • 2015-12-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多