MVC和嵌套Viewmodels的困难

时间:2015-02-16 14:23:28

标签: c# vb.net asp.net-mvc-4

我对MVC很新,所以请记住这一点

我创建了一个viewmodel vmRecurringPack,其中包含另一个模型Entity以及其属性中的其他字段。在我传递vmRecurringPack的视图中,我仅使用某些Entity属性进行显示(我的视图不需要其余字段)

我的问题在于,当我发回我的观点时,其余的字段当然没有被绑定到视图,并且已经失去了它们的价值。这部分在我的情况下很好,但ModelState.IsValid不再有效,因为其中一些字段是必需的。

如何在不删除ModelState.IsValid的情况下解决此问题?

(VB.net回答较好,C#欢迎)

编辑:我已经考虑了我的视图模型的重组,这将有效,但我很好奇其他解决方案是什么

编辑:根据要求,代码。虽然我不知道这个特定问题的要求是什么......关于我的问题,我想显示vmRecurringPack.Entity.CodevmRecurringPack.Entity.Name的字段,但在我的表格中POST {{ 1}}返回false,因为ModelState.IsValid中标记为必需的字段为

vmRecurringPack

Entity

实体

Namespace ViewModels
Public Class vmRecurringPack

    Property Entity As Entity
    Property Name As String
    Property Description As String
    Property Status As String

End Class
End Namespace

3 个答案:

答案 0 :(得分:1)

使用视图模型的指导正是为了避免您遇到的问题。您已经在这里使用了视图模型,但您只是将实体类作为属性附加到其上。如果您不需要实体上的所有内容,那么也要为其创建视图模型。通常,将任何实体类发送到您的视图是一个坏主意(即使它是通过另一个类的属性)。在100个中有99次,你会发现自己回到这里并且需要用视图模型将其切换出来。无论如何。

答案 1 :(得分:0)

视图模型是一种对发送到视图的数据建模的方法,因此如果从浏览器发送到服务器的数据不同,那么常见的方法是创建新的输入模型类型。

public ActionResult Edit()
{
    return View(new RecurringPackViewModel(...));
}

[HttpPost]
public ActionResult Create(RecurringPackInputModel model)
{
    if (ModelState.IsValid)
    { 
       ... 
    }
}

这样,您的视图模型和输入模型都可以有不同的要求。

答案 2 :(得分:0)

重构视图模型是处理此问题的正确方法。重用视图模型是一件好事,以防它们完全适合您的场景,但您不应仅修改验证逻辑/更改应用程序逻辑,以便重用相同的视图。如果您使用几个Entity属性进行显示,而不是仅将这些属性添加到vmRecurringPack对象,而不对它们应用任何验证规则。

在您的情况下,如果您坚持使用原始视图模型,则可能必须实现自定义验证逻辑。例如,FluentValidation等库允许您定义复杂的验证规则。