I'm a Spring newbie.
I set up validation in my domain class like this:
public class Worker {
@NotNull(message="Name must be input")
@Size(min=1,max=50, message="Name must not exceed 50 characters")
private String name;
...
}
Here's the jsp file:
<form:input path="code" readonly="false" />
<font color="red"><form:errors path="code" />
And the controller code:
@RequestMapping(value="/test",method=RequestMethod.POST)
public void form(开发者_运维问答@Valid Worker worker, BindingResult result) {
if (result.hasErrors()) {
return;
}
...
It works, but how can I replace "Name must not exceed 50 characters" with some text (like worker.name.overflow) in my messageSource? May I need to add a messageResolver into BindingResult?
All the search result seems to say about writing a custom Validator class, but I want to use annotation for now. I'm pretty sure there's a way, because in this question someone has done that.
To tell Hibernate validator to do a lookup on a code, put the value of message in braces, e.g., @NotNull(message="{worker.name.NotNull}"
, then put the translation in ValidationMessages.properties in the root of your classpath (/WEB-INF/classes, resources folder in Maven, etc.).
The validator implementation looks those up independently on its own, and they go on the BindingResult already translated as the default message. Happens outside of the Spring messagesource. You could in theory override the LocalValidatorFactory bean to put the validator's message output onto the Errors object as the code and then leave the braces off in the annotation so that the Hibernate Validator passes it through. The source code that turns JSR-303 ConstraintViolations into Spring Errors is simple enough to read and extend. It just puts the name of the annotation on as code, the annotation properties as args, and then the validator's translation as the default message. You can read the implementation here.
You can add a javax.validation.MessageInterpolator
to your javax.validation.Configuration
to tell it to look for messages in other properties files. If you're using the Spring LocalValidatorFactory bean, it has a setMessageInterpolator()
on it that you can use to inject one. Check this source for the Hiberate provider implementation.
This is a bit explanation of problem.
@Size(min = 1, max = 50, message = "Email size should be between 1 and 50")
Now remove { message = "Email size should be between 1 and 50" } from validation tag.
After doing this your annotation will be like this.
@Size(min = 1, max = 50)
Now at controller side debug the method which is being called upon when submitting the form. Below is my method which is receiving the request when user hits submit.
public static ModelAndView processCustomerLoginRequest(IUserService userService, LoginForm loginForm,
HttpServletRequest request, HttpSession session, BindingResult result, String viewType, Map<String, LoginForm> model)
Now place a debug point at very first line of the method and debug the argument "result".
BindingResult result
While dubugging you will find a string like this in codes array.
Size.loginForm.loginId
Now define this string in your properties file and a message against that string. Compile and execute. That message will be displayed whenever that annotation wouldn't be validated.
Size.loginForm.loginId=email shouldn't be empty.
Basically spring makes its own string as key to its property file message. In above key
Size(@Size) = validation annotation name
loginForm = My Class Name
loginId = Property name in LoginForm class.
精彩评论