MVC ModelState验证复杂属性列表

时间:2016-01-06 11:48:40

标签: c# asp.net-mvc validation modelstate complextype

所以,我有一个User模型类。它有UnitViewModel列表。

public class UserViewModel
{
    [Required(ErrorMessage="FirstName")]
    public string FirstName { get; set; }

    [Required(ErrorMessage = "LastName")]
    public string LastName { get; set; }

    public List<UnitViewModel> DesiredUnits { get; set; }
}

public class UnitViewModel
{
    public Guid? UnitID { get; set; }
    [Required(ErrorMessage = "NAMEEE")]
    public string Name { get; set; }

    public bool Selected { get; set; }
}

当我尝试创建新的User时,我会从我的视图中发布UserViewModel。在这里,我得到ModelState.IsValid false。发生这种情况是因为验证还会检查UnitViewModel.Name属性为空(这是正常的,因为我创建了User并且checkbox列有UnitViewModel。用户选择{{1来自现有的UnitViewModel列表)。

我可以通过foreach循环以UnitViewModel的可怕方式修复它,但我不会。

那么,解决方案是什么?如何禁用模型复杂属性列表的验证?

更新
我目前使用的另一个解决方案是在ModelState["DesiredUnits[0].UnitID"].Errors.Clear()的编辑器模板中使用HiddenFor(m=>m.Name),但这种方法的缺点是当我在editortemplate中已经有标签时,UnitViewModel是不必要的。此外,如果我有任何必需的字段,我将不得不为每个字段都有相应的隐藏输入。

2 个答案:

答案 0 :(得分:0)

如果您的请求视图模型包含指定视图不需要的属性或验证规则,则应为此创建一个新对象。

// New model, specific for request
public class UserRequestViewModel
{
    [Required(ErrorMessage="FirstName")]
    public string FirstName { get; set; }

    [Required(ErrorMessage = "LastName")]
    public string LastName { get; set; }
}

public ActionResult Index(UserRequestViewModel requestModel)
{
    //... do something

    // Get the values required to return to the view
    var responseModel = new UserViewModel();
    responseModel.DesiredUnits = new List<UnitViewModel>();

    // Return the response model
    return View(responseModel);
}

如果你这样做,任何为你的应用程序开发的人都清楚,你可以接受哪些行动。

或者,如果您决定不为此目的创建整个新模型,请将验证移至控制器操作中:

public ActionResult Index(UserViewModel requestResponseModel)
{
    // Perform validation
    for (var i = 0; i < requestResponseModel.DesiredUnits.Count(); i++)
    {
        var validationErrorKey = string.Format("DesiredUnits[{0}]", i);

        // Is the Name property empty?
        if (string.IsNullOrWhiteSpace(requestResponseModel.DesiredUnits[i].Name))
        {


            this.ModelState.AddModelError("Posted Name cannot be empty", validationErrorKey );
        }
    }

    if (this.ModelState.IsValid)
    {
        // There was a model validation error
    }

    //... do something

    // Return the response model
    return View(requestResponseModel);
}

作为最后的手段,您可以使用,但我不确定这是否会妨碍对该字段的验证 - 您需要放弃一下:

public ActionResult Index([Bind(Exclude = "DesiredUnits")]UserViewModel requestResponseModel)
{
    // ... do something
}

答案 1 :(得分:0)

使用

   [HttpPost]       
    public ActionResult CreateEnquiryOnly([Bind(Include="FirstName,LastName")]UserViewModel userviewmodel)
    {
        if(ModelState.IsValid)
        {       
        }
    }