できること †
- CDI のメソッドの前処理、後処理を記述する
- 構成
- Interceptor 本体
- Interceptor を組み込むメソッドを指定するための Annotation
- beans.xml
- Interceptor を適用するメソッド
WithHello?.java Interceptor を組み込むメソッドを指定するための Annotation †
package com.mycompany.cdiexam;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import javax.interceptor.InterceptorBinding;
@InterceptorBinding
@Target(value={ElementType.METHOD,ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
public @interface WithHello{
}
HelloInterceptor?.java †
package com.mycompany.cdiexam;
import java.io.Serializable;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import javax.interceptor.AroundInvoke;
import javax.interceptor.Interceptor;
import javax.interceptor.InvocationContext;
@WithHello
@Interceptor
public class HelloInterceptor implements Serializable {
@AroundInvoke
public Object arountInvoke(InvocationContext ic) throws Exception {
DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
try {
// 前処理
String start = df.format(new Date());
// 主処理 (本来呼ばれるはずだったもの)
Object result = ic.proceed();
// 後処理
String end = df.format(new Date());
return "開始:" + start + "<br/>" + result + " </br>終了:" + end;
} catch (Exception e) {
System.out.println("例外が発生。仕方ないね。");
throw e;
}
}
}
- @WithHello? が指定されているメソッドに対して、この Interceptor を適用する
beans.xml †
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
bean-discovery-mode="annotated">
<!--
CDI の Bean は、bean.xml に登録する必要なし。
JEE6 では空の bean.xml が必要。
JEE7 では bean.xml 自体必要なし
-->
<interceptors>
<!-- JEE7 でも Interceptor は、bean.xml に登録する必要あり -->
<class>com.mycompany.cdiexam.HelloInterceptor</class>
</interceptors>
</beans>
HelloCDI.java Interceptor を適用するメソッド †
package com.mycompany.cdiexam;
import java.io.Serializable;
import javax.enterprise.context.SessionScoped;
@SessionScoped
public class HelloCDI implements Serializable {
private int called = 0;
@WithHello
public String hello(String name) {
return "Hello " + name + ".(" + (++called) + " times called)";
}
}
実行結果 †
package com.mycompany.cdiexam;
import java.io.IOException;
import java.io.PrintWriter;
import javax.inject.Inject;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@WebServlet(name = "HelloServlet", urlPatterns = {"/HelloServlet"})
public class HelloServlet extends HttpServlet {
@Inject
private HelloCDI helloCdi;
protected void processRequest(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=UTF-8");
PrintWriter out = response.getWriter();
try {
/* TODO output your page here. You may use following sample code. */
out.println("<!DOCTYPE html>");
out.println("<html>");
out.println("<head>");
out.println("<title>Servlet HelloServlet</title>");
out.println("</head>");
out.println("<body>");
out.println("<h1>" + helloCdi.hello("Az") + "</h1>");
out.println("</body>");
out.println("</html>");
} finally {
out.close();
}
}
// doGet() doPost() 略
}
- Interceptor が適用されて、主処理の実行の前後に時刻が出力されている
Java#Glassfish