10

In Jersey 2 it is possible to do this:

@GET
@PATH("user/{email}")
public IDto getUser(@NotNull @Email @PathParam("email") String validEmail) {
    return userManagementService.findUserByEmail(validEmail);
}

But I cannot make something similar to work in Spring MVC, it seems that the validation is only done when providing an object in @RequestBody or using an SpringMVC Form, for example the following won't work:

@RequestMapping(value="/user/{email}", method = RequestMethod.GET)
public @ResponseBody IDto getUser(@NotNull @Email @PathVariable String validEmail) {
    return userManagementService.findUserByEmail(validEmail);
}   

There are other similar questions, but those seem to be oriented to Spring MVC UI applications, in my case it is only a REST API which returns JSON response so I don't have any View to map/bind to the controller.

raspacorp
  • 5,037
  • 11
  • 39
  • 51
  • You minimally need to annotate with `@Valid`, though this might only work if you have a model class and not just a `String`. – beerbajay Jul 05 '14 at 10:09
  • Yes, the question is about simple parameters not about POJO objects as input, for that I know about the @Valid annotation that will use the bean validation from the annotations in the class. But that is not the feature I am asking for – raspacorp Jul 11 '14 at 16:09

5 Answers5

8

Seems it is possible, using @Validated.

Here's an example.

Based on OP's question, this should work:

@RestController
@Validated
public class MyController {

  @GetMapping(value="/user/{email}")
  public @ResponseBody IDto getUser(@NotNull @Email @PathVariable String validEmail) {
    return userManagementService.findUserByEmail(validEmail);
  }
 
}

In plain Spring implementations, it may be required to manually register the validator bean:

@Bean
public MethodValidationPostProcessor methodValidationPostProcessor() {
    return new MethodValidationPostProcessor();
}
Dormouse
  • 1,617
  • 1
  • 23
  • 33
4

1- Simply add @Validated annotation at the top of your class. 2- Put whatever annotations for validations (@NotBlank, Min(1), etc.) before the @RequestParam annotation in your method signature.

Hani
  • 753
  • 8
  • 10
2

Controller should be annotated with spring's @Validated

So update your code with

@Validated
@RequestMapping(value="/user/{email}", method = RequestMethod.GET)
public @ResponseBody IDto getUser(
    @NotNull 
    @Email 
    @PathVariable String validEmail) {
    return userManagementService.findUserByEmail(validEmail);
}
mahfuj asif
  • 1,691
  • 1
  • 11
  • 32
2

The validated annotation from the org.springframework.validation.annotation.Validated package to validate a @PathVariable. Make sure the class annotated with @Validated.

@GetMapping("/name-for-day/{dayOfWeek}")
  public String getNameOfDay(@PathVariable("dayOfWeek") @Min(1) @Max(7) Integer dayOfWeek) {
        return dayOfWeek + "";
}
fabfas
  • 2,200
  • 1
  • 21
  • 21
1

As far as I can tell, you cannot do this out-of-the-box with Spring.

Options:

  1. Use a regular expression:

    @RequestMapping(value="/user/{email:SOME_REXEXP}", method = RequestMethod.GET)
    public @ResponseBody IDto getUser(@PathVariable String validEmail) {
        return userManagementService.findUserByEmail(validEmail);
    }   
    
  2. Use Hibernate Validator to validate the method. Either call the validator manually, or make Spring call it for you using AOP. See https://github.com/gunnarmorling/methodvalidation-integration

Neil McGuigan
  • 46,580
  • 12
  • 123
  • 152