J'écris une application Web avec Spring 4.0.4 et Spring Boot 1.0.2 utilisant Tomcat comme conteneur Web intégré et je veux implémenter une gestion globale des exceptions qui intercepte toutes les exceptions et les enregistre d'une manière spécifique. Mes exigences simples sont:
Jusqu'à présent, ma solution ressemble à ceci (simplifié, pas de journalisation et pas de redirection vers une vue d'erreur):
@Controller
@RequestMapping("/errors")
public class ErrorHandler implements EmbeddedServletContainerCustomizer
{
@Override
public void customize(final ConfigurableEmbeddedServletContainer factory)
{
factory.addErrorPages(new ErrorPage("/errors/unexpected"));
factory.addErrorPages(new ErrorPage(HttpStatus.NOT_FOUND, "/errors/notfound"));
}
@RequestMapping("unexpected")
@ResponseBody
public String unexpectedError(final HttpServletRequest request)
{
return "Exception: " + request.getAttribute("javax.servlet.error.exception");
}
@RequestMapping("notfound")
@ResponseBody
public String notFound()
{
return "Error 404";
}
}
Le résultat est que les exceptions levées dans les contrôleurs sont correctement gérées par la méthode unexpectedError
et les codes d'état 404 sont gérés par la méthode notFound
. Jusqu'ici tout va bien, mais j'ai les problèmes suivants:
javax.servlet.error.exception
. Et ce n'est même pas l'exception levée, c'est une instance de org.springframework.web.util.NestedServletException
et je dois plonger dans cette exception imbriquée pour récupérer la vraie. Je suis sûr qu'il existe un moyen plus simple, mais je ne le trouve pas.Alors, comment puis-je résoudre ces problèmes? Ou peut-être que la façon dont j'ai implémenté ce gestionnaire d'exceptions global est complètement erronée et qu'il existe une meilleure alternative?
Jetez un œil à ControllerAdvice Vous pouvez faire quelque chose comme ceci:
@ControllerAdvice
public class ExceptionHandlerController {
public static final String DEFAULT_ERROR_VIEW = "error";
@ExceptionHandler(value = {Exception.class, RuntimeException.class})
public ModelAndView defaultErrorHandler(HttpServletRequest request, Exception e) {
ModelAndView mav = new ModelAndView(DEFAULT_ERROR_VIEW);
mav.addObject("datetime", new Date());
mav.addObject("exception", e);
mav.addObject("url", request.getRequestURL());
return mav;
}
}