Should a web framework be a Filter or a Servlet?
Having a web framework handle requests from single point of ent开发者_Python百科ry is a solved problem. However, should that single point of entry be a Filter or a Servlet? Why would a web application developer prefer one over the other? Why would a framework developer prefer one over the other?
Let's look how existing frameworks do it:
- JSF: Servlet
- Spring MVC: Servlet
- Struts/Struts2: Servlet in Struts1, Filter in Struts2
- Wicket: Servlet until 1.2, Filter after 1.3
- Stripes: Filter and Servlet
- Echo: Servlet
- Vaadin: Servlet
That were the most popular frameworks. There are more, but most of them use a Servlet.
Most if not all servlets are supposed to be mapped on a suffix URL pattern, for example *.jsf
(JSF), *.html
(Spring), *.do
(Struts), etc. This enables the developer to easily ignore resources which are not of interest. So the advantage of the Filter of being able to do that disappears. Only Wicket used to have the need to be mapped on an extra path /app/*
and the change of Servlet to Filter in Wicket 1.3 was done with the sole argument that you will be able to map it on just /*
. This however adds extra configuration boilerplate in order to be able to ignore static resources. I personally don't understand why they didn't just use a suffix mapping.
All web frameworks rely on HTTP requests. In a Servlet it's already available straight in the standard methods (often just the service()
method is been used). In a Filter you would need to cast it back (although this is not necessarily expensive).
Also, Sun/Oracle has made a distinct separation between Filters and Servlets on the following grounds: When you want to filter requests/responses on certain conditions, use a Filter. When you want to control requests/responses and/or create responses, use a Servlet.
See also:
- Servlet vs Filter
- Design Patterns web based applications
- How to access static resources when mapping a global front controller servlet on /*
- Difference between / and /* in servlet mapping url pattern
A web application developer should not really care if it is a filter or a servlet. The developer should simply care about how the framework makes their development easier.
Now, I would even take this further to say that a Web framework does not even have to be based on the J2EE spec (as per the Play Framework), in which the rules have been entirely re-written to make web applications easier to develop for a Java programmer.
Filter from personal experience. I came to this conclusion because in the filter I can decide if I need to handle the request. If I don't need to handle it then I can just let the chain do the next filter. In a servlet, if you decide to not continue with the handling then you have to forward which I found didn't work so great.
A Filter is definitely the best choice. A web framework will run as a web application in an application server. The application server will be better for handling some resources, i.e. images and other static files while the web framework should handle calls to dynamic resources. This is easier to achieve if you create a filter that can forward all requests for static resources to the application server (or another filter).
Check this benchmark. You will find Play!framework (Netty based) + Japid template engine is nearly close to static content hosting (even with concurrent user increased).
精彩评论