编辑MVC模型中的对象关系

时间:2016-06-13 21:59:53

标签: c# asp.net-mvc entity-framework entity-framework-6 asp.net-mvc-5.2

我在MVC 5.2.3,Entity Framework 6中遇到了相关对象的问题。我无法更新模型中另一个对象的关系。有一个AudiogramModel,其属性InstrumentModel和从BaseModel继承的int ID。

public class AudiogramModel : BaseModel
{
    //Other properties...

    public InstrumentModel Instrument { get; set; }
}

仪器模型定义如下:

public class InstrumentModel : BaseModel
{
    public string Name { get; set; }
}

就像Audiogram一样从BaseModel继承了一个密钥ID。

在控制器AudiogramController中,方法Edit应该在视图模型AudiogramCreateEditViewModel中接收带有InstrumentModel的整个AudiogramModel,然后用InstrumentModel保存已编辑的AudiogramModel。

视图模型定义为:

public class AudiogramCreateEditViewModel
{
    public AudiogramModel Audiogram { get; set; }
    public int[] Frequencies { get; set; }
    public List<InstrumentModel> Instruments { get; set; }
}

虽然频率和列表并不重要(因为它们用于将这些模型传递到编辑视图),但其中包含了Audiogram属性,这让我感兴趣。

    public ActionResult Edit(AudiogramCreateEditViewModel audiogramEdit)
    {
        if (ModelState.IsValid)
        {
            if (audiogramEdit.Audiogram.IsMusician == true)
            {
                //db is the standard context of the controller
                InstrumentModel instrument = db.InstrumentModels.FirstOrDefault<InstrumentModel>(x => x.Name == audiogramEdit.Audiogram.Instrument.Name);
                if (instrument == null)
                {
                    db.InstrumentModels.Add(audiogramEdit.Audiogram.Instrument);
                    db.SaveChanges();
                }
                else
                {
                    audiogramEdit.Audiogram.Instrument = instrument;
                }
            }
            else
            {
                audiogramEdit.Audiogram.Instrument = null;
            }
            db.AudiogramModels.Attach(audiogramEdit.Audiogram);
            db.Entry(audiogramEdit.Audiogram).State = EntityState.Modified;
            var a = db.ChangeTracker.Entries();
            db.SaveChanges();

            return RedirectToAction("Index"); 
  }

}

模型通过验证,似乎没问题。问题是,虽然听力图模型是正确的,可以用db.AudiogramModels.Add(audiogramEdit.Audiogram)保存;没有办法更新它。更有甚者,没有行db.AudiogramModels.Attach(audiogramEdit.Audiogram);实体跟踪器甚至不跟踪audiogramEdit.Audiogram。有没有办法解决这个问题?

1 个答案:

答案 0 :(得分:0)

这是你不能完全“修复”的东西。请记住代码实际上在做什么。在您的Get操作中,您正在查找AudiogramCreateEditViewModel,将其序列化(及其所有属性),然后将其发送到客户端以在其网页上呈现。客户端重新序列化它并将其发送回Edit方法。服务器对其进行反序列化,并为您提供 new 一个AudiogramCreateEditViewModel实例。

EntityFramework无法知道MVC为您创建的这个新实例。如果要进行更新,则必须告知相关内容。最简单的方法是再次从上下文中获取对象,并从ViewModel中复制属性。

您可能还会注意到,如果您手动复制属性,则根本不需要在ViewModel上安装AudiogramModel实例。您可以创建一个更简单的类,其中仅包含您希望编辑视图的属性以及可用于查找域模型的ID。从长远来看,这会简化您的UI层。