How to do validation in Spring MVC?

In the previous article, we have seen How to upload files in Spring MVC you can check it here How to upload Files in Spring MVC. In this article, we will see How to validate inputs in Spring MVC.

While building any web application, validating input is an important part. Inputs can be validated on the client-side as well as on the server-side.

  • Client-side validation can be done using Javascript for eg. if the input is submitted for an email, a javascript validator would provide an error if anything is submitted that does not involve email.
  • Server-side validation is done on the server where the data is validated before it is sent to the database. It is a secure way of validating input because even if the user clicks on view-source on the browser he won’t be able to see the code.

Here, we will look at the server-side validation in Spring MVC with a simple example.

Spring MVC Validation

To build an application using spring MVC it is necessary to validate the input string. In Spring MVC, we have a Bean Validation API to support validation. (It is available in Spring 4 or higher version). It is a part of the Jakarta JE and Java SE editions.

Bean Validation API

The Bean Validation from the name itself we can understand the validation annotation can be applied to the properties of the bean.

  • The Bean Validation is just a specification API, in order to implement it we require Hibernate Validator.
  • Hibernate Validator is the reference implementation of validation API.

To use it we need to add certain dependencies inside pom.xml.

<!-- https://mvnrepository.com/artifact/org.hibernate/hibernate-validator -->
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-validator</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.hibernate.validator/hibernate-validator-cdi -->
    <dependency>
      <groupId>org.hibernate.validator</groupId>
      <artifactId>hibernate-validator-cdi</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.validation/validation-api -->
    <dependency>
      <groupId>javax.validation</groupId>
      <artifactId>validation-api</artifactId>
      <version>2.0.1.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.hibernate.validator/hibernate-validator-annotation-processor -->
    <dependency>
      <groupId>org.hibernate.validator</groupId>
      <artifactId>hibernate-validator-annotation-processor</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

Regular Expression Validation

Spring MVC also supports regular expression to validate input. In the web- application if we want some password to be validated in some pattern, we can use @Pattern annotation.

Validation Annoatations

Following is the list of annotations we will use to validate inputs in spring MVC.

Annotation

Description

@Max It validates whether the value is less than or equal to the specified maximum.
@Min It validates whether the value is greater than or equal to the specified minimum.
@NotEmpty It validates whether the value is not null/not empty.
@Null It validates whether the value is null.
@NotNull It validates whether the value is not null.
@NotBlank It validates whether the value is not null and trimmed length > 0
@Digits It validates whether the value is a number.
@Pattern It validates whether the value matches with regex.
@Size It validates whether the value is between the min and max.

Spring MVC Validation Example

Create a Spring Project Go to File> New > Other > Search maven > Select Maven Project > Next > Search Filter org.apche.maven.archetypes/webapp > Next > Enter Group Id & Archetype id > Finish

Add the following dependencies into the pom.xml files

<!-- https://mvnrepository.com/artifact/org.hibernate/hibernate-validator -->
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-validator</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.hibernate.validator/hibernate-validator-cdi -->
    <dependency>
      <groupId>org.hibernate.validator</groupId>
      <artifactId>hibernate-validator-cdi</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.validation/validation-api -->
    <dependency>
      <groupId>javax.validation</groupId>
      <artifactId>validation-api</artifactId>
      <version>2.0.1.Final</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.hibernate.validator/hibernate-validator-annotation-processor -->
    <dependency>
      <groupId>org.hibernate.validator</groupId>
      <artifactId>hibernate-validator-annotation-processor</artifactId>
      <version>6.1.3.Final</version>
    </dependency>

    
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-context -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-web -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-web</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-core -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-core</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-beans -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-beans</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/javax.servlet/jstl -->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>jstl</artifactId>
      <version>1.2</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.servlet.jsp/javax.servlet.jsp-api -->
    <dependency>
      <groupId>javax.servlet.jsp</groupId>
      <artifactId>javax.servlet.jsp-api</artifactId>
      <version>2.3.3</version>
      <scope>provided</scope>
    </dependency>
    <!-- https://mvnrepository.com/artifact/javax.servlet/javax.servlet-api -->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>javax.servlet-api</artifactId>
      <version>4.0.1</version>
      <scope>provided</scope>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-webmvc -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>5.3.5</version>
    </dependency>

Create a web.xml file

Web.xml is a deployment descriptor that is used by the server to map the incoming request.

<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
  <display-name>Archetype Created Web Application</display-name>
  <servlet>    
    <servlet-name>spring</servlet-name>    
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> 
    <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>/WEB-INF/Spring-servlet.xml</param-value>
    </init-param>   
    <load-on-startup>1</load-on-startup>      
</servlet>    
<servlet-mapping>    
    <servlet-name>spring</servlet-name>    
    <url-pattern>/</url-pattern>    
</servlet-mapping>  
</web-app>

Create a Spring-servlet.xml

  • Here, we have used <context:component-scan> detects the annotation by package scanning.
  • To resolves views such as JSP, we have used InternalResourceViewResolver.
  • To use validation on Bean, use LocalValidatorFactoryBean
  • Use the <mvc:annotation-driven/> to provide support for validation.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:context="http://www.springframework.org/schema/context"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xmlns:mvc="http://www.springframework.org/schema/mvc"
   xsi:schemaLocation="
   http://www.springframework.org/schema/beans     
   http://www.springframework.org/schema/beans/spring-beans.xsd
   http://www.springframework.org/schema/context 
   http://www.springframework.org/schema/context/spring-context.xsd
   http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">
   
   <mvc:annotation-driven  validator="myBeansValidator"/>
   <!--  component scan -->
   <context:component-scan base-package="org.mvc.controller"></context:component-scan>
   
   <bean id="myBeansValidator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />
   
   
   
  <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
  <property name="prefix" value="/WEB-INF/views/" />
      <property name="suffix" value=".jsp" />
  </bean>
   </beans>

