条件服务器端验证MVC 5

时间:2014-12-19 14:15:09

标签: c# validation asp.net-mvc-5

至少,这至少是一个探索性的问题,看看有什么不可能,看看我想要实现的是什么。

目前我正在使用jQuery Unobtrusive验证和MVC标准服务器端验证,以便在通过Web表单提交数据之前进行验证。现在,我希望表单更加“动态”,这取决于下拉/单选按钮/复选框等的选择。表单的某些部分将显示或隐藏自己,但这对我来说是2个问题:

  1. jQuery Unobtrusive仍然会尝试验证所有表单字段,即使它们被隐藏或显示设置为无。我想我可以使用一些jQuery,每个元素上的自定义类标记来解决这个问题,然后在更新UI时,循环遍历元素并删除/添加data-val。这不是主要问题

    1. 这是最重要的一个。因为我将使用数据注释装饰模型,当数据到达服务器时,如果它的部分是空的,那么显然if(ModelState.IsValid())检查将失败,但我需要在那里触发注释以触发客户端验证
  2. 我想知道,有没有办法可以覆盖现有的MVC服务器端验证逻辑,这样如果选择了某个复选框或下拉值,那么就会绕过一些逻辑。在我想要根据连接方IP地址限制访问之前,我已经编写了一个非常基本的自定义验证属性。

    我知道我可以使用多个ViewModel,但是当用户第一次访问该网站时,表单将不知道他们将选择适当的选项之前将提交的提交类型,此时通用提交对象将在HTTP GET控制器方法上传递给View,理想情况下,我希望在提交简单加载辅助ViewModel后避免重新加载页面。我也在使用文件上传器和文件信息等等都存储在ViewModel中,所以这也需要传递,我可以看到它变得混乱。

    public class Submission
    {
        [HiddenInput(DisplayValue = false)]
        public Guid SubmissionID { get; set; }
    
        [Required(ErrorMessage = "Please provide your name")]
        public string Name { get; set; }
    
        [EmailAddress(ErrorMessage = "Invalid email address")]
        [Required(ErrorMessage = "Please enter an email address")]
        public string Email { get; set; }
    
        [Required(ErrorMessage = "Please provide a contact number")]
        [StringLength(13, ErrorMessage = "Phone number can be no more than 13 digits long")]
        public string Phone { get; set; }
    
        public string SubmissionPurpose { get; set; }
    
        //Suspicious Transaction
        //This should only be validated if, on the POST, the SubmissionPurpose matches the appropriate value
        [Required(ErrorMessage = "Please provide a date")]
        public string TransDateNoticed { get; set; }
    
        public string TransAdditionalDetails { get; set; }
    
        //Support Query
        //This should only be validated if, on the POST, the SubmissionPurpose matches the appropriate value
        [Required(ErrorMessage = "Please provide a date")]
        public string SupDateNoticed { get; set; }
    
        public string SupAdditionalDetails { get; set; }
    
        //Additional Data
    
        public string Message { get; set; }
    
        public List<UploadedFile> Attachments { get; set; }
    
        public IEnumerable<SelectListItem> SubmissionPurposes()
        {
            return new List<SelectListItem>
            {
                new SelectListItem() {Value = "", Text = "Please select an option"},
                new SelectListItem() {Value = "Suspicious Transaction Reporting", Text = "Suspicious Transaction Reporting"},
                new SelectListItem() {Value = "Request a Support Session", Text = "Request a Support Session"}
            };
        }
    

    我对所有建议都很开放,我认为某种自定义数据注释是最好的方法,因为这似乎是我可以对它进行精细控制的唯一方法,但后来我的问题将是如何有一个注释,就像我正在努力向下面努力的想法

    [CustomRequirement, SumissionPurpose = "Suspicious Transaction Reporting"]
    

    我知道在MVC 5.1中他们引入了一个新的DropdownForEnum功能但是从我看来到目前为止我看不到5.1或5.2中的任何新内容可能让我满足这个需求。

2 个答案:

答案 0 :(得分:1)

我过去曾使用Foolproof Validation。它们提供了一些额外的属性客户端验证。

[Is]
[EqualTo]
[NotEqualTo]
[GreaterThan]
[LessThan]
[GreaterThanOrEqualTo]
[LessThanOrEqualTo]

[RequiredIf]
[RequiredIfNot]
[RequiredIfTrue]
[RequiredIfFalse]
[RequiredIfEmpty]
[RequiredIfNotEmpty]
[RequiredIfRegExMatch]
[RequiredIfNotRegExMatch]

答案 1 :(得分:0)

自定义验证属性是可行的方法。请注意,如果模型中的属性是复杂对象,并且它们的验证取决于父对象属性,则不会获得父对象属性的验证上下文。在这种情况下,您必须考虑编写自己的模型验证器,从ModelValidator类实现并将其添加到ModelValidatorProvider工厂类。