この前調べたのをもとにサンプルを組んで動かしてみました。
アノテーションの表記が若干上手くいかないところがあったがなんとか動きました。
何故かは調べてないのですが動いたから良しとします。(^^;
サンプルコードは下記のとおりです。
素人が組んだコードですので間違い等ございますでしょうがおおらかな心でご覧ください。
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.ejb.AccessTimeout;
import javax.ejb.ConcurrencyManagement;
import javax.ejb.ConcurrencyManagementType;
import javax.ejb.Lock;
import javax.ejb.LockType;
import javax.ejb.Singleton;
/**
*
* @author Yucchi
*/
@ConcurrencyManagement(ConcurrencyManagementType.CONTAINER)
@Singleton
@AccessTimeout(value = 20000)
public class Question {
@AccessTimeout(value = 5000)
@Lock(LockType.READ)
public String getshoulderMessage() {
try {
Thread.sleep(3000);
} catch (InterruptedException ex) {
Logger.getLogger(Question.class.getName()).log(Level.SEVERE, null, ex);
}
return “肩が痛くてたまらん(><)”;
}
@AccessTimeout(value = 19000)
@Lock(LockType.WRITE)
public String getWaistMessage() {
try {
Thread.sleep(15000);
} catch (InterruptedException ex) {
Logger.getLogger(Question.class.getName()).log(Level.SEVERE, null, ex);
}
return “腰が痛くてたまらん(><)”;
}
}
———————————————————————————————————————————————-
import java.io.IOException;
import java.io.PrintWriter;
import javax.ejb.EJB;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
*
* @author Yucchi
*/
@WebServlet(urlPatterns = “/Shoulder”)
public class Shoulder extends HttpServlet {
@EJB
private Question question;
protected void processRequest(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType(“text/html;charset=UTF-8″);
PrintWriter out = response.getWriter();
try {
out.println(“<html>”);
out.println(“<head>”);
out.println(“<title>Servlet Shoulder</title>”);
out.println(“</head>”);
out.println(“<body>”);
out.println(“Servlet Shoulder at ” + request.getContextPath());
out.println(“<br>”);
out.println(question.getshoulderMessage());
out.println(“</body>”);
out.println(“</html>”);
} finally {
out.close();
}
}
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
@Override
public String getServletInfo() {
return “肩の調子はどうだい?”;
}// </editor-fold>
}
————————————————————————————————————————————————-
import java.io.IOException;
import java.io.PrintWriter;
import javax.ejb.EJB;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
*
* @author Yucchi
*/
@WebServlet(urlPatterns = “/Waist”)
public class Waist extends HttpServlet {
@EJB
private Question question;
protected void processRequest(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType(“text/html;charset=UTF-8″);
PrintWriter out = response.getWriter();
try {
out.println(“<html>”);
out.println(“<head>”);
out.println(“<title>Servlet Waist</title>”);
out.println(“</head>”);
out.println(“<body>”);
out.println(“Servlet Waist at ” + request.getContextPath());
out.println(“<br>”);
out.println(question.getWaistMessage());
out.println(“</body>”);
out.println(“</html>”);
} finally {
out.close();
}
}
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
@Override
public String getServletInfo() {
return “腰の調子はどうだい?”;
}// </editor-fold>
}
———————————————————————————————————————————————
<%@page contentType=”text/html”%>
<%@page pageEncoding=”UTF-8″%>
<!DOCTYPE HTML PUBLIC “-//W3C//DTD HTML 4.01 Transitional//EN”
“http://www.w3.org/TR/html4/loose.dtd”>
<html>
<head>
<meta http-equiv=”Content-Type” content=”text/html; charset=UTF-8″>
<title>JSP Page</title>
</head>
<body>
<h1>JSP Page</h1>
<a href=”/ConcurrencyManagementTest/Shoulder” target=”_blank”>肩の調子はどう?</a>
<br>
<br>
<a href=”/ConcurrencyManagementTest/Waist” target=”_blank”>腰の調子はどう?</a>
</body>
</html>
——————————————————————————————————————————————
以上お粗末なサンプルです。
実行結果はこのようになります。
JSP のリンクを「腰の調子はどう?」、「肩の調子はどう?」の順番で開きます。
getWaistMessage() が実行されてる間はロックされ getshoulderMessage() メソッドが実行待ちになります。
しかしタイムアウト設定が働き getshoulderMessage() メソッドは実行されずに終了してしまいます。
getWaistMessage() の処理が終わり Waist サーブレットの処理が完了します。
もし、興味があるようでしたら @Lock アノテーションの属性を変えてみたり、処理時間とタイムアウト設定を変更してグリグリしてみると楽しい結果がまっているでしょう。(たぶん)
私の場合、想像していた動作じゃなくてちょっと焦りました。(勉強不足です。)
やはり、実際に動かして確かめないと解らないことってありますね。
[ 追記 ] ちょっとあまりにも不親切な内容だったので(^^;
ちなみに @Lock(LockType.WRITE) アノテーションのついてるメソッドへのアクセスはただ一つだけ許されます。
よって「腰の調子はどう?」のリンクを複数開いた場合順番に一つずつ処理されていきます。
対して @Lock(LockType.READ) アノテーションのついたメソッドは同時に複数のアクセスを許します。
よって「肩の調子はどう?」のリンクを複数開いた場合順番待ちにならず同時に処理されます。