2016-03-04 58 views
2

我有两个POCO实体,ApplicationUser和Account。重复的外键

  • 一个帐户有许多ApplicationUser。
  • 每个帐户只能有一个ApplicationUser谁是BillingContact

所以,我的实体有:

public class ApplicationUser 
{ 
    public string Id { get; set; } 

    public int AccountId { get; set; } 
    public virtual Account Account { get; set; } 
} 

public class Account 
{ 
    public int Id { get; set; } 

    [ForeignKey("BillingContact")] 
    public string BillingContactId { get; set; } 
    public virtual ApplicationUser BillingContact { get; set; } 

    public virtual ICollection<ApplicationUser> Users { get; set; } 

我的问题是,当我创建一个迁移,代码最初只有部分的理解是BillingContact是一个外键。迁移代码使用BillingContactId外键创建帐户表,但它也会创建额外的Account_Id外键字段。

我发现了一个解决方法,但它严肃地不通过“气味”测试。根本问题是我有两个类之间的多个关系,这使得代码优先。特别是,ApplicationUser实体没有导航属性,它是BillingContact外键的“另一端”。

如果我的导航属性添加到ApplicationUser,并与InverseProperty属性,那么代码优先似乎明白了外键,并且不产生额外字段将其标记:

public class ApplicationUser 
{ 
    public string Id { get; set; } 

    public int AccountId { get; set; } 
    public virtual Account Account { get; set; } 

    [InverseProperty("BillingContact")] 
    public virtual ICollection<Account> MyBillingAccounts { get; set; } 
} 

与此问题解决方法是MyBillingAccounts导航属性完全是假的。一个账户有一个相关的ApplicationUser,它是账单联系人,但是反向关系(从ApplicationUser导航回到BillingContactId外键)没有任何实际意义。

因此... 有没有更好(或适当)的方式来教授关于BillingContactId外键的代码优先?

回答

3

你只能用流畅的映射来做到这一点。例如,在你的背景下OnModelCreating的覆盖:

modelBuilder.Entity<Account>() 
      .HasOptional(acc => acc.BillingContact) 
      .WithMany() 
      .HasForeignKey(acc => acc.BillingContactId); 

WithMany()电话表示有没有导航属性关联的反向端。

+0

感谢您的即时答复!实际上,我想我需要'HasRequired()'而不是'HasOptional()',因为我想要FK是必需的(不可为空)。但是这一细节在OP中并不清楚。 –