asp.net-mvc - ModelState 验证不适用于 DropDownList 和嵌套对象

标签 asp.net-mvc asp.net-mvc-4 data-annotations

在我们的应用程序中,我们有一个域层,其中包含带有用于验证的 DataAnnotations 的类。

我们在 ASP.NET MVC ui 层的模型中使用这些类。

例如:

领域层:

public class Company
{
    public int Id { get; set; }

    [Required]
    [StringLength(50)]
    public string Description { get; set; }

    // ... some model logic abreviated
}

public class Supplier 
{
    public int Id { get; set; }

    [Required]
    public string Name { get; set; }

    [Required]
    public Company Company { get; set; }

    // ... some model logic abreviated
}

在我们的 ASP.NET MVC 表示层中:
public class SupplierEditModel
{
    public Supplier Supplier { get; set; }
    public IEnumerable<Company> Company { get; set; }
    public int SelectedCompany { get; set; }

    // ... some model logic abreviated
}

在这种情况下,我们有一个包含公司 DropDownList 的页面。该列表具有约束力,如下所示:
@Html.DropDownListFor(m => m.SelectedCompany, new SelectList(Model.Companies, "Id", "Description", Model.SelectedCompany))

我们的问题出在 Controller 的 POST 方法上,当我们检查 ModelState.IsValid 时,模型无效,因为 Supplier.Company 为空。然后我们可以使用 SelectedCompany 获取公司,但我们的问题是这意味着我们不能做这样的事情:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(SupplierEditModel model)
{
    if (ModelState.IsValid)
    {
        model.CreateSupplier(_supplierService);
        return RedirectToAction("Index");
    }

    return RedirectToAction("Create");
}

我们想在创建供应商之前使用验证。

最佳答案

我看到您(至少)有两个选择:

您可以展平您的 View 模型并省略 Supplier.Company如果您认为不需要它。

public class SupplierEditModel
{
    public int SupplierId { get; set; }
    public string Name { get; set; }
    public Company Company { get; set; }
    public IEnumerable<Company> Company { get; set; }
    public int SelectedCompany { get; set; }

    // ... some model logic abreviated
}

(注意:您的数据注释应该在 View 模型上,而不是域模型上。)

或者

您可以清除 ModelState检查之前的错误IsValid属性(property)
ModelState.Remove(string key, ModelState);

这里的最佳实践可能是使用扁平模型,原因有两个。一,通常只发送 View 需要的内容而不是其他内容是一种很好的做法。如果 View 没有对 Supplier.Company 做任何事情,那么它就不应该是模型的一部分。第二,使用 ModelState.Remove 方法虽然有效,但在某些人看来可能有点笨拙。您可能会在代码审查中遇到一些麻烦;)

关于asp.net-mvc - ModelState 验证不适用于 DropDownList 和嵌套对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15026888/

相关文章:

asp.net - 在同一请求中调用PasswordSignIn和SendTwoFactorCode

c# - RequiredIf 没有触发客户端验证

data-annotations - ASP.net core MVC 6 数据注释关注点分离

c# - RedirectingResponse.AsActionResult() 不再存在,对于 DotNetOpenAuth,我可以用什么替换它?

asp.net - css文件大小有限制吗?

C# 保存对象列表与保存对象(来自 JSON)

asp.net - 将错误从 HttpModule 传递到 MVC 应用程序

asp.net-mvc - 我应该在这里使用 View 模型吗?

asp.net-mvc-3 - 如何使用新的 HttpSessionStateWrapper 和 HttpSessionStateBase?

jQuery 不显眼的验证忽略 MVC3 中的 data-val-required 消息