Spring MVC - Using multiple HandlerExceptionResolvers together

[Last Updated: Jan 25, 2017]

We can use multiple HandlerExceptionResolver at a time by using HandlerExceptionResolverComposite.


Following method of HandlerExceptionResolverComposite can be used to specify multiple HandlerExceptionResolvers:

public void setExceptionResolvers(List<HandlerExceptionResolver> exceptionResolvers)

In resolveException(...) method, this resolver loops through the provided list of resolvers. The first one to return a ModelAndView instance wins. Otherwise null is returned. Here's the snippet:

public class HandlerExceptionResolverComposite implements HandlerExceptionResolver, Ordered {

 private List<HandlerExceptionResolver> resolvers;
 public void setExceptionResolvers(List<HandlerExceptionResolver> exceptionResolvers) {
		this.resolvers = exceptionResolvers;
  public ModelAndView resolveException(HttpServletRequest request,
            HttpServletResponse response,
            Object handler,
            Exception ex) {
   if (resolvers != null) {
    for (HandlerExceptionResolver handlerExceptionResolver : resolvers) {
       ModelAndView mav = handlerExceptionResolver.resolveException(request, response, handler, ex);
       if (mav != null) {
        return mav;
   return null;

Note that, if any of the the provided HandlerExceptionResolver, implements Ordered interface, then the order returned from Ordered#getOrder is not used to sort the provided resolvers. The resolvers are iterated in list's insertion order. So what is the use of Ordered#getOrder()? It is actually used in the DispatcherServlet to iterate through the default and registered exception resolvers. (in the next tutorial we will look into that with an example).

In following example we are going to set two HandlerExceptionResolvers with HandlerExceptionResolverComposite, one from our last tutorial example which is a custom resolver and other will be SimpleMappingExceptionResolver.


Registering HandlerExceptionResolvers in JavaConfig class

public class AppConfig {

    HandlerExceptionResolver exceptionResolverComposite () {
        //the custom resolver from last example
        HandlerExceptionToViewResolver r = new HandlerExceptionToViewResolver();

        SimpleMappingExceptionResolver s = new SimpleMappingExceptionResolver();
        Properties p = new Properties();
        p.setProperty(IllegalAccessException.class.getName(), "simple-test-error-view");

        HandlerExceptionResolverComposite c = new HandlerExceptionResolverComposite();
        c.setExceptionResolvers(Arrays.asList(r, s));
        return c;

The Controller

public class ExampleController {

    //should be handled by our custom resolver because of @ErrorView
    @ErrorView(value = "test-error-view", status = HttpStatus.GONE)
    public String handleRequest () throws Exception {
        throw new Exception("test exception 1");

    //should be handled by handleException() because of @ExceptionHandler.
    //Default resolvers are processed before application registered ones
    public String handleRequest2 () throws Exception {
        throw new OperationNotSupportedException("test exception 2");

    //should be handled by SimpleMappingExceptionResolver's default view
    public String handleRequest3 () throws Exception {
        throw new Exception("test exception 3");

    //should be handled by SimpleMappingExceptionResolver:
    //IllegalAccessException is mapped to 'test-error-view'
    public String handleRequest4 () throws Exception {
        throw new IllegalAccessException("test exception 4");

    //should be handled by our custom resolver even though IllegalAccessException
    //is mapped in SimpleMappingExceptionResolver. Reasons is: in iteration order
    // our custom resolver is first to process
    @ErrorView(value = "test-error-view", status = HttpStatus.FORBIDDEN)
    public String handleRequest5 () throws Exception {
        throw new IllegalAccessException("test exception 5");

    public String handleException (OperationNotSupportedException e) {
        return "exception :" + e.toString();

JSP pages

<%@ page language="java"
    contentType="text/html; charset=ISO-8859-1"

<h3>Test Error View</h3>
 <p>Request Uri: <b>${requestUri}</b></p>
 <p>Exception: <b>${exception['class'].name}</b></p>
 <p>Message: <b>${exception.message}</b></p>
 <p>Response status: <b>${statusValue} (${statusStr})</b></p>

<%@ page language="java"
    contentType="text/html; charset=ISO-8859-1"

<h3>Simple Test Error View</h3>
 <p>Exception: <b>${exception['class'].name}</b></p>
 <p>Message: <b>${exception.message}</b></p>
<%@ page language="java"
    contentType="text/html; charset=ISO-8859-1"

<h3>This is the default exception page</h3>
 <p>Exception: <b>${exception['class'].name}</b></p>
 <p>Message: <b>${exception.message}</b></p>

Run embedded tomcat

mvn tomcat7:run-war







Example Project

Dependencies and Technologies Used:

  • spring-webmvc 4.3.5.RELEASE: Spring Web MVC.
  • javax.servlet-api 3.0.1 Java Servlet API
  • JDK 1.8
  • Maven 3.3.9

Handler Exception Resolver Composite Select All Download
  • handler-exception-resolver-composite
    • src
      • main
        • java
          • com
            • logicbig
              • example
          • webapp
            • WEB-INF
              • views

    See Also