经过多年的ASP.NET表单开发后,我[终于!]处理了MVC(版本3)。我在n层应用程序架构方面有很强的背景,我正在尝试正确地处理这个新项目,明确区分关注点等。
我所做的是通过创建我的POCO以代码优先开始。由此,框架创建了我的数据库。
然后,我通过将所有我的EF查询和CRUD方法放在我的Models程序集中的每个POCO类的Repository类中来实现Repository模式。这样,我的控制器不需要知道如何通过EF访问我的数据。大。
最后,我在Models程序集中创建了一些ViewModel类。我的意图是,对于某些操作(例如创建和编辑),我从RAZOR视图中引用我的ViewModel类,而不是我的POCO类。这样,我可以使用我的POCO类和SelectList来填充ViewModel中的Dropdown。两者都通过引用相关的Repository类来填充,这些类是从我的Controller Actions中调用的。我想我现在正在滚动:
class MyObject
{
public int ID {get;set}
[Required]
[StringLength(512)]
public string Name {get;set;}
}
class MyViewModel // ViewModel for a specific view
{
public MyObject MyModel {get;set;} // the model that is being edited
// other data the view might need, set by the controller
public string SomeMessage { get; set; }
public List<SomeObject> SomeObjects {get;set;} /// e.g. for a drop-down list
// My constructor below that populates the "SomeObjects" list, and accepts the
// "MyObject" class as a parameter in order to set the "MyModel" property above...
// ..........
}
问题......
在我开始使用Controller Create和Edit操作中的ViewModel类之前,我直接传入了POCO类。当我在视图中点击编辑表单中的保存按钮时,一切正常:
旧代码:
[HttpPost]
public ActionResult Edit(MyObject mine)
{
if (ModelState.IsValid)
{
myRepository.Update(mine);
myRepository.SaveChanges();
return RedirectToAction("Index");
}
return View(mine);
}
当我点击保存时,我的POCO类(MyObject)将被返回,自动填充表单中的值,它将成功保存,生命就是桃子。
当我切换到传递我的ViewModel(MyViewModel)时,一切都崩溃了。
我可以通过在编辑视图顶部设置@model引用来引用我的ViewModel(MyViewModel)。然后我能够从我的POCO类(MyObject)填充我的表单字段,该类是ViewModel的一部分。我甚至能够从ViewModel中的SomeObjects集合填充DropDownList,并从我正在编辑的MyObject类中预选正确的DropDownList。一切似乎都很好 UNTIL ......
当我点击保存按钮并调用Controller的Edit ActionResult(POST动作)时,传递给ActionResult的MyObject类(公共ActionResult Edit(MyObject mine))为null。
然后,我尝试将传入的对象更改为我的ViewModel(公共ActionResult编辑(MyViewModel myVM)),其中引用的MyObject类(MyModel)为null。
我缺少什么?
我知道它必须是非常简单的东西,它正盯着我,我无法看到它!
答案 0 :(得分:2)
查看FormCollection,键的名称应与要填充的类的属性相匹配。这就是MVC的默认模型绑定的工作原理。
答案 1 :(得分:1)
维姆,
非常感谢你的帮助。我确实有s参数构造函数,我刚从示例中省略了它。
我实际上已经找到了问题。平心而论,我输入的代码不是真正的代码,因为当我发布这个时,我没有把它放在我面前。问题是我的ViewModel中的实体模型类引用实际上将其set访问器设置为私有:
public MyObject MyModel {get;private set;}
这阻止了模型绑定器在控制器的保存方法期间回发时填充该属性。
我现在要做的就是将我的验证逻辑从我的EF POCO移到我的ViewModel,这似乎是这种模式中推荐的操作。
感谢您的时间,我希望这可以帮助那些对此框架不熟悉的类似问题的人。