In the world of MVC I have this view model...
public class MyViewModel{
[Required]
public string FirstName{ get; set; } }
...and this s
using Resources;
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using System.Reflection;
using System.Resources;
using System.Web;
using System.Web.Mvc;
public class CustomRequiredAttribute : RequiredAttribute, IClientValidatable
{
public CustomRequiredAttribute()
{
ErrorMessageResourceType = typeof(ValidationResource);
ErrorMessageResourceName = "RequiredErrorMessage";
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
{
yield return new ModelClientValidationRule
{
ErrorMessage = GetRequiredMessage(metadata.DisplayName),
ValidationType = "required"
};
}
private string GetRequiredMessage(string displayName) {
return displayName + " " + Resources.ValidationResource.RequiredErrorMessageClient;
}
}
App_GlobalResources/ValidationResource.resx
Now use data annotation
[CustomRequired]
public class GenericRequired: RequiredAttribute
{
public GenericRequired()
{
this.ErrorMessage = "{0} Blah blah";
}
}
Just change
[Required]
to
[Required(ErrorMessage = "Your Message, Bla bla bla aaa!")]
You can write your own attribute:
public class MyRequiredAttribute : ValidationAttribute
{
MyRequiredAttribute() : base(() => "{0} blah blah blah blaaaaaah")
{
}
public override bool IsValid(object value)
{
if (value == null)
{
return false;
}
string str = value as string;
if (str != null)
{
return (str.Trim().Length != 0);
}
return true;
}
}
This is copy of RequiredAttribute from Reflector with changed error message.
This worked for me. Carefully read the comments inside the code. (Based on Chad's answer).
// Keep the name the same as the original, it helps trigger the original javascript
// function for client side validation.
public class RequiredAttribute : System.ComponentModel.DataAnnotations.RequiredAttribute, IClientValidatable
{
public RequiredAttribute()
{
this.ErrorMessage = "Message" // doesnt get called again. only once.
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
{
yield return new ModelClientValidationRule
{
ErrorMessage = "Message", // this gets called on every request, so it's contents can be dynamic.
ValidationType = "required"
};
}
}
It seems that RequiredAttribute doesn't implement IClientValidatable, so if you override the RequiredAttribute it breaks client side validation.
So this is what I did and it works. Hope this helps someone.
public class CustomRequiredAttribute : RequiredAttribute, IClientValidatable
{
public CustomRequiredAttribute()
{
this.ErrorMessage = "whatever your error message is";
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
{
yield return new ModelClientValidationRule
{
ErrorMessage = this.ErrorMessage,
ValidationType = "required"
};
}
}