我对实体框架6有问题。
我正在尝试更新现有实体,但我想完全替换它,而不是一个一个地更新每个单个属性。当我替换属性并调用SaveChanges()
时,它可以很好地保存到数据库中,但是,如果我只想替换整个对象,则它什么都不做。
下面的注释掉的部分显然可以工作,但是当我尝试替换对象(在我的情况下,该对象是ninja.ToModel()
对象,它来自忍者视图模型),它不起作用。
[显然,我缺少了一些东西,我认为它与Attach()
有关,但是到目前为止,我在互联网上找到的所有内容都让我感到困惑。什么是像我想要的那样完全更新对象的正确方法?
public void SaveNinja()
{
using (var context = new ManagerEntities())
{
Ninja nin = context.Ninjas.Find(ninja.ToModel().Id);
// nin.Name = ninja.Name;
// nin.Strength = ninja.Strength;
// nin.Agility = ninja.Agility;
// nin.Intelligence = ninja.Intelligence;
// nin.Gold = ninja.Gold;
context.SaveChanges();
}
Close();
}
仅跟随行查找与您传递的Ninja
匹配的Id
对象。显然,它不会更新找到的对象的属性,因为您没有告诉它这样做。
Ninja nin = context.Ninjas.Find(ninja.ToModel().Id);
如果您不想一一设置对象属性,则可以使用公用方法来设置。
public class Ninja
{
public string Id { get; set; }
public string Name { get; set; }
public void SetNinja(Ninja ninja)
{
Id = ninja.Id;
Name = ninja.Name;
}
}
然后在找到对象时调用它:
Ninja nin = context.Ninjas.Find(ninja.ToModel().Id);
nin.SetNinja(ninja);
因此,如果您加载模型实例,则只需更改值并保存。您不希望数据库识别代表相同模型数据的两个实例。
但是,如果您不打算从数据库中加载任何东西,而要完全自己替换数据库条目,那么您需要做两件事才能使它起作用:
1:确保“主ID”字段(在这里看起来像您将其称为“ Id”)设置为与要替换的对象相同。
2:保存之前,请执行以下操作:
db.Attach(ninja).State = EntityStates.Modified;
该代码段有两件事。首先,它将数据库附加到对象(本质上告诉它“这是您应该使用的该模型的实例”)。然后,第二步,将状态设置为“已修改”,该状态告诉数据库在调用SaveChanges()时需要将其写回磁盘。