Follow Us

Skip Navigation LinksHome > Articles > Asp .Net MVC > ASP .NET MVC 3 Validation using Custom DataAnnotation Attribute

ASP .NET MVC 3 Validation using Custom DataAnnotation Attribute

This article demonstrates how to create custom DataAnnotation ValidationAttribute in MVC 3

By Keyur   On   Saturday, 07 May 2011

Page Views : 37315   |   Technologies : Asp .Net MVC

Rating : Rated :
0
| More..
Introduction

ASP .NET MVC 3 Validation using DataAnnotation

This is the second article from the series of articles on ASP .NET MVC 3 validation. In the first article we looked at using DataAnnotation attributes for applying validation to MVC 3 application. In this article we will take a look at creating custom validation DataAnnotation attribute.

In order to understand this we will create a form where a candidate will have to enter his previous project’s start date and end date. It’s obvious that end date must be greater than start date. In the first article we looked at Compare DataAnnotaiton attribute where we did cross property validation without writing any custom logic. But for something like greater than validation data annotation does not have any out of the box validation attribute. So let’s get started.

A1. Creating MVC 3 application.

The first thing is we need a basic MVC 3 application. Go ahead and create an empty MVC 3 application as shown in the screen shot below.

A2. Adding Controller/Model/View.

Let’s modify our project to have a CandidateModel, CandidateController and Candidate view added to our project. Have a look at the screen shot below.

While adding the view let’s make sure to use the “Create” scaffold template to get HTML in your view out of the box.

A3. Model class

		    public class CandidateInfo
    {
        [Required(ErrorMessage="User name is Required")]                
        [Display(Name = "User name")]
        public string UserName { get; set; }
 
        [Required]
        [DataType(DataType.EmailAddress)]
        [Display(Name = "Email address")]
        public string Email { get; set; }
 
        [Required]
        [DataType(DataType.DateTime)]
        [Display(Name = "StartDate")]
        public DateTime StartDate { get; set; }
 
        [Required]
        [DataType(DataType.DateTime)]
        [Display(Name = "EndDate")]
        [DateGreaterThanAttribute("StartDate")]
        public DateTime EndDate { get; set; }
    }
	

One thing to note here is the DateGreaterThanAttribute , which are going to talk about next.

A4. View code generated using scaffolding.

		    <% using (Html.BeginForm()) { %>
        <%: Html.ValidationSummary(true) %>
        <fieldset>
            <legend>CandidateInfo</legend>
    
            <div class="editor-label">
                <%: Html.LabelFor(model => model.UserName) %>
            </div>
            <div class="editor-field">
                <%: Html.EditorFor(model => model.UserName) %>
                <%: Html.ValidationMessageFor(model => model.UserName) %>
            </div>
    
            <div class="editor-label">
                <%: Html.LabelFor(model => model.Email) %>
            </div>
            <div class="editor-field">
                <%: Html.EditorFor(model => model.Email) %>
                <%: Html.ValidationMessageFor(model => model.Email) %>
            </div>
    
            <div class="editor-label">
                <%: Html.LabelFor(model => model.StartDate) %>
            </div>
            <div class="editor-field">
                <%: Html.EditorFor(model => model.StartDate) %>
                <%: Html.ValidationMessageFor(model => model.StartDate) %>
            </div>
    
            <div class="editor-label">
                <%: Html.LabelFor(model => model.EndDate) %>
            </div>
            <div class="editor-field">
                <%: Html.EditorFor(model => model.EndDate) %>
                <%: Html.ValidationMessageFor(model => model.EndDate) %>
            </div>
    
            <p>
                <input type="submit" value="Create" />
            </p>
        </fieldset>
    <% } %>
    
    <div>
        <%: Html.ActionLink("Back to List", "Index") %>
    </div>
	
Custom Validation DataAnnotation Attribute

This is how the code looks for that custom validation attribute. Let’s try to understand what we are doing here.

		    public sealed class DateGreaterThanAttribute : ValidationAttribute
    {
        private const string _defaultErrorMessage = "'{0}' must be greater than '{1}'";
        private string _basePropertyName;
 
        public DateGreaterThanAttribute(string basePropertyName) : base(_defaultErrorMessage)
        {
            _basePropertyName = basePropertyName;
        }
 
        //Override default FormatErrorMessage Method
        public override string FormatErrorMessage(string name)
        {
            return string.Format(_defaultErrorMessage, name, _basePropertyName);
        }
 
        //Override IsValid
        protected override ValidationResult IsValid(object value, ValidationContext validationContext)
        {
            //Get PropertyInfo Object
            var basePropertyInfo = validationContext.ObjectType.GetProperty(_basePropertyName);
 
            //Get Value of the property
            var startDate = (DateTime)basePropertyInfo.GetValue(validationContext.ObjectInstance, null);
 
            
            var thisDate = (DateTime)value;
 
            //Actual comparision
            if (thisDate <= startDate)
            {
                var message = FormatErrorMessage(validationContext.DisplayName);
                return new ValidationResult(message);
            }
 
            //Default return - This means there were no validation error
            return null;
        }
 
    }

	

We have derived this class from ValidationAttribute . Than we are going to override the base class IsValid method. The important thing to note here we are using the overloaded IsValid method which has ValidationContext  . We have defined a private error message which is being passed to the base class constructor. ValidationContext will contain all the information about the model like Type, Properties and values for the properties.

The basePropertyType is the name of the property against which we are going to validate our current property. From the ValidationContext we will find out first the PropertyInfo and the property values. Once we have these values it is as simple as casting them to DateTime and comparing and based on the result passng True/False for the IsValid method.

Another method we are orverriding here is the FormatErrorMessage where we are using the default error message string while returning the new ValidationResult .

Now, let’s go ahead and run the application try putting incorrect values in the input fields for dates and try submitting the form. You should see the result as below.

Result

Since this validation is not working on the client side, in the next article we will see how we can create creat jQuery validator plugin to enable client side validation.

Thanks.


Keywords : using System.ComponentModel.DataAnnotations;

Tags : DataAnnotationValidationAttributeASP .Net MVC
Rate This Article :

Comments :

blog comments powered by Disqus
User Login
Username :
Password :
Register Login

Forgot Password


Related Articles