1. 程式人生 > >springmvc訪問靜態資源,以及相對路徑,絕對路徑問題.

springmvc訪問靜態資源,以及相對路徑,絕對路徑問題.

一般情況下,在web工程裡,css js png jpg 這類資原始檔,由瀏覽器發起請求,由 tomcat、jetty、nginx 這類程序直接接管,類似於 jfinal、Struts、spring mvc 框架都不會去幹預.


而 WEB-INF 目錄下面由於有 jar 包、配置檔案等需要被保護的檔案,所以 tomcat、jetty 這類 java web 容器天然禁止對 WEB-INF 之下一切資源的訪問

因此, css、js 這類檔案生來就不應該被放在 WEB-INF 之下,這個是由很久以前的 java web 規範決定的

如果一定要放在 WEB-INF 之下,需要新增 Filter 接管這類資源的請求,然後象 tomcat、jetty 一樣將這類資源的內容自行載入並響應給客戶端

靜態資原始檔應該都在webapp目錄下,目錄結構如下:

假如有需要把靜態資源出於安全之類的原因放在了WEB-INF目錄下,那麼springmvc應該首先做如下配置:

    <!--靜態資源訪問  -->
    <mvc:default-servlet-handler/>
    <!--把符合/js/**匹配規則的請求,對映到目錄/WEB-INF/js/下-->
    <mvc:resources mapping="/js/**" location="WEB-INF/js/"/>
    <!--<mvc:resources mapping="/img/**" location="WEB-INF/img/"/>
--> <mvc:resources mapping="/css/**" location="WEB-INF/css/"/> <!--<mvc:resources mapping="/commons/**" location="WEB-INF/commons"/>--> <!--<mvc:resources mapping="/upload/**" location="WEB-INF/upload/"/>--> <!-- 配置ViewResolver檢視解析器 --> <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"
> <!--這裡配置的目的是,把controller返回的邏輯檢視名,加入字首/WEB-INF/jsp/,加入字尾.jsp.例如controller 返回的是邏輯檢視名為test,則會被拼接為/WEB-INF/jsp/test.jsp --> <property name="prefix" value="/WEB-INF/jsp/"/> <property name="suffix" value=".jsp"/> </bean>

然後在前端頁面中呼叫靜態資源.

在呼叫靜態資源的時候,會涉及到路徑問題,相對路徑和絕對路徑.

一般情況下最好用絕對路徑 <%=basePath%>/js/jquery.js
其中basePath是下面的值
<%
 String path = request.getContextPath();
 String basePath = request.getScheme() + "://"
  + request.getServerName() + ":" + request.getServerPort()
  + path + "/";
%>

為什麼要這麼做?因為從靜態的jsp路徑來看它和js的路徑相對關係是../js/,但是往往很多時候我們不是直接訪問jsp頁面的,是通過其他的jsp頁面或者servlet,或者struts的action通過forward的方式轉發過來訪問的,這時候請求的當前路徑就不是該jsp的路徑,而是轉發過來之前那個jsp,servlet或action的路徑,所以和js的相對路徑關係就可能不再是../js/了,而在實際使用中,訪問同一個jsp可能由很多不同的來源,那麼它的相對路徑關係可能隨時都可能改變,這時候jsp頁面裡寫死的相對路徑就無法訪問到對應的資源了。所以要使用絕對路徑訪問。

例如:
假如我們要訪問這個頁面,http://localhost:8080/web/jsp/abc.jsp
abc.jsp的相對路徑是http://localhost:8080/web/jsp/,abc.jsp裡引用了../js/jquery.js,這時候直接訪問abc.jsp是沒有問題的。
但如果由以下三個請求轉發到abc.jsp來訪問
1. http://localhost:8080/web/business/test/test.jsp  
相對路徑是http://localhost:8080/web/business/test/,訪問js需要使用../../js/jquery.js
2. http://localhost:8080/web/struts/action/test.action
相對路徑是http://localhost:8080/web/struts/test/,(?)訪問js需要使用../../js/jquery.js

相對路徑是http://localhost:8080/web/struts/action/ 
3. http://localhost:8080/web/servlet
相對路徑是http://localhost:8080/web/,訪問js需要使用js/jquery.js

這時候abc.jsp裡的../js/jquery.js的死路徑就不能正確訪問到js了。


===========================================

而真正的相對於web工程的絕對路徑寫法是:/ 代表url根路徑,例如http://localhost:8080/web/js/jquery.js裡的http://localhost:8080/,而./代表web工程根路徑http://localhost:8080/web/
所以你還可以這麼寫:
1. /web/js/jquery.js
2. ./js/jquery.js