Java Can';t手例外
我使用Spring并在annotation@ControllerAdvice的帮助下创建了用于处理所有异常的类Java Can';t手例外,java,spring,exception,exception-handling,Java,Spring,Exception,Exception Handling,我使用Spring并在annotation@ControllerAdvice的帮助下创建了用于处理所有异常的类 @EnableWebMvc @ControllerAdvice class RestResponseEntityExceptionHandler extends ResponseEntityExceptionHandler { private final MessageSource messages; private RestResponseEntityE
@EnableWebMvc
@ControllerAdvice
class RestResponseEntityExceptionHandler extends ResponseEntityExceptionHandler {
private final MessageSource messages;
private RestResponseEntityExceptionHandler(@Qualifier("messageSource") MessageSource messages) {
this.messages = messages;
}
@ExceptionHandler({ESInvalidValueException.class})
public ResponseEntity<Object> handleValidation(final RuntimeException ex, final WebRequest request) {
log.error("400 Status Code: " + ex.getMessage());
Locale locale = LocaleContextHolder.getLocale();
final GenericResponse body = GenericResponse.error(
messages.getMessage("portNotValid", null, locale), 400);
return handleExceptionInternal(ex, body, new HttpHeaders(), HttpStatus.BAD_REQUEST, request);
}
}
然后我尝试在控制器中的注释@Valid的帮助下验证端口号。
下面是我的验证类:
@Log4j2
@Component
public class ESRequestDTOValidator implements Validator{
@Override
public boolean supports(Class<?> clazz) {
return ElasticSearchLogRequest.class.isAssignableFrom(clazz);
}
@Override
public void validate(Object target, Errors errors) {
log.debug("Validating: {}", target);
ElasticSearchLogRequest form = (ElasticSearchLogRequest) target;
validatePort(form);
}
private void validatePort(ElasticSearchLogRequest form) {
String reg = "^((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})" +
"|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{0,5})|([0-9]{1,4}))$";
if (!form.getPort().toString().matches(reg)) {
throw new ESInvalidValueException("portNotValid", HTTP_BAD_REQUEST);
}
}
}
@Log4j2
@组成部分
公共类ESRequestDTOValidator实现验证器{
@凌驾
公共布尔支持(类clazz){
返回ElasticSearchLogRequest.class.isAssignableFrom(clazz);
}
@凌驾
公共无效验证(对象目标、错误){
调试(“验证:{}”,目标);
ElasticSearchLogRequest表单=(ElasticSearchLogRequest)目标;
验证端口(表格);
}
专用void validatePort(ElasticSearchLogRequest表单){
String reg=“^((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})”+
"|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{0,5})|([0-9]{1,4}))$";
如果(!form.getPort().toString()匹配(reg)){
抛出新的ESInvalidValueException(“portNotValid”,HTTP\u BAD\u请求);
}
}
}
问题是:
messages.getMessage()
找不到代码为“portNotValid”的消息。在exceptionESInvalidValueException
中,我希望传递不同的消息以验证其他字段,在handleValidation()
方法中,我希望根据消息处理所有这些异常。我怎样才能完成这样的任务?也许还有另一个办法。这是无法实现的。检查这个答案
在您的例子中,bean位于CGLIB代理之后。它创建了一个子类
由于该方法具有final修饰符,因此无法更改
原始ResponseEntityExceptionHandler类对的行为
向后面的bean插入一个调用-请检查我关于
CGLIB
CGLIB代理是一个不同的对象,它将方法调用委托给
原来的豆子
请注意,不可能实现Spring的大部分功能
仅具有子类化的功能,即不分离
物体。当单例作用域bean引用
会话范围bean-显然有许多会话范围bean和
只有一个单例作用域bean
您可以尝试使用一些私有方法来实现这一点,而不是使用Springbean
@Log4j2
@Component
public class ESRequestDTOValidator implements Validator{
@Override
public boolean supports(Class<?> clazz) {
return ElasticSearchLogRequest.class.isAssignableFrom(clazz);
}
@Override
public void validate(Object target, Errors errors) {
log.debug("Validating: {}", target);
ElasticSearchLogRequest form = (ElasticSearchLogRequest) target;
validatePort(form);
}
private void validatePort(ElasticSearchLogRequest form) {
String reg = "^((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})" +
"|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{0,5})|([0-9]{1,4}))$";
if (!form.getPort().toString().matches(reg)) {
throw new ESInvalidValueException("portNotValid", HTTP_BAD_REQUEST);
}
}
}