为一对多关系生成意外的外键

Unexpected foreign key generated for one to many relationship

我已经声明了两个 classes - Person 和 Vehicle,如下所示

public class Person
{
    public Person()
    {
        this.Vehicles = new HashSet<Vehicle>();
    }

    [Key]
    public int PersonID { get; set; }

    [Required, MaxLength(50)]
    public string FirstName { get; set; }

    [Required, MaxLength(50)]
    public string MiddleName { get; set; }

    [Required, MaxLength(50)]
    public string LastName { get; set; }

    [Required, MaxLength(10)]
    public string MobileNo1 { get; set; }
    [MaxLength(10)]
    public string MobileNo2 { get; set; }

    [MaxLength(50)]
    public string Email1 { get; set; }
    [MaxLength(50)]
    public string Email2 { get; set; }

    public virtual ICollection<Vehicle> Vehicles { get; set; }
}

public class Vehicle
{
    [Key]
    public int VehicleID { get; set; }

    [MaxLength(20)]
    public string VehicleNumber { get; set; }

    [ForeignKey("VehicleOwner")]
    public int? VehicleOwnerID { get; set; }
    [ForeignKey("VehicleOwnerID")]
    public virtual Person VehicleOwner { get; set; }

    [ForeignKey("VehicleDriver")]
    public int? VehicleDriverID { get; set; }
    [ForeignKey("VehicleDriverID")]
    public virtual Person VehicleDriver { get; set; }

    [ForeignKey("Person")]
    public int? PersonID { get; set; }
    [ForeignKey("PersonID")]
    public virtual Person Person { get; set; }

}

这会在 Vehicles table 上生成两个外键,如

.ForeignKey("dbo.Person", t => t.PersonID)
.ForeignKey("dbo.Person", t => t.Person_PersonID)

而我所期望的只是

.ForeignKey("dbo.Person", t => t.PersonID)

最初我认为这可能是因为我错过了将实体声明为虚拟的,但事实并非如此。我无法检测到此代码的问题。

与 Vehicles 一样,我还有另一个 class - 与 Person 的结构和关系有些相同的文档。但是对于 Documents,外键是按预期生成的。

正如史蒂夫所说,这是因为您从车辆 class 中引用了 Person。因此,Entity Framework 创建了 3 个键,一个用于 Person、VehicleOwner 和 VehicleDriver。然而,由于从人那里收集车辆,它创建了另一个密钥。你必须在这里使用反向属性属性来告诉Entity Framework你的意思是在实际Vehicle.Person属性上建立Vehicle和Person之间的关系。您可以通过

[InverseProperty("Person")]
public virtual ICollection<Vehicle> Vehicles { get; set; }

另外,你是多余的:

[ForeignKey("Person")]
public int? PersonID { get; set; }
[ForeignKey("PersonID")]
public virtual Person Person { get; set; }

从 int 中删除外键?您车辆中的 PersonID class.

你有 3 个 classes 指向 Person,所以配置为:

public class Vehicle
{
    [Key]
    public int VehicleID { get; set; }

    [MaxLength(20)]
    public string VehicleNumber { get; set; }

    public int? VehicleOwnerID { get; set; }
    [ForeignKey("VehicleOwnerID")]
    public virtual Person VehicleOwner { get; set; }

    public int? VehicleDriverID { get; set; }
    [ForeignKey("VehicleDriverID")]
    public virtual Person VehicleDriver { get; set; }

    public int? PersonID { get; set; }
    [ForeignKey("PersonID")]
    public virtual Person Person { get; set; }

}

虽然语法不正确,但第二个外键来自人身上的车辆集合,EF 无法解析它属于哪个 FK。

所以在你的 Person class 中你需要指向车辆中相应的导航:

[InverseProperty("Person")]
public virtual ICollection<Vehicle> Vehicles { get; set; }

http://www.entityframeworktutorial.net/code-first/inverseproperty-dataannotations-attribute-in-code-first.aspx