HTML5 Form Validation

The latest versions of Google Chrome (16+), Mozilla Firefox (8+), and Internet Explorer (10+) all support HTML5 client-side validation. It is time to take HTML5 validation seriously.

The purpose of the blog post is to describe how you can take advantage of HTML5 client-side validation regardless of the type of application that you are building. You learn how to use the HTML5 validation attributes, how to perform custom validation using the JavaScript validation constraint API, and how to simulate HTML5 validation on older browsers by taking advantage of a jQuery plugin. Finally, we discuss the security issues related to using client-side validation.

Using Client-Side Validation Attributes

The HTML5 specification discusses several attributes which you can use with INPUT elements to perform client-side validation including the required, pattern, min, max, step, and maxlength attributes.

For example, you use the required attribute to require a user to enter a value for an INPUT element. The following form demonstrates how you can make the firstName and lastName form fields required:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>Required Demo</title>
</head>
<body>

    <form>
        <label>
            First Name:
            <input required title="First Name is Required!" />
        </label>
        <label>
            Last Name:
            <input required title="Last Name is Required!" />
        </label>
        <button>Register</button>
    </form>


</body>
</html>

If you attempt to submit this form without entering a value for firstName or lastName then you get the validation error message:

clip_image001

Notice that the value of the title attribute is used to display the validation error message “First Name is Required!”. The title attribute does not work this way with the current version of Firefox. If you want to display a custom validation error message with Firefox then you need to include an x-moz-errormessage attribute like this:

<input required title="First Name is Required!"

     x-moz-errormessage="First Name is Required!" />


clip_image002

The pattern attribute enables you to validate the value of an INPUT element against a regular expression. For example, the following form includes a social security number field which includes a pattern attribute:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>Pattern</title>
</head>
<body>

    <form>
        <label>
            Social Security Number:
            <input required pattern="^d{3}-d{2}-d{4}$"
                title="###-##-####" />
        </label>
        <button>Register</button>
    </form>


</body>
</html>

The regular expression in the form above requires the social security number to match the pattern ###-##-####:

clip_image003

Notice that the input field includes both a pattern and a required validation attribute. If you don’t enter a value then the regular expression is never triggered. You need to include the required attribute to force a user to enter a value and cause the value to be validated against the regular expression.

Custom Validation

You can take advantage of the HTML5 constraint validation API to perform custom validation. You can perform any custom validation that you need. The only requirement is that you write a JavaScript function.

For example, when booking a hotel room, you might want to validate that the Arrival Date is in the future instead of the past:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>Constraint Validation API</title>
</head>
<body>

    <form>
        <label>
            Arrival Date:
            <input id="arrivalDate" type="date" required />
        </label>
        <button>Submit Reservation</button>
    </form>

    <script type="text/javascript">

        var arrivalDate = document.getElementById("arrivalDate");

        arrivalDate.addEventListener("input", function() {
            var value = new Date(arrivalDate.value);
            if (value < new Date()) {
                arrivalDate.setCustomValidity("Arrival date must be after now!");
            } else {
                arrivalDate.setCustomValidity("");
            }

        });

    </script>

</body>
</html>

The form above contains an input field named arrivalDate. Entering a value into the arrivalDate field triggers the input event.

The JavaScript code adds an event listener for the input event and checks whether the date entered is greater than the current date. If validation fails then the validation error message “Arrival date must be after now!” is assigned to the arrivalDate input field by calling the setCustomValidity() method of the validation constraint API. Otherwise, the validation error message is cleared by calling setCustomValidity() with an empty string.

clip_image004

HTML5 Validation and Older Browsers

But what about older browsers? For example, what about Apple Safari and versions of Microsoft Internet Explorer older than Internet Explorer 10?

What the world really needs is a jQuery plugin which provides backwards compatibility for the HTML5 validation attributes. If a browser supports the HTML5 validation attributes then the plugin would do nothing. Otherwise, the plugin would add support for the attributes.

Unfortunately, as far as I know, this plugin does not exist. I have not been able to find any plugin which supports both the required and pattern attributes for older browsers, but does not get in the way of these attributes in the case of newer browsers.

There are several jQuery plugins which provide partial support for the HTML5 validation attributes including:

· jQuery Validation — http://docs.jquery.com/Plugins/Validation

· html5Form — http://www.matiasmancini.com.ar/jquery-plugin-ajax-form-validation-html5.html

· h5Validate — http://ericleads.com/h5validate/

The jQuery Validation plugin – the most popular JavaScript validation library – supports the HTML5 required attribute, but it does not support the HTML5 pattern attribute. Likewise, the html5Form plugin does not support the pattern attribute.

