实体框架代码首先对0.1到许多进行级联删除

本文关键字:许多进 级联 删除 代码 框架 实体 | 更新日期: 2023-09-27 18:30:12

我将这种模型用于0..1对多关系。页面必须具有有效的图书id或为null。

public class Book
{
    [Key]
    public Guid Id { get; set; }
    public virtual List<Page> Pages { get; set; }
}
public class Page
{
    [Key]
    public Guid Id { get; set; }
    public virtual Book Book { get; set; }
}

我想添加级联删除,这样,如果一本书被删除,那么它的所有页面也会被删除,而不是设置为null。

我可以(只能?)用流利的api:来做到这一点

modelBuilder.Entity<Page>()
    .HasOptional(a => a.Book)
    .WithOptionalDependent()
    .WillCascadeOnDelete(true);

使用[Required]是不合适的,因为该字段不是必需的。

但是,这会在数据库中创建另一列Book_Id1、索引和外键,而不是在现有FK上添加级联删除,因为它被定义了两次。

如果我注释掉Book.Pages属性,它会起作用,但我将失去调用book的能力。页面,而必须调用dbcontext.Pages.Where(p => p.Book.Id == book.Id),这并不理想,因为我不希望调用代码必须了解dbcontext对象。

有没有办法同时使用Book.Pages属性和级联删除?也许将两者设置为使用相同的FK名称?

实体框架代码首先对0.1到许多进行级联删除

这里你可以做什么

public class Book
{
    [Key]
    public Guid Id { get; set; }
    public virtual List<Page> Pages { get; set; }
}
public class Page
{
    [Key]
    public Guid Id { get; set; }
    public Guid BookId { get; set;}
    //[ForeignKey("BookId")] you can add the fluent here or during entity builder
    public virtual Book Book { get; set; }
}

modelBuilder.Entity<Page>()
    .HasOptional(a => a.Book)
    .WithMany(a=>a.Pages)
    .HasForeignKey(a=>a.BookId)
    .WillCascadeOnDelete(true);
var pages= dbcontext.Pages.Where(p => p.BookId == book.Id); // this will work

该代码应该可以正常工作

我认为在代码优先的情况下,你必须尝试这个

dbcontext.Page.RemoveRange(book.Pages);
dbcontext.Book.Remove(book);
dbContext.SaveChanges();