Form Submitting with Spring Boot Validation

Posted on


This tutorial is how to create and submit a form and how to validate our registration form.

Necessary Environments

Source Code

You can refer to the source code below.

Let’s start by following these steps

Step 1. Creating a project

  • File → New → Spring Starter Project
    Alt Text
  • Fill the necessary information and add dependencies.
    Alt Text
    Alt Text
  • Project Explorer is like this.
    Alt Text

Step 2. Let’s start code

package com.reytech.demo.model;

import java.time.LocalDate;
import java.util.List;
import javax.validation.constraints.Email;
import javax.validation.constraints.Max;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Past;
import javax.validation.constraints.Positive;
import javax.validation.constraints.Size;
import org.springframework.format.annotation.DateTimeFormat;

public class Student {

    @NotEmpty(message = "{}")
    @Size(min = 2, max = 50, message = "{}")
    private String name;

    @NotNull(message = "{validation.age.NotNull}")
    @Positive(message = "{validation.age.Positive}")
    @Max(value = 18, message = "{validation.age.Maximum}")
    private Integer age;

    @NotEmpty(message = "{}")
    @Email(message = "{}")
    private String email;

    @NotEmpty(message = "{validation.subjects.NotEmpty}")
    private List <String> subjects;

    @NotNull(message = "{validation.birthDate.NotNull}")
    @Past(message = "{validation.birthDate.Past}")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private LocalDate birthDate;

    @NotEmpty(message = "{validation.gender.NotEmpty}")
    private String gender;

    public String getName() {
        return name;

    public void setName(String name) { = name;

    public Integer getAge() {
        return age;

    public void setAge(Integer age) {
        this.age = age;

    public String getEmail() {
        return email;

    public void setEmail(String email) { = email;

    public LocalDate getBirthDate() {
        return birthDate;

    public void setBirthDate(LocalDate birthDate) {
        this.birthDate = birthDate;

    public String getGender() {
        return gender;

    public void setGender(String gender) {
        this.gender = gender;

    public List <String> getSubjects() {
        return subjects;

    public void setSubjects(List <String> subjects) {
        this.subjects = subjects;

  • We will store student information in Student.class model.

  • And, @Size, @NotEmpty, @Email, etc. are to validate input when the user fills an error input.

  • We will use custom message by creating (e.g.message=”{}”, you can see the custom message in file.)

  • We will set custom messages. fill in Name size must be between 2 and 30 must be only characters
validation.age.NotNull=Please fill in Age
validation.age.Maximum=Age must be under 18
validation.age.Positive=Age must not be negative value and 0
validation.age.Pattern=Age must be only numbers fill in Email fill in valid Email
validation.birthDate.NotNull=Please fill in Birth Date
validation.birthDate.Past=Please fill in valid Birth Date
validation.subjects.NotEmpty=Please select Subjects
validation.gender.NotEmpty=Please select Gender

  • To handle, MessageSource and LocalValidatorFactoryBean are needed.
package com.reytech.demo;

import org.springframework.context.MessageSource;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.validation.beanvalidation.LocalValidatorFactoryBean;

public class AppConfiguration {

    public MessageSource messageSource() {
        ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
        return messageSource;

    public LocalValidatorFactoryBean validator() {
        LocalValidatorFactoryBean bean = new LocalValidatorFactoryBean();
        return bean;

package com.reytech.demo.constant;

public enum Gender {

package com.reytech.demo.constant;

public enum Subject {

    private final String value;

    private Subject(String value) {
        this.value = value;

    public String getValue() {
        return value;

package com.reytech.demo.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.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import com.reytech.demo.constant.Gender;
import com.reytech.demo.constant.Subject;
import com.reytech.demo.model.Student;

public class HomeController {

    public String showForm(Model model) {
        Student student = new Student();
        model.addAttribute("student", student);
        model.addAttribute("gender_value", Gender.values());
        model.addAttribute("subject_value", Subject.values());
        return "form";

    public String submitForm(@Valid Student student, BindingResult bindingResult, Model model) {
        if (bindingResult.hasErrors()) {
            model.addAttribute("student", student);
            model.addAttribute("gender_value", Gender.values());
            model.addAttribute("subject_value", Subject.values());
            return "form";
        } else {
            model.addAttribute("result", student);
            return "result";

    public String backHome() {
        return "redirect:/form";


The controller is used to handle GET/POST requests at /HTTP endpoint.

  • The showForm() method is to reach localhost:/8080/form as a GET request and return the view which is form.html by using thymeleaf. It uses a Model object to expose a new Student object to the view template. The values of Gender and Subjects are carried by using the model.addAttribute and displayed the result in result.html.

  • The saveForm() method is to reach localhost:8080/form/result as a POST request when submitting data by the user. The submitted data is saved in “result” and carried by model.addAttribute. And this method returns the view which is result.html but it returns back to form.html when submitted data are errors.


  • We will create a form to fill data in form.html.
<!DOCTYPE html>
<html xmlns:th="">
<meta charset="UTF-8" />
<link rel="stylesheet"
<link rel="stylesheet"
<script src=""></script>
<script src=""></script>
$(function() {
<div class="container">
<h1>Form Registration</h1>
<form th:action="@{/form/result}" th:object="${student}" method="post">
<div class="form-group">
<label>Student Name</label>
<input class="form-control" type="text" th:field="*{name}" />
<span class="error" th:if="${#fields.hasErrors('name')}" th:errors="*{name}">Name Error</span>
<div class="form-group">
<input class="form-control" type="text" th:field="*{age}" />
<span class="error" th:if="${#fields.hasErrors('age')}" th:errors="*{age}">Age Error</span>
<div class="form-group">
<input class="form-control" type="text" th:field="*{email}" />
<span class="error" th:if="${#fields.hasErrors('email')}" th:errors="*{email}">Email Error</span>
<div class="form-group">
<input class="form-control" type="text" id="datepicker" th:field="*{birthDate}">
<span class=<

Leave a Reply

Your email address will not be published. Required fields are marked *