Mr.*_* MX 5 entity-framework one-to-one one-to-many code-first relationships
我正在尝试使用 EF Code First 来做到这一点:
有区域两个表:用户和区域。一个用户属于一个所需的区域,一个区域可以有零个或一个用户(作为管理员)。然后:
用户 *..1 区域和用户 0..1 区域
用户类:
public class User {
public int UserId { get; set; }
public string Name { get; set; }
[ForeignKey("Area")]
public int AreaId { get; set; }
[InverseProperty("Users")]
public virtual Area Area { get; set; }
public virtual Area AreaTitular { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
区域类:
public class Area {
public int AreaId { get; set; }
public string Name { get; set; }
public List<User> Users { get; set; }
[ForeignKey("User")]
public int? UserId { get; set; }
[InverseProperty("AreaTitular")]
public virtual User User{ get; set; }
}
Run Code Online (Sandbox Code Playgroud)
以及 update-database 命令上的错误:
无法确定类型“TestEntityFrameworkCodeFirst.Model.Area”和“TestEntityFrameworkCodeFirst.Model.User”之间关联的主体端。必须使用关系流畅 API 或数据注释显式配置此关联的主体端。
任何帮助将不胜感激:)
我不完全确定这是否可以:
protected override void OnModelCreating(DbModelBuilder modelBuilder) {
modelBuilder.Entity<Area>()
.HasOptional(i => i.User)
.WithOptionalDependent();
base.OnModelCreating(modelBuilder);
}
Run Code Online (Sandbox Code Playgroud)
刚刚在 Context 类的 OnModelCreating 上添加了这个。这是它在 SQL Server 中的样子:
问题在于一对一关系的配置,因为一端必须是principal,而另一端必须是dependent。当你配置这种关系时,实体框架要求依赖的主键也是外键。所以,不要映射UsuarioId
为FK,否则,EF要求FK也必须是PK(注释该属性)。另一个问题是 EF 不知道谁是你们关系中的主角。要指定谁是主体,请使用该Required
属性。例如,如果您在 上添加此属性AreaTitular
,则指定要创建User
,则AreaTitular
必须在保存更改后设置该属性,因此在这种情况下您的主体是 ,Area
依赖项是User
,但这是假设的情况,我不知道我不知道你的逻辑。查看此帖子以获取更多信息:
现在,可以将两端指定为可选,但其中之一必须是主要的。如果这是您的情况,我建议您注释数据注释属性并使用 Fluent Api 来配置关系,如下所示:
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<User>()
.HasRequired(a => a.Area)
.WithMany(c => c.Usuarios)
.HasForeignKey(a => a.AreaId);
modelBuilder.Entity<Area>()
.HasOptional(a => a.Usuario)
.WithOptionalPrincipal(u => u.AreaTitular);
}
Run Code Online (Sandbox Code Playgroud)
我建议您阅读此页面以更好地理解一对一关系。
归档时间: |
|
查看次数: |
3703 次 |
最近记录: |