0
我一直試圖使EmailAddress自定義數據註釋屬性正確驗證電子郵件,它似乎並沒有在我的測試中爲我工作。服務器端自定義數據註釋驗證MVC 3
這裏的測試:
[Test]
public void ModelStateValidation()
{
var invalidEmails = new[] { "testtestcom", "[email protected]", "testtest.com" };
var validEmail = "[email protected]";
//Invalid Email addresses
foreach (var invalidEmail in invalidEmails)
{
var subscription = new SubscriberModel() { FirstName = "f", LastName = "l", Email = invalidEmail, ConfirmEmail = invalidEmail, DateSubscribed = DateTime.Now };
ValidateModelAsFalse(subscription);
}
var subscription2 = new SubscriberModel() { FirstName = "f", LastName = "l", Email = "t", ConfirmEmail = "t", DateSubscribed = DateTime.Now };
ValidateModelAsFalse(subscription2);
//Valid Email address
var subscription3 = new SubscriberModel() { FirstName = "f", LastName = "l", Email = validEmail, ConfirmEmail = validEmail, DateSubscribed = DateTime.Now };
ValidateModelAsTrue(subscription3);
//Last Name doesn't exists
var subscription4 = new SubscriberModel() { FirstName = "f", LastName = "", Email = validEmail, ConfirmEmail = validEmail, DateSubscribed = DateTime.Now };
ValidateModelAsFalse(subscription4);
//First Name doesn't exists
var subscription5 = new SubscriberModel() { FirstName = "", LastName = "l", Email = validEmail, ConfirmEmail = validEmail, DateSubscribed = DateTime.Now };
ValidateModelAsFalse(subscription5);
//Email addresses are equal
var subscription6 = new SubscriberModel() { FirstName = "f", LastName = "l", Email = "[email protected]", ConfirmEmail = "[email protected]", DateSubscribed = DateTime.Now };
ValidateModelAsFalse(subscription6);
}
private static void ValidateModelAsFalse(SubscriberModel subscription3)
{
SubscriptionController controller = new SubscriptionController();
controller.ValidateModel(subscription3);
AssertIsFalse(controller);
}
private static void ValidateModelAsTrue(SubscriberModel subscription3)
{
SubscriptionController controller = new SubscriptionController();
controller.ValidateModel(subscription3);
AssertIsTrue(controller);
}
private static void AssertIsTrue(SubscriptionController controller)
{
Assert.That(controller.ModelState.IsValid, Is.True);
}
private static void AssertIsFalse(SubscriptionController controller)
{
Assert.That(controller.ModelState.IsValid, Is.False);
}
這裏的ValidateModel方法:
<!-- language: c# -->
public static void ValidateModel<T>(this Controller controller, T model)
{
var validationContext = new ValidationContext(model, null, null);
var validationResults = new List<ValidationResult>();
Validator.TryValidateObject(model, validationContext, validationResults);
foreach (var validationResult in validationResults)
{
controller.ModelState.AddModelError(validationResult.MemberNames.First(), validationResult.ErrorMessage);
}
}
型號:
<!-- language: c# -->
public partial class SubscriberModel
{
public int SubscriberID { get; set; }
[Required]
[DisplayName("First Name")]
public string FirstName { get; set; }
[Required]
[DisplayName("Last Name")]
public string LastName { get; set; }
[Required]
[EmailAddress]
[Compare("ConfirmEmail", ErrorMessage = "The emails must match")]
[DisplayName("E-mail")]
public string Email { get; set; }
[Required]
[DisplayName("Confirm E-mail")]
public string ConfirmEmail { get; set; }
[Required]
[DisplayName("Date Subscribed")]
public DateTime DateSubscribed { get; set; }
}
控制器:
public partial class SubscriptionController : Controller
{
public ActionResult Index()
{
return View();
}
[CaptchaValidator]
[HttpPost]
public ActionResult Index(SubscriberModel subscription, bool captchaValid)
{
subscription.DateSubscribed = DateTime.Now;
ModelStateValid = ModelState.IsValid;
if(captchaValid)
{
if (ModelState.IsValid)
{
var test = "";
}
}
return View(subscription);
}
}
EmailAttribute類:
[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, AllowMultiple = false)]
public sealed class EmailAddressAttribute : ValidationAttribute, IClientValidatable
{
private static Regex _regex = new Regex(@"^((([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+(\.([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+)*)|((\x22)((((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(([\x01-\x08\x0b\x0c\x0e-\x1f\x7f]|\x21|[\x23-\x5b]|[\x5d-\x7e]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(\\([\x01-\x09\x0b\x0c\x0d-\x7f]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF]))))*(((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(\x22)))@((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?$", RegexOptions.Compiled | RegexOptions.IgnoreCase);
public EmailAddressAttribute()
: base()
{
ErrorMessage = "Invalid Email";
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context) {
yield return new ModelClientValidationRule {
ValidationType = "email",
ErrorMessage = FormatErrorMessage(metadata.GetDisplayName())
};
}
public override bool IsValid(object value)
{
if (value == null) {
return false;
}
string valueAsString = value as string;
return _regex.Match(valueAsString).Success;
}
}
的IsValid的方法似乎驗證了電子郵件地址,我打算,但由於某些原因,當我去跑在Controller.ValidateModel單元測試,它不會返回false和匹配我的斷言。
謝謝你,但客戶端驗證工作正常,它只是我不能讓服務器端驗證測試,以通過 – 2012-07-13 13:57:23
是提交表單時訪問您的IsValid()方法? – 2012-07-13 14:04:36
是的,當我在IsValid方法中設置斷點時,代碼似乎在我提交表單時正確流動 – 2012-07-13 14:16:18