サーブレットクラスとJSPファイルは
両者ともブラウザからのリクエストを受け付けてページを表示する処理をそれぞれ単独で行えますが
Webアプリケーションを作成する際とくにMVCモデルではどちらか片方だけで完結させずに
両方のメリットを組み合わせる事が一般的です。
本記事の前半ではサーブレットとJSPそれぞれ一方だけでプログラムを実現する例を、
後半ではサーブレットとJSPのそれぞれの良いところを組み合わせて実現する汎用的な例をまとめます。
サーブレットクラス、JSPファイルそれぞれで一方で完結する
リクエストとページの表示をサーブレットクラス、JSPファイルそれぞれで完結する例を確認する。
サーブレットクラスのみ
PrintWriterクラスをインポートし、
getWriterメソッド、printlnメソッドを使用することでHTMLを出力する事が出来る。
@WebServlet("/") public class SampleServlet extends HttpServlet { private static final long serialVersionUID = 1L; protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { Date date = new Date(); SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd"); String today = sdf.format(date); response.setContentType("text/html; charset=UTF-8"); PrintWriter out = response.getWriter(); out.println("<html>"); out.print("<head>"); out.println("<title>TODAY IS</title>"); out.println("</head>"); out.println("<body>"); out.println("<h1>TODAY IS</h1>"); out.println("<p>" + "今日は" + today + "です。</p>"); out.println("</body>"); out.println("</html>"); } }
JSPファイルのみ
JSPファイルはブラウザからのリクエストを受け付けると
アプリケーションサーバによってサーブレットクラスに変換される。
(サーブレットインスタンスを生成する)
JSPファイルからJSPファイルへ、リクエストを送信して受け付けるプログラム
【 index.jsp 】
formから他のjspファイルへ送信する場合、
action属性に指定するのは
/プロジェクト名/WebContentからのパス
となります。
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>Hello Message</title> </head> <body> <p>名前を入力してください。</p> <form action="/example/sample.jsp" method="post"> <input type="text" name="namae"> <button type="submit">送信</button> </form> </body> </html>
【 sample.jsp 】
※パラメーターを取得するためのrequestオブジェクトはjsp内で暗黙的に定義されている
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <% request.setCharacterEncoding("UTF-8"); %> <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>Hello Message</title> </head> <body> <h1>Hello!</h1> <p><%= request.getParameter("namae") %>さん、こんにちは!</p> <div><a href="/example/index.jsp">名前入力に戻る</a></div> </body> </html>
サーブレットとJSPを連携させる
ここからはサーブレットとJSPそれぞれの利点を組み合わせた
Webアプリケーションにおいて推奨される一般的な方法を解説します。
具体的には、ブラウザからのリクエストをサーブレットクラスで受付け、
フォワードの仕組みを利用してJSPファイルでページの表示を行います。
今回は、MVCモデルを用いた簡単な占いプログラムを例に解説します。
【プロジェクトの構成】
【ControllerServlet(コントローラー)】
@WebServlet("/ControllerServlet") public class ControllerServlet extends HttpServlet { private static final long serialVersionUID = 1L; //初回アクセス protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { RequestDispatcher dispatcher = request.getRequestDispatcher("/WEB-INF/index.jsp"); dispatcher.forward(request, response); } //フォーム送信時 protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //文字コードをセット request.setCharacterEncoding("UTF-8"); //占い結果オブジェクトを生成 Fortune fortune = new Fortune(request.getParameter("namae")); request.setAttribute("fortune", fortune);//占い結果オブジェクトをスコープに保存 //結果ページへフォワード RequestDispatcher dispatcher = request.getRequestDispatcher("/WEB-INF/result.jsp"); dispatcher.forward(request, response); } }
【 Fortuneクラス (モデル) 】
ランダムな占いの結果と日付を生成する
public class Fortune { String name =""; String[] luckPattern = {"大吉", "中吉", "吉"}; int index = (int) (Math.random()*3); String luck = luckPattern[index]; Date date = new Date(); SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日"); String today = sdf.format(date); public Fortune(String name) { this.name = name; } public String getName() { return this.name; } public String getLuck() { return this.luck; } public String getToday() { return this.today; } }
【 index.jsp (ビュー) 】
初回アクセス時に、ControllerServletからフォワードされる
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>今日の運勢</title> </head> <body> <h1>今日の運勢</h1> <p>あなたの今日の運勢を占います。<br>名前を入力してください</p> <form action="/fortune_telling/ControllerServlet" method="post"> <input type="text" name="namae"> <button type="submit">占う</button> </form> </body> </html>
【 result.jsp (ビュー) 】
今日の日付と占いの結果を表示する
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <%@ page import="model.Fortune" %> <% Fortune fortune = (Fortune) request.getAttribute("fortune"); %> <!DOCTYPE html> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>今日の運勢</title> </head> <body> <h1>今日の運勢</h1> <p><%= fortune.getName() %>さんの<%= fortune.getToday() %>の運勢は</p> <p><b><%= fortune.getLuck() %></b>です。</p> <a href="/fortune_telling/ControllerServlet">もう一度占う</a> </body> </html>
プロジェクト内のそれぞれファイルの関係性を表すとこのようなイメージになります。
複雑な処理や制御の役割を持つコントローラーは
元がJavaファイルであるサーブレットクラスが担当、
ページを表示させるビューを担当するのはHTMLの出力を得意とするJSPファイルとなり、
フォワードを利用することによって連携を実現します。
一般的なJavaクラスであるFortuneクラスにモデルの役割を持たせ、
ランダムな占い結果と日付の生成を行なっています。
最終的にresult.jspからリクエストスコープへ保存されたFortuneクラスのオブジェクトを参照し、
結果を表示させています。
注意点
・モデルとして役割を持たせるクラスはpublicかつパッケージに所属させる必要があります。
・JSPファイルが直でリクエストされることの無いよう、
ファイルの配置をWebContent直下ではなくWEB-INFディレクトリ以下に配置するようにしておきます。