Entity framework EF 4.1编码第一个ModelBuilder HasForeignKey用于一对一关系
非常简单,我首先使用Entity Framework 4.1代码,我想用modelBuilder上的fluent调用替换我的[ForeignKey(…)]属性。类似于WithRequired(..)和HasForeignKey(..)的内容,下面将显式外键属性(CreatedBySessionId)与关联的导航属性(CreatedBySession)绑定在一起。但我希望这样做是为了一对一的关系,而不是一对多的关系:Entity framework EF 4.1编码第一个ModelBuilder HasForeignKey用于一对一关系,entity-framework,entity-framework-4.1,ef-code-first,code-first,one-to-one,Entity Framework,Entity Framework 4.1,Ef Code First,Code First,One To One,非常简单,我首先使用Entity Framework 4.1代码,我想用modelBuilder上的fluent调用替换我的[ForeignKey(…)]属性。类似于WithRequired(..)和HasForeignKey(..)的内容,下面将显式外键属性(CreatedBySessionId)与关联的导航属性(CreatedBySession)绑定在一起。但我希望这样做是为了一对一的关系,而不是一对多的关系: modelBuilder.Entity<..>().HasMany(
modelBuilder.Entity<..>().HasMany(..).WithRequired(x => x.CreatedBySession).HasForeignKey(x => x.CreatedBySessionId)
modelBuilder.Entity().HasMany(..).WithRequired(x=>x.CreatedBySession).HasForeignKey(x=>x.CreatedBySessionId)
下面是一个更具体的例子。这与[ForeignKey(…)]属性一起工作非常愉快,但我想去掉它,并在modelbuilder上对其进行配置
public class VendorApplication
{
public int VendorApplicationId { get; set; }
public int CreatedBySessionId { get; set; }
public virtual Session CreatedBySession { get; set; }
}
public class Session
{
public int SessionId { get; set; }
[ForeignKey("CurrentApplication")]
public int? CurrentApplicationId { get; set; }
public virtual VendorApplication CurrentApplication { get; set; }
public virtual ICollection<VendorApplication> Applications { get; set; }
}
public class MyDataContext: DbContext
{
public IDbSet<VendorApplication> Applications { get; set; }
public IDbSet<Session> Sessions { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Session>().HasMany(x => x.Applications).WithRequired(x => x.CreatedBySession).HasForeignKey(x => x.CreatedBySessionId).WillCascadeOnDelete(false);
// Note: We have to turn off Cascade delete on Session <-> VendorApplication relationship so that SQL doesn't complain about cyclic cascading deletes
}
}
公共类供应商应用程序
{
public int VendorApplicationId{get;set;}
public int CreatedBySessionId{get;set;}
公共虚拟会话CreatedBySession{get;set;}
}
公开课
{
public int SessionId{get;set;}
[外键(“当前应用程序”)]
public int?CurrentApplicationId{get;set;}
公共虚拟供应商应用程序CurrentApplication{get;set;}
公共虚拟ICollection应用程序{get;set;}
}
公共类MyDataContext:DbContext
{
公共IDbSet应用程序{get;set;}
公共IDbSet会话{get;set;}
模型创建时受保护的覆盖无效(DbModelBuilder modelBuilder)
{
modelBuilder.Entity().HasMany(x=>x.Applications)。WithRequired(x=>x.CreatedBySession)。HasForeignKey(x=>x.CreatedBySessionId)。WillCascadeOnDelete(false);
//注意:我们必须关闭会话VendorApplication关系上的级联删除,以便SQL不会抱怨循环级联删除
}
}
在这里,一个会话可以负责创建多个供应商应用程序(Session.Applications),但一个会话一次最多只能处理一个供应商应用程序(Session.CurrentApplication)。我希望将CurrentApplicationId属性与modelBuilder中的CurrentApplication navigation属性绑定,而不是通过[ForeignKey(…)]属性绑定
我尝试过的事情
删除[ForeignKey(..)]属性时,CurrentApplication属性会在数据库中生成一个CurrentApplication\u Vendor Application ID列,该列不绑定到CurrentApplication ID列
我已尝试使用如下所示的CurrentApplicationId列名显式映射关系,但显然这会产生错误,因为属性会话已在使用数据库列名“CurrentApplicationId”。CurrentApplicationId:
modelBuilder.Entity<Session>().HasOptional(x => x.CurrentApplication).WithOptionalDependent().Map(config => config.MapKey("CurrentApplicationId"));
modelBuilder.Entity();
我觉得这里缺少了一些非常明显的东西,因为我只想执行与[ForeignKey(…)]相同的操作,但在模型生成器中。或者这是一种不好的做法并且被明确忽略的情况?您需要将关系映射为一对多,并在关系中省略集合属性
modelBuilder.Entity<Session>()
.HasOptional(x => x.CurrentApplication)
.WithMany()
.HasForeignKey(x => x.CurrentApplicationId)
modelBuilder.Entity()
.has可选(x=>x.CurrentApplication)
.有很多
.HasForeignKey(x=>x.CurrentApplicationId)
是的,就是这样!我之前确实使用过该配置,但EF抛出了一个多重性冲突异常,因此我确定关系必须为1:1。当然,现在我意识到多重性冲突实际上发生了,因为我最初将CurrentApplicationId设置为不可为空。。。(掌心)。谢谢你的帮助,非常感谢!