Here is an example from MSDN :
PhoneMaskAttribute.cs:
using System; using System.Globalization; using System.ComponentModel.DataAnnotations; [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)] sealed public class PhoneMaskAttribute : ValidationAttribute { // Internal field to hold the mask value. readonly string _mask; public string Mask { get { return _mask; } } public PhoneMaskAttribute(string mask) { _mask = mask; } public override bool IsValid(object value) { var phoneNumber = (String)value; bool result = true; if (this.Mask != null) { result = MatchesMask(this.Mask, phoneNumber); } return result; } // Checks if the entered phone number matches the mask. internal bool MatchesMask(string mask, string phoneNumber) { if (mask.Length != phoneNumber.Trim().Length) { // Length mismatch. return false; } for (int i = 0; i < mask.Length; i++) { if (mask[i] == 'd' && char.IsDigit(phoneNumber[i]) == false) { // Digit expected at this position. return false; } if (mask[i] == '-' && phoneNumber[i] != '-') { // Spacing character expected at this position. return false; } } return true; } public override string FormatErrorMessage(string name) { return String.Format(CultureInfo.CurrentCulture, ErrorMessageString, name, this.Mask); } }
Application:
CustomerMetadata.cs:
using System.Web.DynamicData; using System.ComponentModel.DataAnnotations; [MetadataType(typeof(CustomerMetadata))] public partial class Customer { } public class CustomerMetadata { [PhoneMask("999-999-9999", ErrorMessage = "{0} value does not match the mask {1}.")] public object Phone; }
References:
A practical guide. Configuring data field validation in a data model using custom attributes
Dmitry Zaets
source share