Filter 過濾器是 JavaWeb 的三大組件之一。(Servlet、Filter、Listener)html
Filter 過濾器它是 JavaEE 的規範,能夠在瀏覽器以及目標資源之間起到一個過濾的做用,它的做用是:攔截請求,過濾響應。java
web 中的過濾器:當訪問服務器的資源時,過濾器能夠將請求攔截下來,完成一些特殊的功能。mysql
攔截請求常見的應用場景有:web
① 登陸驗證;sql
② 權限檢查;瀏覽器
③ 事務管理;服務器
④ 統一編碼處理;app
⑤ 敏感字符等等異步
① web.xml 配置jsp
格式:
1 <!--filter 標籤用於配置一個 Filter 過濾器-->
2 <filter>
3 <!--給 filter 起一個別名-->
4 <filter-name>AdminFilter</filter-name>
5 <!--配置 filter 的全類名-->
6 <filter-class>com.atguigu.filter.AdminFilter</filter-class>
7 </filter>
8 <!--filter-mapping 配置 Filter 過濾器的攔截路徑-->
9 <filter-mapping>
10 <!--filter-name 表示當前的攔截路徑給哪一個 filter 使用-->
11 <filter-name>AdminFilter</filter-name>
12 <!-- url-pattern 配置攔截路徑,能夠有多個攔截路徑 13 / 表示請求地址爲: http://ip:port/工程路徑/ 映射到 IDEA 的 web 目錄
14 /admin/* 表示請求地址爲: http://ip:port/工程路徑/admin/* 15 --> 16 <url-pattern>/admin/*</url-pattern> 17 <url-pattern>/client/*</url-pattern> 18 </filter-mapping>
② 註解方式配置
在類上添加 @WebFilter() 便可,裏面填寫訪問所要攔截的資源的路徑。
1 import javax.servlet.*; 2 import javax.servlet.annotation.WebFilter; 3 import java.io.IOException; 4
5 @WebFilter("/*") 6 public class FirstFilter implements Filter { 7 public void destroy() { 8 } 9 // doFilter 方法,專門用於攔截請求,過濾響應
10 public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException { 11 System.out.println("filterDemo1被執行了...."); 12 // 放行操做
13 chain.doFilter(req, resp); 14 } 15
16 public void init(FilterConfig config) throws ServletException { 17
18 } 19
20 }
執行時機:在 web 工程啓動的時候執行(Filter 會建立)
執行時機:在 web 工程啓動的時候,構造方法執行完,馬上執行 init 方法,作一些初始化的操做
執行時機:每次訪問目標資源時都會調用,每次攔截到請求,就會執行(執行屢次);
執行時機:中止 web 工程的時候,就會執行(中止 web 工程,也會銷燬 Filter 過濾器),用來釋放資源
Filter 是一個接口,給咱們提供了下面三個方法
Filter 接口,實現 Filter 須要實現該接口。
(1)init() 方法用於初始化 Filter;
(2)doFilter() 是過濾請求和響應的主要方法;
(3)destory() 用於在 Filter 對象被銷燬前作收尾工做,如是否資源等;
FilterConfig 類是 Filter 過濾器的配置文件類。
Tomcat 每次建立 Filter 的時候,也會同時建立一個 FilterConfig 類,這裏麪包含了 Filter 配置文件的配置信息。
FilterConfig 對象在服務器調用 init() 方法時傳遞進行。
FilterConfig 類的做用是獲取 filter 過濾器的配置內容:
getFilterName():獲取 Filter 的名稱 filter-name 的內容;
getSerletContext():獲取ServletContext 對象(即 application)
getInitParameter():獲取在 Filter 中配置的 init-param 初始化參數;
getInitParameterNames():獲取全部初始化參數的名字;
Demo:
1 web.xml 的配置: 2 <!--filter 標籤用於配置一個 Filter 過濾器-->
3 <filter>
4 <!--給 filter 起一個別名-->
5 <filter-name>AdminFilter</filter-name>
6 <!--配置 filter 的全類名--><filter-class>com.atguigu.filter.AdminFilter</filter-class>
7 <init-param>
8 <param-name>username</param-name>
9 <param-value>root</param-value>
10 </init-param>
11 <init-param>
12 <param-name>url</param-name>
13 <param-value>jdbc:mysql://localhost3306/test</param-value>
14 </init-param>
15 </filter>
16
17 Filter 代碼: 18 public void init(FilterConfig filterConfig) throws ServletException { 19
20 // 一、 獲取 Filter 的名稱 filter-name 的內容
21 System.out.println("filter-name 的值是: " + filterConfig.getFilterName()); 22
23 // 二、 獲取在 web.xml 中配置的 init-param 初始化參數
24 System.out.println("初始化參數 username 的值是: " + filterConfig.getInitParameter("username")); 25 System.out.println("初始化參數 url 的值是: " + filterConfig.getInitParameter("url")); 26
27 // 三、 獲取 ServletContext 對象
28 System.out.println(filterConfig.getServletContext()); 29 }
FilterChain 對象是在 doFilter() 方法被調用時做爲參數傳遞進來的。
doFilter() 方法用於調用 Filter 鏈上的下一個過濾器,若是當前過濾器爲最後一個,過濾器則將請求發送到目標資源。
FilterChain 過濾器鏈(多個過濾器如何一塊兒工做)
① 過濾器1前置代碼
② 過濾器2前置代碼
③ 資源執行 doFilter()
④ 過濾器2 後置代碼
⑤ 過濾器1 後置代碼
① 註解配置:
規則:按照類名的字符串比較規則比較,值小的先執行。
如: AFilter 和 BFilter,AFilter就先執行了。
② web.xml 配置:
規則: 按照 <filter-mapping> 的順序決定的,若是定義的位置越靠前,越先被調用;
① 全部 Filter 和目標資源默認都執行在同一個線程中;
② 多個 Filter 共同執行的時候,它們都是使用同一個 Request 對象;
執行流程圖:
目標資源指的是須要調用 Filter 來進行過濾處理的資源。主要有如下幾種配置方式:
經過 <filter-mapping> 下的 url-pattern 來配置
格式:
<url-pattern>/target.jsp</url-pattern>
以上配置的路徑,表示請求地址必須爲:http://ip:port/工程路徑/target.jsp
精確匹配只要在請求地址徹底同樣時纔會調用 Filter
路徑匹配只要是所請求的資源在設置的路徑下就會調用 Filter
格式:
<url-pattern>/admin/*</url-pattern>
以上配置的路徑,表示請求地址必須爲:http://ip:port/工程路徑/admin/*
後綴匹配只要訪問的資源路徑是以指定後綴結尾就會調用 Filter
格式:
<url-pattern>*.html</url-pattern>
以上配置的路徑, 表示請求地址必須以.html 結尾纔會攔截到
<url-pattern>*.do</url-pattern>
以上配置的路徑, 表示請求地址必須以.do 結尾纔會攔截到
<url-pattern>*.action</url-pattern>
以上配置的路徑, 表示請求地址必須以.action 結尾纔會攔截到
注意:Filter 過濾器它只關心請求的地址是否匹配,不關心請求的資源是否存在!
經過 filter-mapping 中的 servlet-name 來指定過濾的 Servlet
在 Filter 的 filter-mapping 中增長了一個 servlet-name 標籤,這個標籤的值是其中某一個 servlet 的名字,在訪問 Servlet 時就會調用該過濾器請求。
如圖:
(1)執行過濾器
(2)執行要放行的資源
(3)回來執行過濾器放行代碼下面的代碼
(1)init 方法:在服務器啓動後,會建立Filter對象,而後調用init方法。只執行一次,通常用於加載資源。
(2)doFilter 方法:每一次請求被攔截資源時,會執行。執行屢次
(3)destory 方法:在服務器關閉後,Filter對象被銷燬。若是服務器是正常關閉,則會執行destroy方法。只執行一次,通常用於釋放資源。
(1)攔截路徑配置
1. 具體資源路徑: /index.jsp 只有訪問index.jsp資源時,過濾器纔會被執行
2. 攔截目錄: /admin/* 訪問/user下的全部資源時,過濾器都會被執行
3. 後綴名攔截: *.jsp 訪問全部後綴名爲jsp資源時,過濾器都會被執行
4. 攔截全部資源: /* 訪問全部資源時,過濾器都會被執行
(2)攔截方式配置:資源被訪問的方式
在 filter-mapping 還有一個子標籤 dispatcher,該標籤用來指定須要 Filter 處理的請求類型,該標籤能夠配置四個值
配置:
設置 dispatcherTypes 屬性
屬性名 | 解釋 |
REQUEST | 默認值。瀏覽器直接請求資源 |
FORWARD | 轉發訪問資源時調用 Filter |
INCLUDE | 動態包含訪問資源時調用Filter |
ERROR | 錯誤跳轉資源 |
ASYNC | 異步訪問資源 |
web.xml 配置:
設置 <dispatcher></dispatcher>標籤,在裏面填入上面的值便可。
以上四種狀況能夠設置一個,也能夠同時設置多個,若是不設置默認是 Request。