在设置Entity Framework Core外键时出现了一个奇怪的问题。 EF一直在为我的属性自动添加阴影属性,并正在为其创建外键。
这对我来说是完全可以的,但是-我希望能够将外键删除行为设置为级联-使用该“自动”阴影属性,我不允许这样做。
因此,我决定使用Fluent API创建自己的外键:
modelBuilder.Entity<PostDataModel>(e =>
{
// Primary key
e.HasKey(c => c.Id);
// Relation
e.HasOne<PostGroupDataModel>()
.WithMany()
.HasForeignKey("GroupId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
但这并没有太大帮助-仍在为表(GroupId1
)生成自动生成的阴影属性:
public class PostGroupDataModel
{
public int Id { get; set; }
public string Name { get; set; }
public string Params { get; set; }
public List<PostDataModel> Posts { get; set; }
}
public class PostDataModel
{
public int Id { get; set; }
public string Content { get; set; }
public PostGroupDataModel Group { get; set; }
}
是否可以关闭EF Core中阴影属性的自动生成?或至少修改生成的阴影属性以在层叠时删除?
答案 0 :(得分:3)
问题不是阴影属性,而是流畅的配置:
e.HasOne<PostGroupDataModel>()
.WithMany()
通过使用无参数重载,您可以有效地告诉EF两端建立没有导航属性的关系。但是,您确实具有导航属性,因此EF Core使用常规的FK属性/列名称创建了另一个关系。仅仅因为默认名称GroupId
已为您的显式关系保留,它会在其后附加数字以使其唯一。
解决方案是始终使用Has
/ With
重载,这些重载表示存在/不存在导航属性。就您而言:
e.HasOne(x => x.Group)
.WithMany(x => x.Posts)
您可以保留其余配置,但由于GroupId
是FK属性/列的默认值,因此可以跳过.HasForeignKey("GroupId")
。同样,由于DeleteBehavior.Cascade
是必需关系的默认值,因此.OnDelete(DeleteBehavior.Cascade)
也可以跳过,唯一剩下的可以是.IsRequired()
。即
.HasForeignKey("GroupId") // optional
.OnDelete(DeleteBehavior.Cascade) // optional
.IsRequired();
当然,明确指定它们不会造成伤害。