要在 EF Core 中添加没有外键的导航属性,使用 .NET Core Web API 进行 DB-first 迁移

Posted

技术标签:

【中文标题】要在 EF Core 中添加没有外键的导航属性,使用 .NET Core Web API 进行 DB-first 迁移【英文标题】:To add navigation property without foreign key in EF Core, DB-first migration with .NET Core Web API 【发布时间】:2020-08-11 17:30:18 【问题描述】:

我正在使用现有系统并将其更新为 .NET Core、Web API 和 EF Core。

现有系统有2张表:

父表:ID、名称等。 子表:Id、ParentId、姓名等。

虽然ParentId存在于子表中,但没有外键引用,但我希望在查询父表时能够使用include。我已要求不要添加 FK 作为删除的一部分,他们将 -ve 值放入 parentId 列。通过这种方式,他们可以将其带回并以这种方式构建遗留系统。

现在,在 db-first 迁移中,如何在没有 fk 的情况下指定导航属性,以便我的 EF Core 执行关系;或者至少将它们一起归还。添加可为空的外键不是一种选择,因为添加 -ve 值时会破坏系统。

我确实建议完全清理数据库并摆脱 -ve 值,但这涉及大量测试并且无法交付。长话短说如何在数据库首次迁移中添加没有外键的导航属性?

我尝试在模型中添加集合和虚拟条目,但迁移后它被覆盖了。我已经根据本文档在模型构建器上使用 HasMany 添加了这个 - https://docs.microsoft.com/en-us/ef/core/modeling/relationships?tabs=fluent-api%2Cfluent-api-simple-key%2Csimple-key

但是脚手架覆盖了我的导航属性

【问题讨论】:

【参考方案1】:

我找到了答案。

在 EF core 3.x 中,由 DBFrist 脚手架创建的 dbcontext 都是部分类。 所以我做了以下事情: 1. 上下文类的新部分类 - 这里我使用 OnModelCreatingPartial() 方法添加了导航属性的关系。下面的例子

public partial class dbContext : DbContext

    partial void OnModelCreatingPartial(ModelBuilder builder)
    
        builder.Entity<Packcomponent>()
        .HasOne(p => p.Pack)
        .WithMany(b => b.PackComponent)
        .HasForeignKey(p => p.PackId);
    

    在一个新文件中扩展了部分类并在那里添加了导航属性。

    
     public partial class Packcomponent
     
       public Pack Pack  get; set; 
     
     public partial class Pack
     
       public List PackComponent  get; set; 
     

这种方式在搭建脚手架时不会覆盖自定义导航属性,我也可以使用此属性执行 .Include() 等 EF 操作并保存相关实体。真是太棒了!!

【讨论】:

以上是关于要在 EF Core 中添加没有外键的导航属性,使用 .NET Core Web API 进行 DB-first 迁移的主要内容,如果未能解决你的问题,请参考以下文章

ef core 如何一次从具有外键的不同表中获取数据? (数据库优先)

没有导航属性的EF Code First外键

EF Core 2.0 Identity - 添加导航属性

如何在 EF 7 alpha 中添加外键

EF6:导航属性外键到外键

EF Code First CTP5 - 使用属性名称作为外键的列名