Entity framework 如何使用Fluent API正确映射实体?
我有两个实体,一个用户和一个用户配置文件。用户的主键是UserId,UserProfile的主键是UserProfileId。每次在我的应用程序中创建新用户时,我都会创建一个新的用户配置文件,其PK与用户中的PK相同。然后,当我尝试更新UserProfile上的属性时,我最终得到了多重性错误或模式无效错误。以下是我的两个实体:Entity framework 如何使用Fluent API正确映射实体?,entity-framework,foreign-keys,code-first,fluent,Entity Framework,Foreign Keys,Code First,Fluent,我有两个实体,一个用户和一个用户配置文件。用户的主键是UserId,UserProfile的主键是UserProfileId。每次在我的应用程序中创建新用户时,我都会创建一个新的用户配置文件,其PK与用户中的PK相同。然后,当我尝试更新UserProfile上的属性时,我最终得到了多重性错误或模式无效错误。以下是我的两个实体: public class User { public Guid UserId { get; set; } public string UserName {
public class User
{
public Guid UserId { get; set; }
public string UserName { get; set; }
public string Email { get; set; }
public string Password { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public int? PhoneExtension { get; set; }
public string Comment { get; set; }
public Boolean IsApproved { get; set; }
public int PasswordFailuresSinceLastSuccess { get; set; }
public DateTime? LastPasswordFailureDate { get; set; }
public DateTime? LastActivityDate { get; set; }
public DateTime? LastLockoutDate { get; set; }
public DateTime? LastLoginDate { get; set; }
public string ConfirmationToken { get; set; }
public DateTime? CreateDate { get; set; }
public Boolean IsLockedOut { get; set; }
public DateTime? LastPasswordChangedDate { get; set; }
public string PasswordVerificationToken { get; set; }
public DateTime? PasswordVerificationTokenExpirationDate { get; set; }
public virtual ICollection<Role> Roles { get; set; }
public virtual UserProfile UserProfile { get; set; }
}
public class UserProfile
{
public Guid UserProfileId { get; set; }
public virtual User ProfileOwner { get; set; }
public Int64? HomePhone { get; set; }
public Int64? MobilePhone { get; set; }
public virtual User Manager { get; set; }
}
this.SetEntityState行引发以下错误:
违反了多重性约束。关系“WhelenPortal.Data.Context.UserProfile\u ProfileOwner”的角色“UserProfile\u ProfileOwner\u Source”的多重性为1或0..1
我已经试着让它工作了两天了,请帮忙!!!提前谢谢
根据要求,这里有一些补充信息。我在这里使用的是存储库模式和工作单元。下面是我的GetUserProfileById代码。该服务使用存储库,因此我将两者都显示出来
public UserProfile GetUserProfileByID(Guid id)
{
if (id == null)
throw new BusinessServicesException(Resources.UnableToRetrieveUserProfileExceptionMessage, new ArgumentNullException("id"));
try
{
Model.UserProfile userProfile = _userProfileRepository.GetUserProfileByID(id);
if (userProfile != null)
return ToServicesUserProfile(userProfile);
return null;
}
catch (InvalidOperationException ex)
{
throw new BusinessServicesException(Resources.UnableToRetrieveUserProfileExceptionMessage, ex);
}
}
…和存储库:
public UserProfile GetUserProfileByID(Guid id)
{
return this.GetDbSet<UserProfile>().Find(id);
}
公共用户配置文件GetUserProfileByID(Guid id)
{
返回这个.GetDbSet().Find(id);
}
因此,经过多次尝试,这对我来说终于奏效了,希望它能以某种方式帮助其他人。我的用户类保持不变,但我的UserProfile类更改为:
public class UserProfile
{
public Guid UserProfileId { get; set; }
public virtual User ProfileOwner { get; set; }
public Guid? ManagerId { get; set; }
public virtual User Manager { get; set; }
public Int64? HomePhone { get; set; }
public Int64? MobilePhone { get; set; }
}
这是fluent映射:
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Entity<User>()
.HasOptional(u => u.UserProfile)
.WithRequired(u => u.ProfileOwner);
modelBuilder.Entity<UserProfile>()
.HasOptional(u => u.Manager)
.WithMany()
.HasForeignKey(u => u.ManagerId);
}
模型创建时受保护的覆盖无效(DbModelBuilder modelBuilder)
{
基于模型创建(modelBuilder);
modelBuilder.Entity()
.has可选(u=>u.UserProfile)
.带必填项(u=>u.ProfileOwner);
modelBuilder.Entity()
.has可选(u=>u.Manager)
.有很多
.HasForeignKey(u=>u.ManagerId);
}
能否显示GetUserProfileByID
和SetEntityState
?所有涉及的方法都使用相同的上下文实例吗?如果是,为什么要将状态设置为Modified
?更改跟踪会将更改的属性标记为自动修改。我已更新问题,以包含您请求的信息。嗯ToServicesUserProfile(userProfile)
,那里发生了什么?这是一个n层项目,所以我有一个业务层、数据层和web层。ToServicesUserProfile(userProfile)本质上将模型对象映射到业务层的模型对象。整个项目与丝绸项目的结构密切相关。您可以在这里的MSDN上看到:或者在这里的codeplex上看到:在我看来,乍一看,您的映射看起来是正确的。魔鬼可能在某些细节上。问题是EF细节(对于回答您的问题很重要)隐藏在您的体系结构和许多方法调用之下。您是否可以尝试从所有这些方法中提取相关代码,以便清楚地看到何时使用上下文、哪些查询以及其他DbContext和DbSet方法?
public class UserProfile
{
public Guid UserProfileId { get; set; }
public virtual User ProfileOwner { get; set; }
public Guid? ManagerId { get; set; }
public virtual User Manager { get; set; }
public Int64? HomePhone { get; set; }
public Int64? MobilePhone { get; set; }
}
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Entity<User>()
.HasOptional(u => u.UserProfile)
.WithRequired(u => u.ProfileOwner);
modelBuilder.Entity<UserProfile>()
.HasOptional(u => u.Manager)
.WithMany()
.HasForeignKey(u => u.ManagerId);
}