6. フィルタ
- 6.1. フィルタとは
- 6.2. フィルタの作成
- 6.3. フィルタの設定
- 6.4. フィルタの機能の拡張
6.1. フィルタとは
「フィルタ」とはクライアントからのリクエストおよびレスポンスに対して、リソース(サーブレット/JSP/HTMLなど)での処理の前および後に何らかの処理を行うオブジェクトの事です。リクエストのパラメータ値を変更したり、ログの出力を行ったり様々なものが考えられます。
フィルタの機構が追加されたのは、サーブレット2.3からです。それまでにもフィルタの機構はベンダー独自に組み込まれていたのですが、バージョン2.3からはサーブレット標準の機能となりました。これによりベンダーに依存しないフィルタ機構を実現する事ができます。
6.2. フィルタの作成
フィルタは「javax.servlet.Filter」インタフェースを実装して作成します。このインタフェースで定義されているメソッドは3つで、それぞれが呼び出されるタイミングおよび処理内容は以下の通りです。
init(javax.servlet.FilterConfig) |
フィルタが初めて使用されるときに呼び出されます。「FilterConfig」は主にフィルタの初期設定値を読み出すために使用します。 |
doFilter(javax.servlet.ServletRequest, javax.servlet.ServletResponse, javax.servlet.FilterChain) |
フィルタの対象となるリソースが呼び出されたときに実行されます。「FilterChain」は次のフィルタやリクエストの対象であるJSPページやサーブレットの処理を実行するのに使用されます。 |
destroy() |
フィルタが破棄されるときに呼び出されます。何らかの後処理が必要な場合に実装します。 |
以下はリクエストの文字コードを指定するフィルタです。文字コードを初期設定値から読み出して指定しています。
import javax.servlet.Filter; import javax.servlet.FilterConfig; import javax.servlet.FilterChain; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import javax.servlet.ServletException; import java.io.IOException; public final class EncodingFilter implements Filter{ private String encoding=null; public void init(FilterConfig config) throws ServletException{ encoding=config.getInitParameter("encoding"); } public void doFilter(ServletRequest request,ServletResponse response,FilterChain chain) throws ServletException,IOException{ request.setCharacterEncoding(encoding); chain.doFilter(request,response); } public void destroy(){ encoding=null; } }
12行目、FilterConfigの「getInitParameter」で初期設定値を読み出しています。設定の行い方は次節で説明します。15〜19行目の「doFilter」メソッド内でリクエストの文字コードを指定しています(17行目)。18行目で次のフィルタ(当該フィルタが最後のフィルタの場合は、リクエストの対象のリソース)が呼び出されます。
レスポンスに対して処理を行う事も可能です。以下のフィルタはページの最後に訪問者数を表示しています。訪問者数の管理には「ServletContext」を利用しています。ServletContextにおいても、「getAttribute」「setAttribute」メソッドでオブジェクトの登録が行えます。登録されたオブジェクトはWebアプリケーション全体で共有されます。
public final class CounterFilter implements Filter{ private ServletContext context=null; public void init(FilterConfig config) throws ServletException{ context=config.getServletContext(); context.setAttribute("counter", new Integer(1); } public void doFilter(ServletRequest request,ServletResponse response,FilterChain chain) throws ServletException,IOException{ chain.doFilter(request,response); Integer counter=(Integer)context.getAttribute("counter"); PrintWriter writer=((HttpServletResponse)response).getWriter(); writer.println(counter.intValue()); context.setAttribute("counter", new Integer(counter.intValue()+1)); } public void destroy(){ context=null; } }
FilterChainのdoFilterメソッドによって一連の処理が実行されるので、これより前で処理を行うか後ろで処理を行うかで、クライアントからの要求と応答のどちら側でフィルタリングを行うか決定する事ができます。