jacekn
jacekn

Reputation: 1541

How to display error message from Spring validator?

I've been spending good few hours on this, so it's time to ask.

Controller

@RequestMapping(value="/articleHeaderEdit/{articleId}", method=RequestMethod.POST)
public ModelAndView submitHeader(@PathVariable Integer articleId, @ModelAttribute("screenObject") ArticleHeaderEditScreenObject articleHeaderEditScreenObject, @ModelAttribute("article") Article article, BindingResult bindingResult, Model model, Locale locale) throws Exception {
    validator.validate(articleHeaderEditScreenObject, bindingResult);

    ModelAndView modelAndView=new ModelAndView();

    if(bindingResult.hasErrors()) {
        initializeScreenObject(articleHeaderEditScreenObject, article, locale);
        modelAndView.setViewName(WebView.ARTICLE_HEADER_EDIT_PAGE.getViewName());

    } else {
        modelAndView.setViewName("redirect:/article/" + articleId);
    }

    return modelAndView;
}   

Validator

@Component
public class ArticleHeaderEditScreenObjectValidator implements Validator {
    @Override
    public boolean supports(Class<?> clazz) {
        return ArticleHeaderEditScreenObject.class.isAssignableFrom(clazz); 
}

@Override
public void validate(Object validatedObject, Errors errors) {
    ValidationUtils.rejectIfEmptyOrWhitespace(errors, "title", "required.title", "Title is required.");
}

View (only the relevant html)

<form:form modelAttribute="screenObject" action="${screenObject.getFormAction()}">

    <form:errors path="*" />

    <form:errors />

    <form:input path="title" />
    <form:errors path="title" />

The error is there. I get the right view and I double checked by debugging. None of the three errors tags works, though. When I submit the page, it keeps newly entered data, so model works fine.

I see a lot of people struggling with this. Generally, it's the fact that model attribute has a different name in the form and in the controller but in this case they are the same. Any idea what else is missing?

Upvotes: 0

Views: 3778

Answers (1)

hellojava
hellojava

Reputation: 5064

The secret is in order of the parameters you are passing in to submitHeader method.

Spring documentation clearly specifies that BindingResult bindingResult argument should be written exactly after the model object you want to validate.

So if you are passing in multiple ModelAttributes, the one having the BindingResult after it will have all the errors bind to that object.

So in your case the BindingResult will have errors specific to Article object and not ArticleHeaderEditScreenObject object.

Reference comment from spring documentation:

The Errors or BindingResult parameters have to follow the model object that is being bound immediately as the method signature might have more that one model object and Spring will create a separate BindingResult instance for each of them so the following sample won't work:

http://static.springsource.org/spring/docs/3.1.x/spring-framework-reference/html/mvc.html#d0e29628

Upvotes: 2

Related Questions