1

我们有一个模型,其中一个公共实体被其他实体(域)使用,我们希望以一种通用的方式在实体之间创建一个关系,如果可能。实体框架,当一个实体被其他几个实体使用时建模场景

在这个例子中,该地址由学生和由学校和每个人都可以有一个或几个地址,一个地址只能属于一个实体(不多对多关系)

public class Address 
    { 
     public int Id { get; set; } 
     public string Name { get; set; } 
     public int? RefId { get; set; } 
    } 

public class School 
    { 
     public int Id { get; set; } 
     public string SchoolName { get; set; } 
     public ICollection<Address> Address { get; set; } 
    } 

    public class Student 
    { 
     public int Id { get; set; } 
     public string StudentName { get; set; } 
     public ICollection<Address> Address { get; set; } 
    } 

EF6模型首先创建下面的模式(不带任何附加的配置)

CreateTable(
       "dbo.Addresses", 
       c => new 
        { 
         Id = c.Int(nullable: false, identity: true), 
         Name = c.String(), 
         RefId = c.Int(), 
         School_Id = c.Int(), 
         Student_Id = c.Int(), 
        }) 
       .PrimaryKey(t => t.Id) 
       .ForeignKey("dbo.Schools", t => t.School_Id) 
       .ForeignKey("dbo.Students", t => t.Student_Id) 
       .Index(t => t.School_Id) 
       .Index(t => t.Student_Id); 

本质上,加入外键对于每个实体。这种模式很有效,但我们不确定这是否是最佳做法。

我们看到的问题是,当使用Address添加其他实体时,我们需要继续添加与FK(例如Library - LibraryId)一起的新实体的ID。它打破了地址概念的抽象。

我们尝试使用抽象参考ID(RefId)并配置EF将其用作FK键,但它为同一个表创建了两个FK。

另一种选择是不使用任何导航属性并手动填充和处理实体之间的关系 - 实际上不使用ORM功能。

由于这似乎是一个常见的情况,有没有一种方法来以通用的方式建模?

+0

这里的(反)模式名称是* polymorpic associations *。使用这个作为搜索词,你会发现很多帖子让你走上正确的轨道。 –

回答

0

的一种方法是创建一个抽象类和继承:

public abstract class AddressRef 
{ 
    public int AddressId { get; set; } 

    // Navigational properties 
    public virtual Address { get; set; } 
} 

现在你可以继承时,需要在地址引用上面的类:

public class School : AddressRef 
{ 
    // other properties 
} 

public class Student : AddressRef 
{ 
    // other properties 
} 

这将允许你只在一个地方管理参考,并根据需要在多个类中使用它。