我正在尝试通过使用JSR-303 bean验证在我的rest控制器上执行一些参数验证。但是,当我用@HystrixCommand注释对方法进行注释时,将忽略所有验证。

例如 :

    @RestController
    @Validated
    public class TestController {

        //This method ignore all validations :(, even if age < 10
        @HystrixCommand(fallbackMethod = "fallback")
        @RequestMapping(value = "/notok", method = RequestMethod.GET)
        ResponseEntity<String> methodNotOk(
                HttpServletRequest request,
                @Min(10) @RequestParam(name = "age") final int age
        ) {
            return ResponseEntity.ok("Age is " + age);
        }

        //This method will raised an error if age < 10, because of the age validation.
        //This is the expected behavior
        @RequestMapping(value = "/ok", method = RequestMethod.GET)
        ResponseEntity<String> methodOk(
                HttpServletRequest request,
                @Min(10) @RequestParam(name = "age") final int age
        ) {
            return ResponseEntity.ok("Age is " + age);
        }

        //Hystrix fallback
        private ResponseEntity<String> fallback(HttpServletRequest request, @RequestParam("age") final int age, Throwable e) {
            return ResponseEntity.badRequest().body("error");
        }

    }


对于methodNotOk,完全忽略了@Min批注,因此服务器可以响应Age is 5,这对于此测试用例是不正确的。

但是,如果我删除@HystrixCommand,一切都会像发条一样。

因此,问题是使用@HystrixCommand时如何验证某些方法参数?

谢谢您的帮助

最佳答案

我有同样的问题,但我在网上找不到任何东西。

我认为原因是方面的加载顺序(在加载Validator之前,HystrixCommandAspect创建了Bean的代理),但是我找不到使用Spring的Java配置更改它的方法。

我的最后一招是使用@HystrixCommand将逻辑移至另一个Bean,然后在Controller中使用委托模式

@RestController
@Validated
public class TestController {

    @Autowired
    private TestHystrixController delegate;

    @RequestMapping(value = "/notok", method = RequestMethod.GET)
    ResponseEntity<String> methodNotOk(HttpServletRequest request,
         @Min(10) @RequestParam(name = "age") final int age) {
        return delegate.methodNotOk(request, age);
    }
}

@Controller
class TestHystrixController {

    @HystrixCommand(fallbackMethod = "fallback")
    ResponseEntity<String> methodNotOk(HttpServletRequest request,
         final int age) {
        return ResponseEntity.ok("Age is " + age);
    }
}

09-05 15:51