当我尝试关联现有实体时,为什么实体框架会创建一个新实体?

时间:2015-03-14 16:03:28

标签: entity-framework many-to-many

我有多对多关系(用户对技能),当我尝试将现有技能与用户关联时,它总是会创建一个新技能。

用户:

public class ApplicationUser : IdentityUser
{
    public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser> manager)
    {
        // Note the authenticationType must match the one defined in CookieAuthenticationOptions.AuthenticationType
        var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);
        // Add custom user claims here
        return userIdentity;
    }

    public virtual ICollection<Skill> Skills { get; set; }
}

技能:

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

    public string Name { get; set; }
}

OnModelCreating:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        base.OnModelCreating(modelBuilder);

        modelBuilder.Entity<ApplicationUser>()
            .HasMany<Skill>(user => user.Skills)
            .WithMany();
    }

创建关联:

public ActionResult Skills(SkillsViewModel viewModel)
    {
        var user = UserManager.FindById(User.Identity.GetUserId());

        if(!string.IsNullOrWhiteSpace(viewModel.NewSkill)
            && !user.Skills
            .Where(sk => sk.Name == viewModel.NewSkill)
            .Any())
        {
            var foundSkill = this.db.Skills
                .Where(sk => sk.Name == viewModel.NewSkill)
                .FirstOrDefault();

            if(foundSkill != null)
            {
                user.Skills.Add(foundSkill);
            }
            else
            {
                user.Skills.Add(new Skill()
                    {
                        Name = viewModel.NewSkill
                    });
            }
        }

        if(viewModel.SelectedSkillId > 0)
        {
            var foundSkill = this.db.Skills.Find(viewModel.SelectedSkillId);


            user.Skills.Add(foundSkill);
        }

        this.UserManager.Update(user);

        return RedirectToAction("skills");
    }

我已经介入,并确认我确实得到了一个“发现的技能”。从数据库中,但在我将其添加到用户并保存用户之后,与用户关联的技能不是我找到的技能,而是具有相同名称和不同ID的新技能。

1 个答案:

答案 0 :(得分:0)

我明白了。 UserManager正在加载一个DbContext,我试图关联从不同的DbContext加载的技能。

快速入侵测试并修复此问题是从与技能相同的DbContext加载用户,更新用户,保存DbContext。

长期解决方案是确保每个请求都使用相同的DbContext。