The h5Validate plugin provides the best support for the HTML5 validation attributes. The following page illustrates how this plugin supports both the required and pattern attributes:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>h5Validate</title>
    <style type="text/css">
        .validationError {
            border: solid 2px red;
        }
        .validationValid {
            border:  solid 2px green;
        }
    </style>
</head>
<body>
    <form id="customerForm">
        <label>
            First Name:
            <input id="firstName" required />
        </label>
        <label>
            Social Security Number:
            <input id="ssn" required pattern="^d{3}-d{2}-d{4}$"
                title="Expected pattern is ###-##-####" />
        </label>
        <input type="submit" />
    </form>

    <script type="text/javascript" src="Scripts/jquery-1.4.4.min.js"></script>
    <script type="text/javascript" src="Scripts/jquery.h5validate.js"></script>
    <script type="text/javascript">

        // Enable h5Validate plugin
        $("#customerForm").h5Validate({
            errorClass: "validationError",
            validClass: "validationValid"
        });

        // Prevent form submission when errors
        $("#customerForm").submit(function (evt) {
            if ($("#customerForm").h5Validate("allValid") === false) {
                evt.preventDefault();
            }
        });

    </script>

</body>
</html>

When an input field fails validation, the validationError CSS class is applied to the field and the field appears with a red border. When an input field passes validation, the validationValid CSS class is applied to the field and the field appears with a green border.

clip_image006

From the perspective of HTML5 validation, the h5Validate plugin is the best of the plugins. It adds support for the required and pattern attributes to browsers which do not natively support these attributes such as IE9. However, this plugin does not include everything in my wish list for a perfect HTML5 validation plugin.

Here’s my wish list for the perfect back compat HTML5 validation plugin:

1. The plugin would disable itself when used with a browser which natively supports HTML5 validation attributes. The plugin should not be too greedy – it should not handle validation when a browser could do the work itself.

2. The plugin should simulate the same user interface for displaying validation error messages as the user interface displayed by browsers which natively support HTML5 validation. Chrome, Firefox, and Internet Explorer all display validation errors in a popup. The perfect plugin would also display a popup.

3. Finally, the plugin would add support for the setCustomValidity() method and the other methods of the HTML5 validation constraint API. That way, you could implement custom validation in a standards compatible way and you would know that it worked across all browsers both old and new.

Security

It would be irresponsible of me to end this blog post without mentioning the issue of security. It is important to remember that any client-side validation — including HTML5 validation — can be bypassed.

You should use client-side validation with the intention to create a better user experience. Client validation is great for providing a user with immediate feedback when the user is in the process of completing a form. However, client-side validation cannot prevent an evil hacker from submitting unexpected form data to your web server.

You should always enforce your validation rules on the server. The only way to ensure that a required field has a value is to verify that the required field has a value on the server. The HTML5 required attribute does not guarantee anything.

Summary

The goal of this blog post was to describe the support for validation contained in the HTML5 standard. You learned how to use both the required and the pattern attributes in an HTML5 form. We also discussed how you can implement custom validation by taking advantage of the setCustomValidity() method.

Finally, I discussed the available jQuery plugins for adding support for the HTM5 validation attributes to older browsers. Unfortunately, I am unaware of any jQuery plugin which provides a perfect solution to the problem of backwards compatibility.

Discussion

  1. Stilgar says:

    I have long maintained that the only useful part of HTML5 for people who build applications for real customers in The Real World ™ is the input enhancements (both the validation and the new input types). People who build applications for The Real World ™ do not care about Canvas or Video or WebGL. They care about countless validators, JavaScript calendars/datepickers, etc. Sadly browser makers don’t pay enough attention to these because implementing hardware accelerated canvas allows them to present fancier demos. The devs fall for this because they all believe they will use these features when they create The Next Big Thing ™… and then they go back to coding validators and JS datepickers.

    The saddest part is that your article contains a mistake. The latest version of IE is IE9. At least this is the case in The Real World ™

    • Corey Gaudin says:

      I agree with you Stilgar. Although that other stuff is nice to completely remove the need for a plugin model (and mobile support) such as Flash/Silverlight, the real meat and potatoes for business applications is simplistic validation and more input controls. It is unheard of that in the year 2012 we are still having to utilize javascript widgets to inject in controls on simple textbox controls. I understand that the Html Specs move slow, but this is reeeeally slow for such a simple yet under utilized feature that should have been web baked 5-10 years ago.

  2. SleepyCoder says:

    Actually, there is increasing use of the canvas element to implement “controls” and other components in html5 where consistent appearance and tight control of presentation and layout is important for the functionality of the component. For example, I’m seeing excell-like spreadsheet components being implemented quite successfully in canvas.

  3. Michael says:

    I look forward to your team building that jQuery validation plugin you speak of. ;) Hopefully we will have it one of these days, as my company has to support back to IE7 for quite some time.