この記事は3年以上前に書かれた記事です。情報が古い可能性があります。
Struts の全てのバージョン、及び Struts 2.3 系 までのバージョンは脆弱性が報告されており、その使用は非推奨となっています。
Struts2 で action の処理の前後に別の処理を割り込ませることのできる仕組み、インターセプタ(Interceptor)を使ってみる。
struts.xml 設定
基本的なインタセプタを定義。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
<package name="app-default" extends="struts-default">
<!-- インタセプタ以外の設定いろいろ ここから -->
<!-- インタセプタ以外の設定いろいろ ここまで -->
<!-- デフォルトインタセプタの設定 ここから -->
<interceptors>
<interceptor-stack name="defaultInterceptorsStack">
<!-- 不要なインタセプタは消しておくこと -->
<interceptor-ref name="exception" />
<interceptor-ref name="systemExceptionHandleInterceptor" />
<interceptor-ref name="logicalExceptionHandlingInterceptor" />
<interceptor-ref name="alias" />
<interceptor-ref name="servletConfig" />
<interceptor-ref name="i18n" />
<interceptor-ref name="chain" />
<interceptor-ref name="debugging" />
<interceptor-ref name="profiling" />
<interceptor-ref name="modelDriven" />
<interceptor-ref name="fileUpload" />
<interceptor-ref name="checkbox" />
<interceptor-ref name="staticParams" />
<interceptor-ref name="defaultParametersInterceptor">
<param name="excludeParams">dojo\..*</param>
</interceptor-ref>
<interceptor-ref name="validation">
<param name="excludeMethods">
input,back,cancel,browse
</param>
<param name="validateAnnotatedMethodOnly">
false
</param>
</interceptor-ref>
<interceptor-ref name="validatorFailureFollowInterceptor" />
<interceptor-ref name="workflow">
<param name="excludeMethods">
input,back,cancel,browse
</param>
</interceptor-ref>
</interceptor-stack>
</interceptors>
<!-- デフォルトインタセプタの設定 ここまで -->
<!-- デフォルトのインタセプタスタックを定義 -->
<default-interceptor-ref name="defaultInterceptorsStack" />
</package>
</struts>
インタセプタのクラスを作成
com.opensymphony.xwork2.interceptor.Interceptor を implements したクラスをつくる。
package foo;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.ActionSupport;
import com.opensymphony.xwork2.interceptor.Interceptor;
@SuppressWarnings("serial")
public class BeforeInterceptor implements Interceptor {
/**
* 初期化。
*/
public void init() {
// 特に処理は不要。
}
/**
* 終了。
*/
public void destroy() {
// 特に処理は不要。
}
/**
* 割り込み処理を実装。
*/
public String intercept(ActionInvocation invocation) throws Exception {
// ここにアクション前後に割り込ませたい処理を書く。
return invocation.invoke();
}
}
インタセプタのアクションを定義
アクションの前後に割り込ませたいインタセプタを定義。 インタセプタというのは、要は、Webで呼び出されるアクションの前後に必ず追従して呼び出される別のアクションと考えれば良い。ので、定義の仕方もアクションと同じ。
この定義は struts.xml に書いても良いけど、ここは別ファイルに定義して include することにする。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
<package name="foo" namespace="/foo" extends="app-default">
<interceptors>
<!-- カスタムインタセプタの定義 -->
<interceptor name="beforeInterceptor"
class="BeforeInterceptor" />
<!-- 呼び出しスタックの定義 -->
<interceptor-stack name="fooStack">
<!-- 以下に書いた順番で呼び出されていく -->
<interceptor-ref name="beforeInterceptor"/>
<interceptor-ref name="defaultInterceptorsStack" />
</interceptor-stack>
</interceptors>
<!-- アクションの定義 -->
<action name="loginHogeAction" method="login" class="hogeAction">
<!-- ここにアクションの処理前に割り込ませたいスタックを指定 -->
<interceptor-ref name="fooStack"/>
<!-- アクションの設定 -->
<result name="input" >/WEB-INF/foo/login.vm</result>
<result name="success" >/WEB-INF/foo/loginOk.vm</result>
<!-- ここにアクションの処理後に割り込ませたいスタックを指定 -->
</action>
</package>
</struts>
このファイルを struts.xml に include しておく。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
...
<include file="/foo.xml" />
...
</struts>
これでインタセプタの処理がアクションの前(後)に必ず実行されるようになる。