您的位置:首页 > 编程语言 > Java开发

Spring MVC的配置访问静态资源的三种方案

2017-10-07 15:38 351 查看
原文链接1:http://blog.csdn.net/geeloong/article/details/72476688

原文链接2:http://blog.csdn.net/sjjsh2/article/details/53100728

方案一:激活Tomcat的defaultServlet来处理静态文件

copy

<servlet-mapping>     

    <servlet-name>default</servlet-name>    

    <url-pattern>*.jpg</url-pattern>       

</servlet-mapping>      

<servlet-mapping>         

    <servlet-name>default</servlet-name>      

    <url-pattern>*.js</url-pattern>      

</servlet-mapping>      

<servlet-mapping>          

    <servlet-name>default</servlet-name>         

    <url-pattern>*.css</url-pattern>        

</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" 

方案二: 在spring3.0.4以后版本提供了mvc:resources 
mvc:resources 的使用方法:

<!-- 对静态资源文件的访问 -->      

<mvc:resources mapping="/images/**" location="/images/" /> 
 

 

mapping:映射到ResourceHttpRequestHandler进行处理  

location:指定静态资源的位置.可以是web application根目录下、jar包里,这样可以把静态资源压缩到jar包中  

cache-period:可以使得静态资源进行web cache cop




如果出现下面的错误,可能是没有配置<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.

方案三 ,使用<mvc:default-servlet-handler/>



<mvc:default-servlet-handler/>  

       '/' 将会替换掉容器的default servlet, 将会处理所有其他handler(Servlet)都不处理的访问请求.如果web.xml没有配置其他特殊路径的servlet, 基本上所有的请求都交由DispatcherServlet处理. 将不会再访问容器中原始默认的servlet(静态资源的访问就是通过容器默认servlet处理的),故而静态资源将不可访问!!


       default-servlet-handler将在SpringMVC上下文中定义一个DefaultServletHttpRequestHandler,它会对进入DispatcherServlet的请求进行筛查。如果发现是没有经过映射的请求,就将该请求交由WEB应用服务器默认的Servlet进行处理。如果不是静态资源的请求,才由DispatcherServlet继续进行处理。

新的问题出现了,你会发现以前的Controller不能访问了!!!

那么为什么会出现这个情况?

default-servlet-handler将在SpringMVC上下文中定义一个DefaultServletHttpRequestHandler。

DefaultServletHttpRequestHandlerj的avadoc如下:

/*使用servlet容器的默认servlet处理静态资源*/

 * An {@link HttpRequestHandler} for serving static files using the Servlet container's "default" Servlet.

 /*当DispatcherServlet url-pattern为 ‘/’时,该handler将会使用‘/*’去匹配请求路径;因此,重置了servlet容器对静态资源的默认处理*/

 * <p>This handler is intended to be used with a "/*" mapping when the

 * {@link org.springframework.web.servlet.DispatcherServlet DispatcherServlet}

 * is mapped to "/", thus  overriding the Servlet container's default handling of static resources.

/*匹配该handler的mapping 应该是最后到达,当没有其他mapping可以处理请求时才会执行该handler匹配的mapping。*/

 * The mapping to this handler should generally be ordered as the last in the chain so that it will

 * only execute when no other more specific mappings (i.e., to controllers) can be matched.

即,当DispatcherServlet url-pattern为 ‘/’时,该handler将会使用‘/*’去匹配请求路径。

参考servlet的url-pattern规则可知 ‘/*’可以拦截一切请求。因为’/’将servlet定义为默认serlvet,在没有精确匹配servlet出现前,’/*'将拥有最高的优先级!!

这是很严重的,/*可以拦截路径和资源型的请求,并转发到默认的serlvet!!!

也就是说,静态资源此时可以由默认default servlet进行处理,但是default servlet不能处理你的业务请求(mapping)!!

所以,需要保证该handler对应的handler mapping在执行顺序中为最后!!!

解决办法:就是再加上 

<mvc:annotation-driven
/>

/ 和 /* 之间的区别:

 <url-pattern>/</url-pattern>:将servlet定义为容器默认servlet,当没有其他servlet能够处理当前请求时,由该servlet进行处理。

 <url-pattern>/*</url-pattern>:会匹配所有url - 路径型的和后缀型的url(包括/login , *.jsp , *.js 和 *.html 等)
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  spring mvc