Asp.net mvc 使用Linq2Sql更新数据

Asp.net mvc 使用Linq2Sql更新数据,asp.net-mvc,linq-to-sql,Asp.net Mvc,Linq To Sql,我的mvc ActionResult中有这个 [HttpPost] public ActionResult _ChangeDetails( [Bind(Prefix="ContactDetails")] userDetail UserDetail ) { MemberChangeDetailsFormViewModel fvm = new MemberChangeDetailsFormViewModel(); if (ModelState

我的mvc ActionResult中有这个

    [HttpPost]
    public ActionResult _ChangeDetails( [Bind(Prefix="ContactDetails")] userDetail UserDetail )
    {
        MemberChangeDetailsFormViewModel fvm = new MemberChangeDetailsFormViewModel();

        if (ModelState.IsValid)
        {
            //save
            UserDetailRepository repository = new UserDetailRepository();
            repository.Save(UserDetail);
            return RedirectToAction("Index", "Member");
        }

        fvm.ContactDetails = UserDetail;

        return View(fvm);
    }
然后在我的存储库中我有

if (userDetail.id != Guid.Empty)
{
    userDetail orig = dc.userDetails.Where(x => x.id == userDetail.id).Single();
    dc.userDetails.Attach(userDetail, orig);
    dc.Refresh(System.Data.Linq.RefreshMode.KeepCurrentValues, userDetail);
    dc.SubmitChanges();
}
然而,“附加”正在生成错误无法添加密钥已在使用的实体。

据我所知,这是因为L2S已经连接了物体。我尝试过在使用和不使用orig对象的情况下执行此操作,但得到了相同的消息


从模型中更新表中数据的最佳实践是什么?

Linq to SQL无法处理同一数据上下文中具有相同键的两个对象。一些选择:

选项1:使用两种不同的数据上下文:

public void Update(UserDetail modifiedUser)
{
    using (UserDetailDataContext dc1 = new UserDetailDataContext())
    using (UserDetailDataContext dc2 = new UserDetailDataContext())
    {
        UserDetail originalUser = dc1.UserDetails.Single(u => u.id == modifiedUser.id);
        dc2.UserDetails.Attach(modifiedUser, originalUser);
        dc2.SubmitChanges();
    }
}
选项2:不要拉原始对象;将新对象注释为更新:

public void Update(UserDetail modifiedUser)
{
    using (UserDetailDataContext dc = new UserDetailDataContext())
    {
        dc.UserDetails.Attach(modifiedUser);
        dc.Refresh(RefreshMode.KeepCurrentValues, modifiedUser);
        dc.SubmitChanges();
    }
}

中有更多的讨论,Rick Strahl有一个基于版本控制的策略,如果您愿意修改表模式以添加时间戳。

错误发生在“附加”处,因此选项2不起作用,我不确定是否需要第二个上下文。我应该使用originalUser,更新字段,然后提交更改吗?与meGriegs相比似乎有点落后,您在问题中输入的代码失败了,因为它试图将两个具有相同键的对象加载到上下文中:orig(使用Where/Single查询)和userDetails(使用Attach。)选项2工作,因为它只加载一个这样的对象:userDetails with Attach。如果你还没有真正尝试过,你可能想尝试一下。我已经用一个物体尝试过了,我得到了同样的结果。我尝试了使用和不使用orig对象。@OrenTrutner,我确认只有选项1有效。第二个选项抛出相同的“无法添加具有已在使用的密钥的实体”。