实体框架对同一个表

时间:2015-06-08 19:28:18

标签: c# entity-framework ef-code-first code-first

我在使用EF代码优先创建数据库时遇到问题。我有一个实体玩家和一个实体炸船。

每个友谊都会引用两名球员。其中一个是发件人,另一个是友谊的接收者。

这是我的实体:

Player.cs

public class Player
{
    public int PlayerId { get; set; }

    [Required]
    public string Name { get; set; }

    [Required]
    public string Email { get; set; }

    [InverseProperty("Receiver")]
    public virtual List<Friendship> FriendshipsIncoming { get; set; }

    [InverseProperty("Sender")]
    public virtual List<Friendship> FriendshipsOutgoing { get; set; }
}

Friendship.cs

public class Friendship
{
    public int FriendshipId { get; set; }

    public int SenderId { get; set; }
    public int ReceiverId { get; set; }

    [ForeignKey("Sender")]
    public Player Sender { get; set; }

    [ForeignKey("Receiver")]
    public Player Receiver { get; set; }

    [Required]
    public bool Confirmed { get; set; }
}

我尝试按照本教程中显示的方式实现关系: http://www.entityframeworktutorial.net/code-first/inverseproperty-dataannotations-attribute-in-code-first.aspx

尝试使用&#34; update-database&#34;更新数据库时命令我收到以下错误消息:

  

属性&#39; Receiver&#39;上的ForeignKeyAttribute在类型&#39; Darta.WebApi.Models.Friendship&#39;无效。外键名称&#39; Receiver&#39;在依赖类型&#39; Darta.WebApi.Models.Friendship&#39;中找不到。 Name值应该是以逗号分隔的外键属性名称列表。

我也尝试使用如下所示的fluent-api解决问题: http://csharpwavenet.blogspot.sg/2013/06/multiple-foreign-keys-with-same-table.html

protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.Entity<Friendship>()
            .HasRequired(b => b.Sender)
            .WithMany(a => a.FriendshipsOutgoing)
            .HasForeignKey(b=>b.SenderId);

        modelBuilder.Entity<Friendship>()
            .HasRequired(b => b.Receiver)
            .WithMany(a => a.FriendshipsIncoming)
            .HasForeignKey(b => b.ReceiverId);
    }

在这种情况下,我收到以下错误:

  

介绍FOREIGN KEY约束&#39; FK_dbo.Friendships_dbo.Players_SenderId&#39;在桌上&#39;友谊&#39;可能会导致循环或多个级联路径。指定ON DELETE NO ACTION或ON UPDATE NO ACTION,或修改其他FOREIGN KEY约束。   无法创建约束或索引。查看以前的错误。

2 个答案:

答案 0 :(得分:2)

您应该只需要数据注释 FluentAPI。你不需要两者兼而有之。如果您想使用[ForeignKey][InverseProperty]属性,请删除FluentAPI代码。

另请注意,在[ForeignKey][InverseProperty]属性中,您需要指定列的名称,而不是导航属性。

public class Player
{
    public int PlayerId { get; set; }

    [Required]
    public string Name { get; set; }

    [Required]
    public string Email { get; set; }

    [InverseProperty("ReceiverId")]
    public virtual ICollection<Friendship> FriendshipsIncoming { get; set; }

    [InverseProperty("SenderId")]
    public virtual ICollection<Friendship> FriendshipsOutgoing { get; set; }
}

public class Friendship
{
    public int FriendshipId { get; set; }

    public int SenderId { get; set; }
    public int ReceiverId { get; set; }

    [ForeignKey("SenderId")]
    public Player Sender { get; set; }

    [ForeignKey("ReceiverId")]
    public Player Receiver { get; set; }

    [Required]
    public bool Confirmed { get; set; }
}

答案 1 :(得分:2)

我会纠正答案。 InverseProperty必须是有效的实体类型。所以在这种情况下,Friendship.Receiver,Friendship.Sender

公共类播放器    {        public int PlayerId {get;组; }

   [Required]
   public string Name { get; set; }

   [Required]
   public string Email { get; set; }

   [InverseProperty("Receiver")]
   public virtual ICollection<Friendship> FriendshipsIncoming { get; set; }

   [InverseProperty("Sender")]
   public virtual ICollection<Friendship> FriendshipsOutgoing { get; set; }

}

公共课友谊    {        public int FriendshipId {get;组; }

   public int SenderId { get; set; }
   public int ReceiverId { get; set; }

   [ForeignKey("SenderId")]
   public Player Sender { get; set; }

   [ForeignKey("ReceiverId")]
   public Player Receiver { get; set; }

   [Required]
   public bool Confirmed { get; set; }

}