【问题标题】:Is it possible to add client validation to class level validator for MVC C#?是否可以将客户端验证添加到 MVC C# 的类级别验证器?
【发布时间】:2018-04-05 09:03:24
【问题描述】:

我有一个带有自定义验证器的嵌套模型,用于验证子元素。这种方法非常适合服务器端,但是,我还想添加客户端支持。

这是我的模型:

public class Customer
    {
        public string Name { get; set; } = "";

        [AtLeastOneProperty("HomePhone", "WorkPhone", "CellPhone", ErrorMessage = "At least one phone number is required for Customer")]
        public Phone phone { get; set; }

        public Customer()
        {
            phone = new Phone();
        }
    }
     public class Phone
     {
        public string HomePhone { get; set; } = "";

        public string WorkPhone { get; set; } = "";

        public string WorkExt { get; set; } = "";

        public string CellPhone { get; set; } = "";
     }

这是我的验证器:

public class AtLeastOnePropertyAttribute : ValidationAttribute, IClientValidatable
    {
        private readonly string[] _properties;
        public AtLeastOnePropertyAttribute(params string[] properties)
        {
            _properties = properties;
        }

        protected override ValidationResult IsValid(object value, ValidationContext validationContext)
        {
            if (_properties == null || _properties.Length < 1)
            {
                return null;
            }
            PropertyDescriptorCollection properties = TypeDescriptor.GetProperties(value);

            List<string> props = new List<string>();
            props.Add(properties[0].ToString());
            foreach (var property in _properties)
            {

                validationContext = new ValidationContext(value);

                var propertyInfo = validationContext.ObjectType.GetProperty(property);
                if (propertyInfo == null)
                {
                    return new ValidationResult(string.Format("unknown property {0}", property));
                }

                var propertyValue = propertyInfo.GetValue(validationContext.ObjectInstance, null);
                if (propertyValue is string && !string.IsNullOrEmpty(propertyValue as string))
                {
                    return null;
                }

                if (propertyValue != null)
                {
                    return null;
                }
            }

            return new ValidationResult(FormatErrorMessage(validationContext.DisplayName), props);
        }

        public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
        {
            var rule = new ModelClientValidationRule
            {
                ErrorMessage = ErrorMessage,
                ValidationType = "atleastonerequired"
            };
            rule.ValidationParameters["properties"] = string.Join(",", _properties);

            yield return rule;
        }
    }

此代码适用于服务器端验证,但是,我无法让它为我正在检查的那些属性构建客户端验证不显眼的标签。现在它正在尝试为类级别 Phone 构建标签,因为属性标签位于嵌套模型属性而不是单个属性之上。

甚至可以让它添加客户端标签吗?也许制作一个验证适配器?

【问题讨论】:

    标签: c# jquery asp.net-mvc validation unobtrusive-validation


    【解决方案1】:

    我之前也使用过Expressive Annotations。它们允许我们指定具有布尔条件的属性,这些条件可以在客户端和服务器端触发。

    【讨论】:

    • 我使用了表达性注解,它适用于单个属性。是的,有一种方法可以Parent-to-Child,但您需要在子类中包含父 TParent 引用,在父类中包含 TChild 引用。我之所以有上面的代码是为了重用“子”类。我想我知道你的意思是通过向孩子添加一个布尔属性并检查 RequireIf("Flag == true")...
    • 是的,根据逻辑从Phone返回布尔值并将其用作验证的表达式。
    猜你喜欢
    • 1970-01-01
    • 2012-07-29
    • 1970-01-01
    • 2010-09-14
    • 2014-07-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多