Create the bean class – Player.java

  • Inside this class, use the annotation on the fields.
  • Here, we have use @NotNull,@NotBlank annotation on Id, name.
  • Also, used regex on the password field using @Pattern.
package org.mvc.controller;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Pattern;
import javax.validation.constraints.Size;




public class Player {

  @NotNull(message = "Id is required")	
  private Long id;
  @NotBlank(message = "Name is required")
  private String name;
  @NotBlank(message = "Email is required")
  private String email;
  @NotBlank(message = "Password is required")
  @Pattern(regexp = "^[a-zA-Z0-9]{6}", message = "Length of the Password cannot be more than 6")
  private String password;
  public Long getId() {
    return id;
  }
  public void setId(Long id) {
    this.id = id;
  }
  public String getName() {
    return name;
  }
  public void setName(String name) {
    this.name = name;
  }
  public String getEmail() {
    return email;
  }
  public void setEmail(String email) {
    this.email = email;
  }
  public String getPassword() {
    return password;
  }
  public void setPassword(String password) {
    this.password = password;
  }
  @Override
  public String toString() {
    return "Player [id=" + id + ", name=" + name + ", email=" + email + ", password=" + password + "]";
  }
  
}

Create a Controller – Home Controller

  • The @Controller here defines the class as Controller in SpringMVC.
  • The @RequestMapping is used to map the URL.
  • The @Valid annotation is used to apply validation rules on the object player.
  • The  BindingResult interface contains the result of validation.
  • It should be noted that BindingResult should always come after the @Valid.
package org.mvc.controller;

import javax.validation.Valid;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class HomeController {

  @RequestMapping("/")
  public String home(Model m) {
    Player player = new Player();
    m.addAttribute("player", player);
    return "index";
  }

  @RequestMapping("/add")
  public String form(@Valid @ModelAttribute("player") Player player, BindingResult result) {
    System.out.println(result);
    if(result.hasErrors()) {
      return "index";
    }
    System.out.println(player);
    return "result";

  }
}

Create Views

  • In index. jsp, we have created a form to accept Id, name, email, and password.
  • Here, we have to use the form tag library of Spring MVC.
  • To display error, use the <f:errro path=””/> tag.
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<%@ taglib prefix="f" uri="http://www.springframework.org/tags/form"%>
<html>
<head>
 <style>
      .error {
         color: #ff0000;
      }

   </style>
<!-- CSS only -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous">
<!-- JavaScript Bundle with Popper -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js" integrity="sha384-MrcW6ZMFYlzcLA8Nl+NtUVF0sA7MsXsP1UyJoMp4YLEuNSfAP+JcXn/tWtIaxVXM" crossorigin="anonymous"></script>
<title>Spring MVC</title>
</head>
<body style="background-color: #e2e2e2">
<div class="container mt-5">
  <div class="card " style="width: 25rem; ">
    <div class="card-body">
      <h5 class="card-title " align="center" >Player Form</h5>
      <f:form modelAttribute="player" action="add" method="post">
      <div class="form-group">
          <label for="exampleInputEmail1">Player Id</label>
          <f:input path="id" class="form-control" />
          <f:errors path="id" cssClass="error"/>
        </div>
        <div class="form-group">
          <label for="exampleInputEmail1">Name</label>
          <f:input path="name" class="form-control" />
          <f:errors path="name" cssClass="error"/>
        </div>
        <div class="form-group">
          <label for="exampleInputEmail1">Email</label>
          <f:input path="email" class="form-control" />
          <f:errors path="email" cssClass="error"/>
        </div>
        <div class="form-group">
          <label for="exampleInputEmail1">Password</label>
          <f:input path="password" class="form-control" type="password" />
          <f:errors path="password" cssClass="error"/>
          
        </div>
        <br>
        <div class="form-group mt-2 ">
        <center>	<input type="submit" value="Add Player" class="btn btn-warning"></center>
        </div>

      </f:form>

    </div>
  </div>
</div>	
</body>
</html>

result.jsp

This page just displays the values entered in the fields.

<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<%@ taglib prefix="f" uri="http://www.springframework.org/tags/form"%>
<html>
<head>
<!-- CSS only -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous">
<!-- JavaScript Bundle with Popper -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js" integrity="sha384-MrcW6ZMFYlzcLA8Nl+NtUVF0sA7MsXsP1UyJoMp4YLEuNSfAP+JcXn/tWtIaxVXM" crossorigin="anonymous"></script>
<title>Spring MVC</title>
</head>
<body  style="background-color: #e2e2e2">

  <h1 align="center">Validation in Spring MVC</h1>
  <div class="container mt-5">
  <div class="card " style="width: 25rem; " align="center">
  <h5 class="card-title " align="center" >Getting Form Data</h5>
    <div class="card-body">
    <table class="table mt-3 table-info "  >
      <tr>
        <td>Id</td>
        <td><c:out value="${player.id }"/></td>
      </tr>
      <tr>
        <td>Name</td>
        <td><c:out value="${player.name }"/></td>
      </tr>
      <tr>
        <td>Email</td>
        <td><c:out value="${player.email }"/></td>
      </tr>
      <tr>
        <td>Password</td>
        <td><c:out value="${player.password }"/></td>
      </tr>
      
      
    </table>
</div></div></div>
</body>
</html>

Now, just deploy the application on the server and see the following output. On click on Add Player, the following error will show.

                                   

In this way, we validate input in Spring MVC using Bean Validation API which is uses Hibernate Validator as an implementor.