2012-01-09 130 views
0

我有一个详细信息页面,可以让我编辑与特定项目相关的信息。ASP.NET MVC ViewModel更新

public ActionResult Details(int id) 
    { 
     Call call = db.Calls.Find(id); 
     return View(new CallFormViewModel(call)); 
    } 

我用一个视图模型 -

public class CallFormViewModel 
{ 
    public Call  Call { get; private set; } 

    public CallFormViewModel() 
    { 
     Call = new Call(); 
    } 

    public CallFormViewModel(Call call) 
    { 
     Call = call; 
    } 
} 

当我提出,我想只允许“调用”对象的某些属性进行更新。我的帖子处理方法是这样的 -

[HttpPost] 
    public ActionResult Details(CallFormViewModel callForm) 
    { 

     (some code removed for clarity) 

     UpdateModel(callForm.Call ,new string[] { 
      "Contact", 
      "Summary", 
      "Description", 
     } 

    } 

的问题是,callForm已经与所有从表单输入的更新提交之前,我甚至打电话的UpdateModel。

我该如何改变它并使用UpdateModel来选择性地更新字段?

感谢

编辑:

我觉得我一直在寻找这个错误的方式。我应该做的是:

[HttpPost] 
    public ActionResult Details(int id, CallFormViewModel callForm) 
    { 

     var call = db.Calls.Find(id); 

     (some code removed for clarity) 

     UpdateModel(call, "Call", new string[] { 
      "Contact", 
      "Summary", 
      "Description", 
     } 

    } 

这样,它采取了不完整的数据[只有田野,我想]并将其应用到实际的模型。我一直在混淆callForm.Call和实际的模型对象,事实上它只是它的一个表示。

必须等到我开始测试这个理论。

+0

您最好使用'AutoMapper'从实体切换到ViewModel。 ViewModel应该是您使用和操作的唯一“数据”,直到您想保存\编辑,然后切换到您保存的真实实体。 AutoMapper帮助将ViewModel从实体中分离出来。希望这个技巧能够在不久的将来帮助你很多。 – gdoron 2012-01-09 08:37:22

回答

2

当您在Action参数中编写ViewModel时,Model Binder将ViewModel属性绑定到“传入”数据。这应该工作:

[HttpPost] 
public ActionResult Details() 
{ 
    CallFormViewModel callForm = new CallFormViewModel(); 

    UpdateModel(callForm.Call ,new string[] { 
     "Contact", 
     "Summary", 
     "Description", 
    } 
} 

更新:

绑定属性选项:

[Bind(Include = "Contact,Summary,Description")] 
public class CallFormViewModel 
{ 
    // As before... 
} 
+0

callForm是如何构建的? – NoPyGod 2012-01-09 03:12:07

+0

@NoPyGod,我不确定它必须在之前构建,但你可以“新”它。我更新了。 – gdoron 2012-01-09 03:14:27

+0

如果在CallFormViewModel本身也有相关的属性,我应该这样做UpdateModel(callForm,new string [] {“something”,“somethingelse”,“call.contact”,“call.summary”})?当我开始做这样的事情时,它看起来像是一些非常可恶的代码。 – NoPyGod 2012-01-09 03:22:04

0

你并不需要调用的UpdateModel因为你会得到通过更新模型作为你方法的参数。如果您更喜欢使用UpdateModel,则应从操作方法中删除参数。

要那么只更新领域你有兴趣,你应该:

  1. 有方法采取只包括应该更新领域的不同视图模型。
  2. 更改窗体,以便只有要更新的字段位于由HTML.TextBoxFor()方法创建的文本框(或其他可更新控件)中。
+0

你写的第二个选项是危险的。可能有恶意用户发送他的数据,如 - 折扣= 100%或?经理=真。第一个选项**(IMO)**太复杂了,有一个实体有两个视图模型,只需使用Bind属性即可。 – gdoron 2012-01-09 03:40:16