ASP.NET MVC 2自定义ModelValidator的问题
我试图validation我视图中的两个文本框字段中的任何一个都提供了值。 我做了这个模型validation器:
public class RequireEitherValidator : ModelValidator { private readonly string compareProperty; private readonly string errorMessage; public RequireEitherValidator(ModelMetadata metadata, ControllerContext context, string compareProperty, string errorMessage) : base(metadata, context) { this.compareProperty = compareProperty; this.errorMessage = errorMessage; } public override IEnumerable Validate(object container) { if (Metadata.Model == null) yield break; var propertyInfo = container.GetType().GetProperty(compareProperty); if (propertyInfo == null) throw new InvalidOperationException("Unknown property:" + compareProperty); string valueToCompare = propertyInfo.GetValue(container, null).ToString(); if (string.IsNullOrEmpty(Metadata.Model.ToString()) && string.IsNullOrEmpty(valueToCompare)) yield return new ModelValidationResult { Message = errorMessage }; } }
这个validation逻辑永远不会被击中,我认为这是因为没有值提供给文本框。
如果您需要它,这里是我创建的提供者和属性以及属性用法:
public class MyValidatorProvider : AssociatedValidatorProvider { protected override IEnumerable GetValidators( ModelMetadata metadata, ControllerContext context, IEnumerable attributes) { foreach (var attrib in attributes.OfType()) yield return new RequireEitherValidator(metadata, context, attrib.CompareProperty, attrib.ErrorMessage); } } public class RequireEitherAttribute : Attribute { public readonly string CompareProperty; public string ErrorMessage { get; set; } public RequireEitherAttribute(string compareProperty) { CompareProperty = compareProperty; } } public class StudentLogin { [DisplayName("Last Name")] [Required(ErrorMessage = "You must supply your last name.")] public string LastName { get; set; } [DisplayName("Student ID")] [RegularExpression(@"^d{1,8}$", ErrorMessage = "Invalid Student ID")] [RequireEither("SSN", ErrorMessage = "You must supply your student id or social security number.")] public int? StudentId { get; set; } [DisplayName("Social Security Number")] [RegularExpression(@"^d{9}|d{3}-d{2}-d{4}$", ErrorMessage = "Invalid Social Security Number")] public string SSN { get; set; } }
我的看法:
Please supply the following information to login:
-
x.LastName) %>
x.LastName)%> x.LastName) %>
-
x.StudentId) %>
x.StudentId) %> x.StudentId) %>
- OR -
x.SSN)%>
x.SSN) %> x.SSN) %>
解决这个问题的一种方法不仅仅是创建ValidationAttribute并在类级别应用它。
[RequireEither("StudentId", "SSN")] public class StudentLogin
错误消息将自动显示在“validation摘要”中。 该属性看起来像这样(我通过将所有内容视为字符串只是为了简洁,大大简化了IsValid()中的validation逻辑:
public class RequireEither : ValidationAttribute { private string firstProperty; private string secondProperty; public RequireEither(string firstProperty, string secondProperty) { this.firstProperty = firstProperty; this.secondProperty = secondProperty; } public override bool IsValid(object value) { var firstValue = value.GetType().GetProperty(this.firstProperty).GetValue(value, null) as string; var secondValue = value.GetType().GetProperty(this.secondProperty).GetValue(value, null) as string; if (!string.IsNullOrWhiteSpace(firstValue)) { return true; } if (!string.IsNullOrWhiteSpace(secondValue)) { return true; } // neither was supplied so it's not valid return false; } }
请注意,在这种情况下,传递给IsValid()的对象是类本身的实例而不是属性。
我喜欢Steve和Ronnie的解决方案,虽然他们创建的自定义属性可能用于其他类/属性对,但我不喜欢这个简单案例的“魔术字符串”和reflection,我通常创建一个适合的validation手头的情景。
例如,在这种情况下,我会创建类似于:
[AttributeUsage(AttributeTargets.Class)] public class RequireStudentInfoAttribute : ValidationAttribute { public override bool IsValid(object value) { var student = value as StudentLogin; if(student == null) { return false; } if (student.StudentId.HasValue || !string.IsNullOrEmpty(student.SSN)) { return true; } return false; } }
只需将它应用于StudentLogin类,如:
[RequireStudentInfo] public class StudentLogin
关于客户端validation,我通常会访问https://xval.codeplex.com/ ,因为它与Data Annotations的集成非常好
使用史蒂夫的建议只做了一些细微的改变:
public class RequireEitherAttribute : ValidationAttribute { private string firstProperty; private string secondProperty; public RequireEitherAttribute(string firstProperty, string secondProperty) { this.firstProperty = firstProperty; this.secondProperty = secondProperty; } public override bool IsValid(object value) { object firstValue = value.GetType().GetProperty(firstProperty).GetValue(value, null); object secondValue = value.GetType().GetProperty(secondProperty).GetValue(value, null); return InputSupplied(firstValue) || InputSupplied(secondValue); } private bool InputSupplied(object obj) { if (obj == null) return false; if (obj is string) { string str = (string)obj; if (str.Trim() == string.Empty) return false; } return true; } }
由于这不是属性级别validation,因此我必须向视图添加validation摘要。
我仍然很好奇如何将其与客户端validation联系起来。
上述就是C#学习教程:ASP.NET MVC 2自定义ModelValidator的问题分享的全部内容,如果对大家有所用处且需要了解更多关于C#学习教程,希望大家多多关注—计算机技术网(www.ctvol.com)!
本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。
ctvol管理联系方式QQ:251552304
本文章地址:https://www.ctvol.com/cdevelopment/992501.html