【发布时间】:2020-10-03 14:55:14
【问题描述】:
我正在尝试将 EF 配置为在检索用户或产品时包含文档。实体 Document 有一个 ReferenceId 属性,它应该存储 UserId 或 ProductId。这样,当我为用户或产品保存文档时,UserId 或 ProductId 会保存到 Document.ReferenceId。
实体:
公共类用户
{
公共字符串 ID { 获取;放; }
公共 ICollection 文档 { 获取;放; }
}
公开课产品
{
公共字符串 ID { 获取;放; }
公共 ICollection 文档 { 获取;放; }
}
公共类文档
{
公共字符串 ID { 获取;放; }
公共字符串 ReferenceId { 获取;放; }
}
配置:
builder.Entity(e => { e.HasKey(e => e.Id); e.Property(p => p.Id).ValueGeneratedOnAdd(); e.HasMany(e => e.Documents) .WithOne() .OnDelete(DeleteBehavior.Cascade); }); builder.Entity(e => { e.HasKey(e => e.Id); e.Property(p => p.Id).ValueGeneratedOnAdd(); e.HasMany(e => e.Documents) .WithOne() .OnDelete(DeleteBehavior.Cascade); }); builder.Entity(e => { e.HasKey(e => e.Id); e.Property(p => p.Id).ValueGeneratedOnAdd(); e.ToTable("文档"); });
保存:
var 用户 = 新用户 { };
var userDocument = new Document { ReferenceId = user.Id };
var 产品 = 新产品 { };
var productDocument = new Document { ReferenceId = product.Id };
_context.Users.Add(user);
_context.Products.Add(product);
_context.Add(userDocument);
_context.Add(productDocument);
_context.SaveChanges();
迁移:
migrationBuilder.CreateTable(
名称:“文件”,
列:表 => 新
{
Id = table.Column(可为空:false),
ReferenceId = table.Column(可为空: true),
ProductId = table.Column(可为空: true),
UserId = table.Column(可为空:true)
},
约束:表 =>
{
table.PrimaryKey("PK_Documents", x => x.Id);
表.外键(
名称:“FK_Documents_Products_ProductId”,
列:x => x.ProductId,
principalTable: "产品",
主体列:“ID”,
onDelete: 参考动作.Cascade);
表.外键(
名称:“FK_Documents_Users_UserId”,
列:x => x.UserId,
principalTable: "用户",
主体列:“ID”,
onDelete: 参考动作.Cascade);
});
我不想在 Documents 表上创建 2 个外键(ProductId 和 UserId)。有没有办法让 EF 自动将 UserId 和 ProductId 链接到 ReferenceId?
【问题讨论】:
-
试着想象一下这在纯 SQL 中应该是什么样子。一个字段不可能是多个表的 FK。这就是臭名昭著的多态关联(反)模式。
-
嗨格特,我同意你的看法。我不想有任何FK。我想要的是找到一种方法(如果可能的话)让 EF 自动将 User.Id 和 Product.Id 映射到 Document.ReferenceId (所以我不需要手动分配值)。检索记录时也是如此。
-
不确定如何创建没有外键的相关实体。拥有外键并不意味着您必须手动分配它们
-
您实际上是在让 EF 读懂您的想法。不幸的是,这不受支持。
-
您可以尝试在 Documents 属性上添加 [NotMapped]。所以你不会在你的迁移文件上看到外键......我认为最简单的方法是,即使这样,它也不是一个很好的数据库结构......
标签: c# entity-framework-core .net-core-3.1 ef-core-3.0