首先需要明确几容易混淆的规则:
-
servlet容器中的匹配规则是特定的规则。不要用通配符或正则表达式的匹配规则来看待servlet的url-pattern。
-
Servlet 2.5开始,一个servlet可以使用多个url-pattern规则,<servlet-mapping>标签声明了与该servlet相应的匹配规则,每个<url-pattern>标签代表1个匹配规则;
-
当servlet容器接收到浏览器发出的一个url请求后,容器会用url减去当前应用的上下文路径,以剩余的字符串作为servlet映射,假如url是http://localhost:8080/app/index.html,其应用上下文是app,容器会将http://localhost:8080/appDemo去掉,用剩下的/index.html部分拿来做servlet的映射匹配
-
url-pattern映射匹配过程是有优先顺序的
-
而且当有一个servlet匹配成功以后,就不会去理会剩下的servlet了。
缺省匹配
<servlet-mapping>
<servlet-name>MyServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
匹配顺序
-
精确匹配
servlet-mapping1:<url-pattern>/ab/aa.html</url-pattern>,
servlet-mapping2:<url-pattern>/*</url-pattern>。
当一个请求http://localhost:8080/app/ab/aa.html 来的时候,servlet-mapping1匹配到,不再用servlet-mapping2匹配
-
路径匹配,先最长路径匹配,再最短路径匹配
servlet-mapping1:<url-pattern>/ab/*</url-pattern>,
servlet-mapping2:<url-pattern>/*</url-pattern>。
当一个请求http://localhost:8080/app/ab/aa.html来的时候,servlet-mapping1匹配到,不再用servlet-mapping2匹配
-
扩展名匹配
servlet-mapping1:<url-pattern>/ab/*</url-pattern>,
servlet-mapping2:<url-pattern>*.action</url-pattern>。
当一个请求http://localhost:8080/app/ab/aa.action来的时候,servlet-mapping1匹配到,不再用servlet-mapping2匹配
-
缺省匹配,以上都找不到servlet,就用默认的servlet,配置为<url-pattern>/</url-pattern>
<url-pattern>/*</url-pattern>
/* 会覆盖掉其他所有的servlet,包括servlet容器提供的,例如default servlet 和 the JSP servlet。因为除去精确匹配,优先级排第二的就是路径匹配,它的优先级要比扩展名匹配和缺省匹配优先级高。一般/*只在过滤器中使用。
<url-pattern>/</url-pattern>
最后匹配
/ 不会覆盖其他的servlet。仅仅会取代servlet容器内置的缺省servlet,它通常会触发静态资源和目录,例如CSS/JS/image/ 等文件。servlet容器内置的缺省servlet同时能够处理HTTP缓存请求,媒体文件流(音频、视频)、和文件下载摘要。通常,你最好不要重写内置缺省的servlet,如果要覆盖重写,你必须实现上面列出的任务。这个模式是最后匹配的,jsp文件都是属于扩展名匹配,优先级高于这个缺省匹配。