I would like to map my servlet to /*
, but it failed with an infinite loop.
<servlet>
<servlet-name>helloServlet</servlet-name>
<servlet-class>my.HelloServlet</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>helloServlet</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
The java code is:
public class HelloServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response){
request.getRequestDispatcher("/WEB-INF/jsps/hello.jsp").forward(request, response);
}
}
If I map to /hello
, everything works fine.
As the HelloServlet
is mapped to /*
, it will also be invoked on RequestDispatcher#forward()
and cause the infinite loop.
How is this caused and how can I solve it?
This is possible duplicate to Servlet Filter going in infinite loop when FORWARD used in mapping in JSF
Otherwise should check what your JSP contains, it could be that it makes request for css or image files that can result in this behaviour. Also would recommend to try without a wildcard.
This is not possible. The JSP should actually invoke container's builtin
JspServlet
. But the/*
mapping definied by the webapp has a higher precedence.You need to map the servlet on a more specific URL pattern like
/pages/*
and create a servlet filter which forwards non-static requests to that servlet. Yes, non-static requests (image/CSS/JS files) are also covered by/*
, but they should not be processed by the servlet at all.Assuming that you've all static resources in
/resources
folder, the following should do:With the following in filter's
doFilter()
:This takes place fully transparently without any change to
/pages
in the URL. The forward to the JSP will not trigger the filter or the servlet. Filters do by default not kick in on forwards and the JSP forward path does not match the controller servlet's URL pattern any more.Alternatively, if you have your own default servlet implementation, then you could map the servlet to
/
and let it delegate to the default servlet if the request isn't applicable as a front controller request. This is what Spring MVC is doing under the covers. Creating a default servlet is however not a trivial task as it should be capable of responding to conditional requests, caching requests, streaming requests, resume requests, directory listing requests, etecetera.See also: