Validation of Request Models using OVal

OVal is a validation framework which works by annotating beans with constraints.
Code reference:

POM dependency


Annotations in Bean

There are various annotations provided by OVal which sit under net.sf.oval.constraint package. Below are standard @NotNull and @NotEmpty constraints added to Book model.

public class Book implements Serializable {

    @Id @JsonIgnore
    private String id;
    @NotNull @NotEmpty
    private String title;
    @NotNull @NotEmpty
    private String author;
    private YearMonth publishedYear;
    private List<String> categories;
    @NotNull @NotEmpty
    private String publisher;
    private long isbnCode;

Validating Bean

Validating bean is as simple as creating a net.sf.oval.Validator object and calling its validate method. This method returns a list of ConstraintViolation which encapsulates all the data related to validation failures.

Book book = ...
net.sf.oval.Validator validator = new Validator();
List<ConstraintViolation> violations = validator.validate(book);

How to use in Spring Boot

Since Validator is thread safe, let’s create a bean for it from a configuration class and autowire it in our controllers. So first line of all controllers would be to validate the incoming model.

package org.gluecoders.library.config;

import net.sf.oval.Validator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

public class Oval {

    public Validator validator(){
        return new Validator();


Below is the controller class using the Validator instance.

@RequestMapping(produces = MediaType.APPLICATION_JSON_UTF8_VALUE, path = "/books")
public class Books {

    private final static Logger LOGGER = LoggerFactory.getLogger(Books.class);

    private BookService bookService;

    private Validator validator;
public ResponseEntity<Book> addBook(@RequestBody Book book) {
   List<ConstraintViolation> violations = validator.validate(book);
   if(!violations.isEmpty()) {"violations {} for request payload {}", violations, book);
      return new ResponseEntity<>(HttpStatus.BAD_REQUEST);
   }"addBook invoked for Book {}", book);
   book = bookService.addBook(book);
   return new ResponseEntity<>(book, HttpStatus.CREATED);

Now if validation fails for received request, then controller will return a 400 Bad Request response.

Let’s also add a test case for BadRequest in BooksTest that was created in REST introduction.

public void addBook_MissingParams() throws Exception {
   String bookContent = mapper.writeValueAsString(incompleteBook);
   verify(bookService, never()).addBook(incompleteBook);

Here an incompleteBook(some parameters are null) is send in request, and it is expected that 400 response will be returned.

Prev      TOC      Next