【问题标题】:Entity Framework 6 code first fluent api config for one to one entity relationshipEntity Framework 6 code first fluent api config用于一对一的实体关系
【发布时间】:2015-05-11 05:44:56
【问题描述】:

我目前有 2 个实体之间的一对一关系。主要实体如下所示:

public class PrimaryEntity
{
   // primary key
   public Guid Id { get; set; }
   // some other properties...
   public RelatedEntity Related { get; set; }
}

我的相关实体如下所示:

public class RelatedEntity
{
   // both the primary and foreign key
   public Guid PrimaryEntityId { get; set; }

   // some other properties
}

所以我的问题是,如何使用 EF 6 fluent api 定义这种一对一的关系(不能使用注释)?我为此尝试了许多不同的配置设置变体,但都没有运气。甚至可以定义这样的单边关系,并且键名不同吗?我的 RelatedEntity 是否对主键和外键使用相同的属性?

感谢任何帮助。

更新:

我能够解决问题。罪魁祸首是在 PrimaryEntity 的构造函数中,我设置了 Related = new RelatedEntity。我猜EF不喜欢这样。我发现提供的所有 3 个答案在其他方面几乎相同。感谢大家的帮助。

【问题讨论】:

    标签: c# .net entity-framework-6


    【解决方案1】:

    是的,您可以配置与 EF fluent api 的一对一关系。

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        // Configure StudentId as PK for StudentAddress
        modelBuilder.Entity<StudentAddress>()
            .HasKey(e => e.StudentId);
    
        // Configure StudentId as FK for StudentAddress
        modelBuilder.Entity<Student>()
                    .HasOptional(s => s.StudentAddress) // Mark StudentAddress is optional for Student
                    .WithRequired(ad => ad.Student); // Create inverse relationship
    
    }
    

    取自http://www.entityframeworktutorial.net/code-first/configure-one-to-one-relationship-in-code-first.aspx

    【讨论】:

    • 我实际上试过这个,但遇到了问题。如果我使用 .Include("RelatedEntity") 运行查询,那么它似乎可以工作,但 RelatedEntity 对象的属性都设置为 null。如果我使用 .Include() 语句,我会得到多重错误。
    【解决方案2】:

    RelatedEntity 类中你还需要定义一个导航属性,它指向PrimaryEntity 类:

    public class RelatedEntity
    {
       // both the primary and foreign key
       public Guid PrimaryEntityId { get; set; }
    
       public PrimaryEntity Primary { get; set; }
       // some other properties
    }
    

    然后您可以使用它在您的自定义DbContext 类的OnModelCreating 方法中配置您的一对一关系:

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        base.OnModelCreating(modelBuilder);
    
        modelBuilder.Entity<RelatedEntity>().HasKey(e => e.PrimaryEntityId);    
        modelBuilder.Entity<RelatedEntity>().HasRequired(re => re.Primary).WithOptional(pe => pe.Related);
    }
    

    请注意,这里 RelatedEntityPrimaryEntityId 属性被显式配置为主键,因为在您的情况下它的名称超出了默认的主键命名约定。

    这是一个生成的代码优先迁移,它表明你得到了你需要的东西:

    CreateTable(
        "dbo.PrimaryEntities",
        c => new
            {
                Id = c.Guid(nullable: false),
            })
        .PrimaryKey(t => t.Id);
    
    CreateTable(
        "dbo.RelatedEntities",
        c => new
            {
                PrimaryEntityId = c.Guid(nullable: false),
            })
        .PrimaryKey(t => t.PrimaryEntityId)
        .ForeignKey("dbo.PrimaryEntities", t => t.PrimaryEntityId)
        .Index(t => t.PrimaryEntityId);
    

    【讨论】:

    • 得到了与 Gosia 的答案相同的结果:“如果我使用 .Include("RelatedEntity") 运行查询,那么它似乎可以工作,但是 RelatedEntity 对象的属性都设置为 null。如果我使用 .Include() 语句时出现多重错误。”
    • @Digitalfront 您是否尝试过使用.Include("Related") 而不是.Include("RelatedEntity")?据我所知,应该使用导航属性的名称而不是相关实体的名称。
    • 是的,这实际上是一个错字。我使用了导航属性名称。
    • @Digitalfront 请提供有关您遇到的错误以及您如何使用.Include() 语句的更多详细信息,这会导致多重错误。
    • Error with .include("Related")...“在 EntityFramework.dll 中发生了“System.InvalidOperationException”类型的异常,但未在用户代码中处理附加信息:违反了多重性约束。关系“RelatedEntity_Primary”的角色“RelatedEntity_Primary_Source”的多重性为 1 或 0..1。”
    【解决方案3】:
    public class PrimaryEntity
    {
        // primary key
        public Guid Id { get; set; }
        // some other properties...
        public RelatedEntity Related { get; set; }
    }
    public class RelatedEntity
    {
        // both the primary and foreign key
        public Guid PrimaryEntityId { get; set; }
    
        // some other properties
     }
    
     //mapping
     //configure the primary key as mentioned above
     modelBuilder.Entity<RelatedEntity>() 
          .HasKey(t => t.PrimaryEntityId );
    
     modelBuilder.Entity<PrimaryEntity>()
          .HasRequired(p => p.Related )
          .WithRequiredPrincipal(); //empty parenthesis for one sided navigation.
    

    未经测试 - 我的头顶...

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-06-08
      • 1970-01-01
      • 2012-01-20
      • 1970-01-01
      • 2016-06-01
      • 1970-01-01
      • 2013-01-26
      • 2014-05-02
      相关资源
      最近更新 更多