Client-Side Validation

Browsers check HTML attributes such as required on their own; ASP.NET Core's validation scripts check your model's data annotations in the browser, from the data-val attributes the tag helpers write.

Apprentice · ASP.NET Core · HTML · Updated

After this lesson you can

  • Turn on client-side validation from data annotations with the validation scripts partial, and use HTML validation attributes

Key takeaways

  • Browsers check HTML attributes such as required, minlength and type="email" on their own, with their own messages.
  • asp-for writes your data annotations into the input as data-val attributes, with your messages; the validation scripts do the checking.
  • Add <partial name="_ValidationScriptsPartial" /> in the view's Scripts section, and the form is checked before it's sent, with no JavaScript to write.
  • The server still checks ModelState.IsValid every time: scripts can be switched off, and rules that need the database only run there.

Server-side validation protects your data, but the user only finds out after the round trip to the server. Client-side validation checks in the browser, before the form is sent, so a message appears straight away.

HTML's own validation

Browsers understand a few validation attributes by themselves:

<form method="post" action="/Account/Login">
    <input type="text" name="userName" required>
    <input type="password" name="password" required minlength="8">
    <button type="submit">Sign in</button>
</form>

The browser won't send this form while a required field is empty, and shows its own message.

Attribute Rule
required Must be filled in
minlength, maxlength Fewest and most characters
min, max Smallest and largest number (or date)
type="email", type="number", type="date" Must be that kind of value
pattern Must match a regular expression

They're quick to add, but each browser shows its own messages, in its own style.

Validation from your data annotations

ASP.NET Core can check your model's annotations in the browser, with your own messages. Look at what asp-for writes for the product form:

<input class="form-control" type="text" data-val="true"
       data-val-length="A name can be at most 40 characters." data-val-length-max="40"
       data-val-required="Enter the product&#x27;s name."
       id="ProductName" maxlength="40" name="ProductName" value="">

Every data-val-... attribute is one of your rules, with its message: [Required] became data-val-required, [StringLength(40)] became data-val-length. On their own they do nothing. A small set of scripts reads them and does the checking.

Turning it on

The MVC template ships the scripts in wwwroot/lib (jQuery Validation and its unobtrusive add-on) and a partial view that loads them, Views/Shared/_ValidationScriptsPartial.cshtml. Add it to the form's view, in the Scripts section from Layouts and _ViewStart:

@section Scripts {
    <partial name="_ValidationScriptsPartial" />
}

Now, in the browser:

  • leaving the name empty and moving on shows Enter the product's name. in the field's asp-validation-for span, at once;
  • the form isn't sent until every rule passes;
  • the messages are your ErrorMessage texts, the same ones the server would show.

There's no JavaScript to write: the rules are the attributes on your model.

The server still checks

Client-side validation is a convenience. Anyone can switch off scripts, or send a request without your form. Your POST action still checks ModelState.IsValid, every time, and rules that need the database, such as There's already a product with that name, only exist on the server.

Check yourself

1 question to try on the lesson page.

So what

One line in the view, and the rules on your model check the form as it's filled in, with your own messages. The user gets instant feedback; the server keeps the final say.

Key terms

Cheat sheets