フィルタを多重に設定する

広告

フィルタは1つだけではなく、複数のフィルタを設定することが出来ます。これによって目的に応じた小さなフィルタを作成し、汎用的なフィルタを作成することが可能になります。

複数のフィルタを1つのサーブレットに対して設定するには単に2つのフィルタを定義するだけです。フィルターはweb.xml内で定義した順番に実行されます。

例として次のような同じURLパターンを対象とするフィルタが2つ定義されていたとします。この場合<filter-mapping>が先に定義されている「filtertest」フィルタがまず実行され、次に「filtertest2」フィルタが実行されます。

<web-app>
  <filter>
    <filter-name>filtertest</filter-name>
    <filter-class>FilterTest</filter-class>
  </filter>

  <filter>
    <filter-name>filtertest2</filter-name>
    <filter-class>FilterTest2</filter-class>
  </filter>

  <filter-mapping>
    <filter-name>filtertest</filter-name>
    <url-pattern>/hello/*</url-pattern>
  </filter-mapping>

  <filter-mapping>
    <filter-name>filtertest2</filter-name>
    <url-pattern>/hello/*</url-pattern>
  </filter-mapping>
</web-app>

次に<filter-mapping>の定義の順番を変更してみます。

<web-app>
  <filter>
    <filter-name>filtertest</filter-name>
    <filter-class>FilterTest</filter-class>
  </filter>

  <filter>
    <filter-name>filtertest2</filter-name>
    <filter-class>FilterTest2</filter-class>
  </filter>

  <filter-mapping>
    <filter-name>filtertest2</filter-name>
    <url-pattern>/hello/*</url-pattern>
  </filter-mapping>

  <filter-mapping>
    <filter-name>filtertest</filter-name>
    <url-pattern>/hello/*</url-pattern>
  </filter-mapping>
</web-app>

この場合は「filtertest2」フィルタが実行されてから「filtertest」フィルタが実行されます。

同じサーブレットが対象になっている場合、<filter>要素が定義された順番ではなく、<filter-mapping>が定義された順番にフィルタは実行されることに注意して下さい。

サンプルプログラム

では簡単なサンプルプログラムでフィルタを試してみましょう。

web.xmlファイルは下記のようにしました。

<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app xmlns="http://java.sun.com/xml/ns/j2ee"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
   http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"
  version="2.4">

  <filter>
    <filter-name>filtertest</filter-name>
    <filter-class>FilterTest</filter-class>
  </filter>

  <filter>
    <filter-name>filtertest2</filter-name>
    <filter-class>FilterTest2</filter-class>
  </filter>

  <filter-mapping>
    <filter-name>filtertest</filter-name>
    <url-pattern>/helloworld</url-pattern>
  </filter-mapping>

  <filter-mapping>
    <filter-name>filtertest2</filter-name>
    <url-pattern>/helloworld</url-pattern>
  </filter-mapping>

  <servlet>
    <servlet-name>helloworld</servlet-name>
    <servlet-class>HelloWorld</servlet-class>
  </servlet>

  <servlet-mapping>
    <servlet-name>helloworld</servlet-name>
    <url-pattern>/helloworld</url-pattern>
  </servlet-mapping>
</web-app>

プログラムは下記の通りです。

HelloWorld.java

import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;

public class HelloWorld extends HttpServlet {
  public void doGet(HttpServletRequest request, HttpServletResponse response)
    throws IOException, ServletException{

    response.setContentType("text/html; charset=Shift_JIS");
    PrintWriter out = response.getWriter();

    System.out.println("HelloWorld");

    out.println("<html>");
    out.println("<head>");
    out.println("<title>フィルタテスト</title>");
    out.println("</head>");
    out.println("<body>");

    out.println("<p>Hello World!</p>");

    out.println("</body>");
    out.println("</html>");
  }
}

FilterTest.java

import java.io.*;
import javax.servlet.*;
import javax.servlet.Filter;
import javax.servlet.FilterChain;

public class FilterTest implements Filter{
  public void doFilter(ServletRequest request, ServletResponse response,
    FilterChain chain){

    try{
      System.out.println("フィルタ実行");

      chain.doFilter(request, response);
    }catch (ServletException se){
    }catch (IOException e){
    }
  }

  public void init(FilterConfig filterConfig) throws ServletException{
  }

  public void destroy(){
  }
}

FilterTest2.java

import java.io.*;
import javax.servlet.*;
import javax.servlet.Filter;
import javax.servlet.FilterChain;

public class FilterTest2 implements Filter{
  public void doFilter(ServletRequest request, ServletResponse response,
    FilterChain chain){

    try{
      System.out.println("フィルタ2実行");

      chain.doFilter(request, response);
    }catch (ServletException se){
    }catch (IOException e){
    }
  }

  public void init(FilterConfig filterConfig) throws ServletException{
  }

  public void destroy(){
  }
}

上記をコンパイル後に「d:¥servlet-sample¥filter¥WEB-INF¥classes¥」ディレクトリにクラスファイルを移動した後で、ブラウザで「http://localhost:8080/filter/helloworld」へアクセスしてみます。

Filterテスト

まず呼び出したサーブレットは普通に実行されています。次にフィルタとして設定したサーブレットが実行されているか確認します。

Filterテスト

呼び出したサーブレットが実際に実行される前に、フィルタとフィルタ2が順に実行されていることが確認できます。

( Written by Tatsuo Ikura )

関連記事 (一部広告含む)