No busques más por internet porque llegaste al lugar indicado, tenemos la respuesta que deseas pero sin liarte.
Solución:
Spring MVC configura de hecho un controlador de excepciones para usted.
Por defecto, DefaultHandlerExceptionResolver
se utiliza como se indica en la clase javadoc:
Implementación predeterminada del
HandlerExceptionResolver
interfaz que resuelve las excepciones estándar de Spring y las traduce a los códigos de estado HTTP correspondientes.Este solucionador de excepciones está habilitado de forma predeterminada en el Spring común
org.springframework.web.servlet.DispatcherServlet
.
Eso es correcto para los controladores MVC.
Pero para los controladores de excepciones para controladores REST (su requisito aquí), Spring confía en el ResponseEntityExceptionHandler
clase.
La primera clase tiene métodos que regresan. ModelAndView
s mientras que la segunda clase tiene métodos que devuelven ReponseEntity
s.
Puede definir un controlador de excepciones personalizado anotando su clase con @ControllerAdvice
en ambos casos (controladores MVC y REST) pero como su requisito es para controladores REST, centrémonos en eso.
Además de anotar un controlador de excepciones personalizado con @ControllerAdvice
, también puede hacer eso para extender una clase de controlador de excepciones base como ResponseEntityExceptionHandler
para anular algunos comportamientos.ResponseEntityExceptionHandler
implementaciones permite conocer todas las excepciones realmente manejadas y mapeadas. Mira el handleException()
método que es el método de fachada de la ResponseEntityExceptionHandler
clase :
/**
* Provides handling for standard Spring MVC exceptions.
* @param ex the target exception
* @param request the current request
*/
@ExceptionHandler(
HttpRequestMethodNotSupportedException.class,
HttpMediaTypeNotSupportedException.class,
HttpMediaTypeNotAcceptableException.class,
MissingPathVariableException.class,
MissingServletRequestParameterException.class,
ServletRequestBindingException.class,
ConversionNotSupportedException.class,
TypeMismatchException.class,
HttpMessageNotReadableException.class,
HttpMessageNotWritableException.class,
MethodArgumentNotValidException.class,
MissingServletRequestPartException.class,
BindException.class,
NoHandlerFoundException.class,
AsyncRequestTimeoutException.class
)
@Nullable
public final ResponseEntity
Entonces, la pregunta es: ¿cómo anular el controlador de excepciones para una excepción específica?
Este enfoque no puede funcionar:
@ExceptionHandler(value = HttpRequestMethodNotSupportedException.class )
protected ResponseEntity
Porque dentro de la clase del controlador de excepciones, Spring no le permite definir más de una vez un mapeo para un Exception
subclase. Por lo tanto, no se permite agregar este mapeo en su controlador de excepciones personalizado porque Spring ya define un mapeo para esa excepción en el ResponseEntityExceptionHandler
clase.
Concretamente, evitará que el contenedor Spring se inicie con éxito.
Debería obtener una excepción como:
Caused by: java.lang.IllegalStateException: Ambiguous @ExceptionHandler method mapped for [class org.springframework.web.HttpRequestMethodNotSupportedException]: {protected org.springframework...
Para facilitar que las subclases de clientes anulen el manejo / mapeo real para una excepción específica, Spring implementó la lógica de cada excepción capturada y manejada por sí misma en un protected
método de El ResponseEntityExceptionHandler
clase.
Entonces, en su caso (anulando el controlador de HttpRequestMethodNotSupportedException
), solo anular handleHttpRequestMethodNotSupported()
eso es lo que buscas:
if (ex instanceof HttpRequestMethodNotSupportedException)
HttpStatus status = HttpStatus.METHOD_NOT_ALLOWED;
return handleHttpRequestMethodNotSupported((HttpRequestMethodNotSupportedException) ex, headers, status, request);
Por ejemplo de esta manera:
@ControllerAdvice
public class MyExceptionHandler extends ResponseEntityExceptionHandler
@Override
protected ResponseEntity
Recuerda que te damos el privilegio agregar una reseña si hallaste tu duda a tiempo.