部署描述符是JavaEE程序常見的一部分,但是之前都沒有較為全面的學習過,這里就較為全面的記錄一下部署描述符中的元素。部署一個Servlet 3 或以上應用程序是一件輕而易舉的事。通過Servlet注解,對於不太復雜的應用程序,甚至可以部署沒有描述符的Servlet/JSP應用程序。但是需要更加精細配置或是我們不能修改框架源碼的情況,仍然需要部署描述符。首先,部署描述符必須命名為web.xml並位於WEB-INF目錄下。Java類編譯后class文件和配置文件都會放置在WEB-INF/classes目錄下,而Java類庫都放在WEB-INF/lib目錄下,所有的應用程序資源打包成war為后綴的jar文件,這個war中包含WEB-INF(web.xml, classes,lib),頁面資源。
在存在如下場景,部署描述符不能少:
- 需要傳遞全局初始化參數給ServletContext
- 有多個過濾器,並要設置調用順序
- 需要修改會話超時設置
- 需要限制資源的訪問,並配置用戶身份驗證方式
先來看看web.xml的頭部聲明:
<?xml version="1.0" encoding="UTF-8"?> <web-app
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://java.sun.com/xml/ns/javaee"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_1.xsd" version="3.1"> [metadata-complete="true|false"] ... </web-app>
xsi:schemaLocation 屬性指定了元素文檔的位置,以便可以進行驗證。version屬性指定了Servlet規范的版本。
可選的metadata-complete屬性指定部署描述符是否是完整的,若值為True,則Servlet/JSP容器將忽略Servlet注解。若值為False或不存在該值,則容器必須檢查類文件的Servlet注解
web-app元素是文檔的根元素,並且可以包含的如下子元素:
- Servlet聲明和映射
- ServletContext的初始化參數
- 會話配置
- 監聽器類
- 過濾器聲明和映射
- MIME類型映射
- 歡迎頁面列表
- 錯誤頁面
- JSP特定的設置
- JNDI設置
核心元素
在web-app的子元素可以以任何順序出現。但某些元素,如session-config,jsp-config和login-config只能出現一次,而另一些元素,如Servlet,filter,welcome-file-list可以出現多次
context-param
context-param元素作為全局初始化參數配置,可以傳值給ServletContext。這些值可以被任何Servlet/JSP頁面讀取。context-param元素由名稱/值構成,並可以通過調用ServletContext的getInitParameter方法來讀取。可以定義多個context-param元素,每個參數名在本應用中必須唯一。ServletContext.getInitParameterNames()方法會返回所有的參數名稱。
每一個context-param元素必須包含一個param-name元素和一個param-value元素。param-name定義參數名,而param-value定義參數值。另外還有一個可選的元素,即description元素,可用來描述參數。
<context-param> <param-name>location</param-name> <param-value>localhost</param-value> </context-param> <context-param> <param-name>port</param-name> <param-value>8080</param-value> <description>The port number userd</description> </context-param>
distributable
若定義了distributable元素,則表明應用程序已部署到分布式的Servlet/JSP容器。distributable元素屬性為空:
<distributable/>
error-page
error-page元素包含一個HTTP錯誤代碼與資源路徑或Java異常類型與資源路徑之間的映射關系。error-page元素定義容器在特定的HTTP錯誤或異常時應返回的資源路徑。
error-page元素由以下成分構成:
- error-code,指定一個HTTP錯誤代碼
- exception-type,指定Java的異常類型(全路徑名稱)
- location,指定要被顯示的資源位置。該元素必須以“/”開始
<error-page> <error-code>404</error-code> <location>/error.html</location> </error-page> <error-page> <exception-type>javax.servlet.ServletException</exception-type> <location>/exception.html</location> </error-page>
當出現HTTP404時,會顯示位於應用程序目錄下的error.html頁面。發生ServletException會顯示exception.html頁面。
filter
filter指定一個Servlet的過濾器。該元素至少包括一個filter-name元素和一個filter-class元素。此外,它還可以包含以下元素:icon,display-name,discription,init-param以及async-supported。
filter-name元素定義了過濾器的名稱。過濾器名稱必須全局唯一。filter-class元素指定過濾器類的全路徑名稱。可由init-param元素來配置過濾器的初始化參數(類似於<context-param>),一個過濾器可以配置多個init-param。
<filter> <filter-name>UpperCaseFilter</filter-name> <filter-class>cn.lynu.filter.UpperCaseFilter</filter-class> </filter> <filter> <filter-name>IamgeFilter</filter-name> <filter-class>cn.lynu.filter.ImageFilter</filter-class> <init-param> <param-name>frequency</param-name> <param-value>2018</param-value> </init-param> <init-param> <param-name>resolution</param-name> <param-value>1024</param-value> </init-param> </filter>
filter-mapping
過濾器映射元素時指定過濾器要被映射到的一個或多個資源。過濾器可以被映射到Servlet或者URL模式。過濾器映射元素中包含一個filter-name元素和一個url-pattern元素或者servlet-name元素。filter-name元素的值必須與filter元素聲明的某一個過濾器名稱相匹配。
<filter> <filter-name>LoggingFilter</filter-name> <filter-class>cn.lynu.filter.LoggingFilter</filter-class> </filter> <filter> <filter-name>SecondFilter</filter-name> <filter-class>cn.lynu.filter.SecondFilter</filter-class> </filter> <filter-mapping> <filter-name>LoggingFilter</filter-name> <servlet-name>FirstServlet</servlet-name> </filter-mapping> <filter-mapping> <filter-name>SecondFilter</filter-name> <servlet-name>/*</servlet-name> </filter-mapping>
第一個過濾器分別用於映射到一個Servlet上,第二個filter用於過濾所有請求
listener
listener元素用於注冊一個監聽器。其子元素listener-class包含監聽器類的全路徑名
<listener> <listener-class>cn.lynu.listener.AppListener</filter-class> </listener>
Servlet
Servlet元素當然是用於配置Servlet,包括如下子元素:
- 一個可選的icon元素
- 一個可選的description元素
- 可選的display-name元素
- 一個servlet-name元素
- 一個servlet-class元素或一個jsp-file元素
- 零個或更多的init-param元素
- 一個可選的load-on-startup元素
- 可選的run-as元素
- 可選的enabled元素
- 可選的async-supported元素
- 可選的multipart-config元素
- 零個或多個security-role-ref元素
一個Servlet元素至少必須包含一個servlet-name元素和一個servlet-class元素。或者一個servlet-name元素和一個jsp-file元素
servlet-name元素定義的Servlet名稱在應用程序中必須是唯一的
servlet-class元素指定的類名為全路徑名
jsp-file元素指定JSP頁面的路徑,該路徑時應用程序的相對路徑,必須以“/”開始
init-param的子元素可以用來傳遞一個初始化參數給Servlet。init-param結構同context-param
可以使用load-on-startup元素在當Servlet/JSP容器啟動的時候自動加載Servlet。加載一個Servlet是指實例化Servlet和調用它的init方法。默認情況下,在第一次訪問Servlet的時候才開始加載。load-on-startup可以指定一個整數值來指定加載順序。多個Servlet都包含一個load-on-startup元素,則數值小的優先加載。如果兩個Servlet具有相同的load-on-startup,則加載的順序不能確定。
run-as用於覆蓋調用EJB的安全標識。角色名是當前Web應用程序定義的安全角色之一
enabled元素也是一個可選的元素。它的值可以是True或False。設置子元素為False,則可以禁用這個Servlet
Servlet-mapping
Servlet-mapping元素將一個Servlet映射到一個URL模式。該元素必須有一個servlet-name元素和url-pattern元素
<servlet> <servlet-name>springDispatcherServlet</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <!--使用默認配置 --> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>springDispatcherServlet</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping>
locale-encoding-mapping-list和locale-encoding-mapping
locale-encoding-mapping-list元素包含一個或多個locale-encoding-mapping元素。每個locale-encoding-mapping定義了locale以及編碼的映射,分別用locale以及encoding元素定義。locale元素的值必須在ISO639中定義的與語言編碼,如zh。或者采用“語言編碼_國家編碼”格式,如zh_CN。其中,國家編碼的值必須在ISO3166中定義。
<locale-encoding-mapping-list> <locale-encoding-mapping> <locale>zh_CN</locale> <encoding>UTF-8</encoding> </locale-encoding-mapping> </locale-encoding-mapping-list>
login-config
login-config元素包括auth-method,realm-name以及form-login-config元素,每個元素都是可選的。
auth-method元素定義了認證方式,可選值為BASIC,DIGEST,FORM和CLIENT-CERT
realm-name元素定義用於BASIC以及DIGEST認證方式的realm名稱
form-login-config則定義了用於FORM認證方式的登錄頁面和失敗頁面。如果沒有采用FORM認證方式,則該元素被忽略。
form-login-config元素包括form-login-page和form-error-page兩個子元素。form-login-page配置了顯示登錄頁面的資源路徑,路徑為應用程序的相對路徑,其必須以“/”開始。form-error-page則配置了失敗時顯示錯誤頁面的資源路徑,同樣為相對於應用目錄的,必須以“/”開始。
下面是一個實例:
<login-config> <auth-method>DIGEST</auth-method> <realm-name>Members Only</realm-name> </login-config>
另一個實例如下:
<login-config> <auth-method>FORM</auth-method> <form-login-config> <form-login-page>/loginForm.jsp</form-login-page> <form-error-page>/errorPage.jsp</form-error-page> </form-login-config> </login-config>
mime-mapping
mime-mapping元素用來把一個MIME類型映射到一個擴展名。該元素由一個extension元素和一個mime-type元素組成
<mime-mapping> <extension>text</extension> <mime-type>text/plain</mime-type> </mime-mappfing>
session-config
session-config元素定義了javax.servlet.http.HttpSession實例的參數。此元素可以包括一個或多個以下內容:session-timeout,cookie-config或tracking-mode。
- session-timeout元素指定會話超時間隔(分鍾),session默認是30分鍾過時。該值必須為整數,如果該值為零或負數,這會話將永不超時
- cookie-config元素定義了會話創建的cookie配置
- tracking-mode元素定義了跟蹤會話模式。其有效值是COOKIE,URL或SSL
<session-config> <session-timeout>12</session-timeout> </session-config>
welcome-file-list
welcome-file-list元素指定當前用戶在瀏覽器中輸入URL沒有指定頁面時,顯示的默認的Servlet名或JSP頁面或靜態頁面。welcome-file-list元素包含與一個或多個welcome-file元素。welcome-file元素包含默認的文件名,如果在第一個welcome-file元素知道那個的文件沒有找到,則Web容器將嘗試顯示第二個,直到最后一個。
<welcome-file-list> <welcome-file>login.jsp</welcome-file> <welcome-file>login.html</welcome-file> </welcome-file-list>
我們也可以將一個Servlet作為歡迎頁
<welcome-file-list> <welcome-file>login.jsp</welcome-file> <welcome-file>servlet/welcome</welcome-file> </welcome-file-list>
jsp-property-group
jsp-property-group中的元素可為一組JSP文件配置屬性,使用這個元素可以做到一下幾點:
- 指示是否忽略EL
- 指示是否忽視Java腳本
- 指明頁面的編碼方式
jsp-property-group可以有如下子元素:
- 一個或多個url-pattern元素
- 一個可選的el-ignored元素
- 一個可選的page-encoding元素
- 一個可選的scripting-invalid元素
url-pattern元素用來指定應用相對屬性配置的URL模式
el-ignored元素值為true或false.true表示在匹配的JSP頁面中忽略使用EL,該值默認是False
page-encoding元素指定JSP頁面的編碼方式,和頁面的pageEncoding的有效值是一樣的。如果page-encoding元素與匹配的JSP中的pageEncoding屬性值不同時,則會產生一個轉換時錯誤
scripting-invalid元素值為True或False。True值是指URl模式的JSP頁面不再支持<% Java 腳本%>語法,默認值是False.
所有的JSP頁面不執行EL表達式:
<jsp-config> <jsp-property-group> <url-pattern>*.jsp</url-pattern> <el-ignored>true</el-ignored> </jsp-property-group> </jsp-config>
所有的JSP頁面不支持<% scripting%>語法:
<jsp-config> <jsp-property-group> <url-pattern>*.jsp</url-pattern> <scripting-invalid>true</scripting-invalid> </jsp-property-group> </jsp-config>