Spring MVC 静态资源的访问

问题描述:  
    我们在spring mvc框架中为了是URL更符合RESTful风格,通常在web.xml中会配置spring框架servlet 的 url 拦截为  "/"  ,也就是拦截所有资源的url请求,这样一来,所有的资源包括, js  | css |  图片  |  所有静态资源都将经过框架的servlet拦截。不应该是这样的。所以有了对应servlet的url拦截为“/”的时候,对静态资源访问不应该经过servlet拦截的问题处理。如果  servlet-mapping  的 url-pattern  为  “*.do”,就是只拦截有一定后缀的url,那么就不会有静态资源访问的问题了。 


一、 spring mvc 下默认访问的三种方式  

1>. 第一种   访问tomcat容器的默认页面  
Xml代码   收藏代码
  1. <welcome-file-list>   
  2.   <welcome-file>/index.html</welcome-file>   
  3. </welcome-file-list>  

这种方式通常用来访问我们的初始页面  
2>. 第二种   spirng mvc 默认index controller 方式  
( 如果在tomcat容器没有配置默认页面,怎spring mvc 会主动去寻找/index的controller,如果有则会调用,没有则会显示404页面
Java代码   收藏代码
  1. @RequestMapping(value="/index")  
  2. public ModelAndView index(HttpServletRequest request, HttpServletResponse response){  
  3.        return new ModelAndView("index");  
  4. }  

3>. 第三种   spirng mvc 配置根节点访问“/”方式  
Java代码   收藏代码
  1. @RequestMapping(value="/")   
  2. public ModelAndView index(HttpServletRequest request,HttpServletResponse response){   
  3.          return new ModelAndView("index");   
  4. }  

或者 
Xml代码   收藏代码
  1. <mvc:view-controller path="/" view-name="home"/>  

This is a shortcut for defining a ParameterizableViewController that immediately forwards to a view when invoked. 

 三种方法 优先级别 是  1>3>2 

二、 spring mvc 使用RESTFull 的url风格拦截所有资源请求时的静态资源的访问配置,避免被spring mvc框架的匹配,因为这是没有必要的,可恶的。  

.如果spring mvc框架的servlet-mapping的url-pattern为 “/”  ,若我们没有处理静态资源,就会造成静态资源的访问出现  404 

解决方案: 
1>. 激活web应用服务器(如Tomcat)的defaultServlet来处理静态文件  
Xml代码   收藏代码
  1. <servlet-mapping>  
  2.     <servlet-name>default</servlet-name>  
  3.     <url-pattern>*.jpg</url-pattern>  
  4. </servlet-mapping>  
  5. <servlet-mapping>  
  6.     <servlet-name>default</servlet-name>  
  7.     <url-pattern>*.js</url-pattern>  
  8. </servlet-mapping>  
  9. <servlet-mapping>  
  10.     <servlet-name>default</servlet-name>  
  11.     <url-pattern>*.css</url-pattern>  
  12. </servlet-mapping>  

要配置多个,每种文件配置一个   
要写在DispatcherServlet的前面, 让defaultServlet先拦截,这个就不会进入Spring了,可能性能是最好的。
 

Tomcat, Jetty, JBoss, and GlassFish   默认 Servlet的名字 -- "default" 
Google App Engine  默认 Servlet的名字 -- "_ah_default" 
Resin  默认 Servlet的名字 -- "resin-file" 
WebLogic  默认 Servlet的名字  -- "FileServlet" 
WebSphere   默认 Servlet的名字 -- "SimpleFileServlet" 

2>. 在spring3.0.4以后版本提供了  <mvc:resources />  
Xml代码   收藏代码
  1. <mvc:resources mapping="/static/**" location="/static/" />  

/static/**映射到 ResourceHttpRequestHandler进行处理,location指定静态资源的位置.可以是web application根目录下、jar包里面,这样可以把静态资源压缩到jar包中。cache-period 可以使得静态资源进行web cache 

如果出现下面的错误,可能是没有配置<mvc:annotation-driven />的原因。 
报错WARNING: No mapping found for HTTP request with URI [/mvc/user/findUser/lisi/770] in DispatcherServlet with name 'springMVC' 

使用<mvc:resources/>元素,把mapping的URI注册到SimpleUrlHandlerMapping的urlMap中, 
key为mapping的URI pattern值,而value为ResourceHttpRequestHandler, 
这样就巧妙的把对静态资源的访问由HandlerMapping转到ResourceHttpRequestHandler处理并返回,所以就支持classpath目录,jar包内静态资源的访问. 
另外需要注意的一点是,不要对SimpleUrlHandlerMapping设置defaultHandler.因为对static uri的defaultHandler就是ResourceHttpRequestHandler, 
否则无法处理static resources request. 

3>. 使用<mvc:default-servlet-handler/>  
Xml代码   收藏代码
  1. <mvc:default-servlet-handler/>  

会把"/**" url,注册到SimpleUrlHandlerMapping的urlMap中,把对静态资源的访问由HandlerMapping转到 org.springframework.web.servlet.resource.DefaultServletHttpRequestHandler 处理并返回. 
DefaultServletHttpRequestHandler使用就是各个Servlet容器自己的默认Servlet. 


补充说明:多个HandlerMapping的执行顺序问题: 
DefaultAnnotationHandlerMapping的order属性值是:0 

<mvc:resources/ >自动注册的 SimpleUrlHandlerMapping的order属性值是: 2147483646 

<mvc:default-servlet-handler/>自动注册的SimpleUrlHandlerMapping的order属性值是:2147483647 

spring会先执行order值比较小的。当访问一个a.jpg图片文件时,先通过DefaultAnnotationHandlerMapping 来找处理器,一定是找不到的,我们没有叫a.jpg的Action。再按order值升序找,由于最后一个SimpleUrlHandlerMapping 是匹配"/**"的,所以一定会匹配上,再响应图片。 

  加载一个静态资源是却要经过框架servlet的层层pattern,不必要的性能开销。  
最后还是特别强调,像一开始说的,如果框架servlet的url-pattern是指定后缀的,如 “*.go” ,那么框架的url拦截就只会匹配后缀带 .go  的request,就不会有静态资源访问的问题了。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值