
サーブレット&JSPの基本|ひとこと広場のログイン機能を作成する
入力された利用者情報をサーブレットで受け取り、セッションスコープに保存する。ひとこと広場のログイン機能を作ろう
前回の記事では、ひとこと広場の全体像を確認し、開発準備として動的WebプロジェクトHiroba、User.java、ShortMessage.java、index.jspを作成しました。
今回の記事では、いよいよログイン機能を作成します。
ログイン機能は、Webアプリケーションでよく使われる基本的な機能です。利用者がトップ画面で利用者名とパスワードを入力し、ログインボタンをクリックすると、その情報がサーブレットへ送信されます。
サーブレットでは、送信された利用者名とパスワードを受け取り、Userインスタンスを作成します。その後、ログイン処理を行うモデルに判定を依頼します。
今回の学習用アプリケーションでは、パスワードが1234であればログイン成功とします。利用者名は自由に入力できます。
ログインに成功した場合は、Userインスタンスをセッションスコープに保存します。セッションスコープに保存しておくことで、次の画面でもログイン中の利用者情報を利用できます。
ログイン結果画面では、セッションスコープからUserインスタンスを取得します。取得できた場合はログイン成功、取得できない場合はログイン失敗として画面を表示します。
この記事では、ログイン処理を行うLoginLogic.java、ログインリクエストを受け取るLogin.java、ログインフォームを追加したindex.jsp、ログイン結果を表示するloginResult.jspを作成します。
今回作成するログイン機能
ひとこと広場のログイン機能では、トップ画面から利用者名とパスワードを送信します。
入力されたパスワードが1234であればログイン成功です。ログインに成功した場合は、利用者情報をセッションスコープに保存します。
ログイン機能の動き
| 項目 | 内容 |
|---|---|
| 入力する情報 | 利用者名、パスワード |
| 認証に使う値 | パスワード |
| ログイン成功条件 | パスワードが1234と一致する |
| ログイン成功時 | Userインスタンスをセッションスコープに保存する |
| ログイン失敗時 | セッションスコープにUserインスタンスを保存しない |
| 結果表示 | loginResult.jspで成功または失敗を表示する |
今回は、データベースを使った本格的なユーザー管理は行いません。
ServletとJSPの基本を確認するため、全ユーザー共通のパスワード1234で判定します。
ログイン機能で作成するファイル
今回作成するファイルは、次の4つです。
作成するファイル一覧
| ファイル | 種類 | 役割 |
|---|---|---|
| LoginLogic.java | モデル | パスワードを確認し、ログインできるか判定する |
| Login.java | コントローラ | ログインフォームから送信されたリクエストを処理する |
| index.jsp | ビュー | トップ画面にログインフォームを表示する |
| loginResult.jsp | ビュー | ログイン成功または失敗の結果を表示する |
User.javaは、前回の記事で作成済みです。
今回のログイン機能では、そのUser.javaを利用して、利用者名とパスワードを1つのインスタンスとして扱います。
図1:ひとこと広場のログイン機能の流れ

この図から分かること
ログイン機能では、トップ画面のフォームからLogin.javaへPOSTリクエストを送ります。
Login.javaは、送信された利用者名とパスワードを取得し、Userインスタンスを作成します。そのUserインスタンスをLoginLogic.javaに渡して、ログインできるかを判定します。
ログインに成功した場合は、Userインスタンスをセッションスコープに保存します。loginResult.jspでは、セッションスコープからUserインスタンスを取得し、成功または失敗の表示を切り替えます。
ログイン処理をモデルに分ける
ログイン判定は、Login.javaの中に直接書くこともできます。
しかし、MVCモデルを意識すると、ログイン判定のような処理はモデルに分けたほうが整理しやすくなります。
今回作成するLoginLogic.javaは、ログインできるかどうかを判定するモデルです。
LoginLogic.javaの役割
| 項目 | 内容 |
|---|---|
| 受け取るもの | Userインスタンス |
| 確認するもの | Userインスタンスが持つパスワード |
| 成功条件 | パスワードが1234と一致する |
| 戻り値 | 成功ならtrue、失敗ならfalse |
LoginLogic.javaは、画面表示を行いません。
また、リクエストパラメータを直接取得することもありません。
あくまで、Userインスタンスを受け取り、その中のパスワードを確認して、ログイン成功か失敗かを返す役割です。
ログインに関する処理を行うモデルを作成する
まず、ログイン判定を行うLoginLogic.javaを作成します。
ログインに関する処理を行うモデルの例
ファイル名: LoginLogic.java
package model;
public class LoginLogic {
public boolean execute(User user) {
if (user.getPass().equals("1234")) {
return true;
}
return false;
}
}LoginLogic.javaは、modelパッケージに作成します。
executeメソッドは、Userインスタンスを受け取ります。そして、user.getPassでパスワードを取得し、その値が1234と一致するかどうかを確認します。
一致する場合はtrueを返します。一致しない場合はfalseを返します。
LoginLogic.javaのポイント
LoginLogic.javaでは、ログイン判定だけを担当しています。
処理の流れ
| 順番 | 処理 | 内容 |
|---|---|---|
| 1 | Userインスタンスを受け取る | フォーム入力をもとに作成された利用者情報を受け取る |
| 2 | user.getPassを実行する | Userインスタンスからパスワードを取得する |
| 3 | 1234と比較する | 入力されたパスワードが正しいか判定する |
| 4 | trueまたはfalseを返す | ログイン結果をLogin.javaへ返す |
今回は学習用のため、パスワードを1234に固定しています。
実際のアプリケーションでは、データベースに保存されたユーザー情報を確認するような処理になりますが、ここではServletとJSPの流れを理解することを優先します。
コントローラでログインリクエストを処理する
次に、ログインに関するリクエストを処理するサーブレットを作成します。
Login.javaは、トップ画面のフォームから送信されたPOSTリクエストを受け取ります。
フォームから送信される利用者名とパスワードを取得し、Userインスタンスを作成します。
その後、LoginLogic.javaを使ってログイン判定を行います。
Login.javaの主な役割
| 処理 | 内容 |
|---|---|
| リクエストパラメータの取得 | nameとpassを取得する |
| Userインスタンスの生成 | 入力された利用者名とパスワードをまとめる |
| ログイン判定 | LoginLogic.javaに処理を依頼する |
| セッションスコープへの保存 | ログイン成功時だけloginUserとして保存する |
| フォワード | loginResult.jspへ処理を渡す |
Login.javaは、ログイン機能の中心になるコントローラです。
トップ画面とモデル、ログイン結果画面をつなぐ役割を持っています。
ログインに関するリクエストを処理するコントローラを作成する
Login.javaは、servletパッケージに作成します。
URLパターンは/Loginです。
ログインに関するリクエストを処理するコントローラの例
ファイル名: Login.java
package servlet;
import java.io.IOException;
import jakarta.servlet.RequestDispatcher;
import jakarta.servlet.ServletException;
import jakarta.servlet.annotation.WebServlet;
import jakarta.servlet.http.HttpServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.servlet.http.HttpSession;
import model.LoginLogic;
import model.User;
@WebServlet("/Login")
public class Login extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doPost(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
// リクエストパラメータの取得
request.setCharacterEncoding("UTF-8");
String name = request.getParameter("name");
String pass = request.getParameter("pass");
// Userインスタンスの生成
User user = new User(name, pass);
// ログイン処理
LoginLogic loginLogic = new LoginLogic();
boolean isLogin = loginLogic.execute(user);
// ログイン成功時の処理
if (isLogin) {
// ユーザー情報をセッションスコープに保存
HttpSession session = request.getSession();
session.setAttribute("loginUser", user);
}
// ログイン結果画面にフォワード
RequestDispatcher dispatcher =
request.getRequestDispatcher(
"WEB-INF/jsp/loginResult.jsp");
dispatcher.forward(request, response);
}
}このサーブレットでは、doPostメソッドを使っています。
トップ画面のログインフォームからPOSTで送信されるため、Login.javaではdoPostメソッドが実行されます。
Login.javaでリクエストパラメータを取得する
Login.javaでは、最初にフォームから送信された値を取得します。
取得しているのは、利用者名とパスワードです。
フォームのname属性と取得処理
| フォーム側のname属性 | サーブレット側の取得 |
|---|---|
| name | request.getParameter("name") |
| pass | request.getParameter("pass") |
フォーム側のname属性と、getParameterの引数は一致している必要があります。
一致していない場合、サーブレット側で値を正しく取得できません。
また、日本語の利用者名を扱うために、request.setCharacterEncoding("UTF-8")を実行しています。これにより、POSTで送られてきた文字列をUTF-8として扱えるようにします。
Userインスタンスを生成する
取得した利用者名とパスワードは、Userインスタンスにまとめます。
Login.javaでは、次のようにUserインスタンスを作成しています。
User user = new User(name, pass);
Userインスタンスにまとめることで、ログイン判定を行うLoginLogic.javaへ渡しやすくなります。
Userインスタンスに入る情報
| プロパティ | 内容 |
|---|---|
| name | フォームで入力された利用者名 |
| pass | フォームで入力されたパスワード |
User.javaは、前回の記事で作成したJavaBeansです。
ログイン処理では、このUserインスタンスを使って、利用者名とパスワードをひとまとまりの情報として扱います。
ログイン成功時だけセッションスコープに保存する
LoginLogic.javaによる判定結果は、boolean型のisLoginに入ります。
isLoginがtrueの場合、ログイン成功です。
ログインに成功した場合だけ、Userインスタンスをセッションスコープに保存します。
セッションスコープへの保存
| 処理 | 内容 |
|---|---|
| request.getSession | HttpSessionインスタンスを取得する |
| session.setAttribute("loginUser", user) | loginUserという属性名でUserインスタンスを保存する |
セッションスコープに保存しておくことで、次の画面でもログイン中の利用者情報を取得できます。
今回の例では、loginUserという属性名で保存しています。
ログインに失敗した場合は、セッションスコープにUserインスタンスを保存しません。そのため、loginResult.jspでloginUserを取得しようとしてもnullになります。
図2:ログイン成功時にUserインスタンスをセッションスコープへ保存する

この図から分かること
Login.javaでは、ログイン判定の結果によってセッションスコープへの保存を行うかどうかが変わります。
パスワードが1234でログイン成功になった場合だけ、UserインスタンスをloginUserという属性名でセッションスコープに保存します。
ログインに失敗した場合は、Userインスタンスを保存しません。そのため、loginResult.jspでloginUserを取得したときにnullになります。
この違いを利用して、ログイン結果画面では成功と失敗の表示を切り替えます。
トップ画面にログインフォームを追加する
前回作成したindex.jspは、ひとこと広場へようこそという見出しだけの画面でした。
今回は、このindex.jspにログインフォームを追加します。
ログインフォームでは、利用者名とパスワードを入力できるようにします。
フォームで指定する内容
| 項目 | 指定内容 |
|---|---|
| formタグのaction属性 | Login |
| formタグのmethod属性 | post |
| 利用者名のname属性 | name |
| パスワードのname属性 | pass |
| 送信ボタン | ログイン |
action属性にLoginを指定することで、フォーム送信時にLogin.javaへリクエストが送られます。
method属性にpostを指定しているため、Login.javaではdoPostメソッドが実行されます。
トップ画面を出力するビューを修正する
index.jspを次のように修正します。
トップ画面を出力するビューを修正した例
ファイル名: index.jsp
<%@ 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>
<form action="Login" method="post">
利用者名:<input type="text" name="name"><br>
パスワード:<input type="password" name="pass"><br>
<input type="submit" value="ログイン">
</form>
</body>
</html>index.jspは、src/main/webappディレクトリの直下に保存します。
ブラウザからhttp://localhost:8080/Hiroba/へアクセスすると、デフォルトページとしてindex.jspが表示されます。
ブラウザの表示例

index.jspのポイント
index.jspでは、ログイン用のフォームを追加しています。
フォーム部品の対応
| 画面の入力欄 | inputタグのtype属性 | name属性 | サーブレットでの取得 |
|---|---|---|---|
| 利用者名 | text | name | request.getParameter("name") |
| パスワード | password | pass | request.getParameter("pass") |
パスワード欄では、inputタグのtype属性にpasswordを指定しています。
これにより、画面上では入力した文字が伏せ字で表示されます。
ただし、伏せ字で表示されるだけで、暗号化されるわけではありません。この段階では、フォームの基本動作として、パスワード用の入力欄を作成していると考えましょう。
ログイン結果画面を作成する
次に、ログイン結果を表示するloginResult.jspを作成します。
loginResult.jspでは、セッションスコープからloginUserを取得します。
取得できた場合は、ログインに成功したと判断して、成功メッセージと利用者名を表示します。
取得できなかった場合は、ログインに失敗したと判断して、失敗メッセージとトップ画面へのリンクを表示します。
ログイン結果画面の表示内容
| 状態 | 表示内容 |
|---|---|
| ログイン成功 | ログインに成功しました、ようこそ利用者名さん、ひとこと投稿・閲覧へ |
| ログイン失敗 | ログインに失敗しました、トップへ |
ログイン成功時には、次の記事で作成するメイン画面へのリンクも表示します。
ログイン結果画面を出力するビューを作成する
loginResult.jspは、src/main/webapp/WEB-INF/jspディレクトリに作成します。
ログイン結果画面を出力するビューの例
ファイル名: loginResult.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" %>
<%@ page import="model.User" %>
<%
// セッションスコープからユーザー情報を取得
User loginUser =
(User) session.getAttribute("loginUser");
%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>ひとこと広場</title>
</head>
<body>
<h1>ひとこと広場ログイン</h1>
<% if (loginUser != null) { %>
<p>ログインに成功しました</p>
<p>ようこそ<%= loginUser.getName() %>さん</p>
<a href="Main">ひとこと投稿・閲覧へ</a>
<% } else { %>
<p>ログインに失敗しました</p>
<a href="index.jsp">トップへ</a>
<% } %>
</body>
</html>loginResult.jspでは、JSPの暗黙オブジェクトsessionを使っています。
サーブレットのようにrequest.getSessionを実行しなくても、JSPではsessionをそのまま利用できます。
loginResult.jspのポイント
loginResult.jspでは、セッションスコープにUserインスタンスが保存されているかどうかで表示を切り替えています。
JSPで行っていること
| 処理 | 内容 |
|---|---|
| page import="model.User" | JSPでUser型を使えるようにする |
| session.getAttribute("loginUser") | セッションスコープからUserインスタンスを取得する |
| (User) | Object型からUser型へキャストする |
| loginUser != null | ログイン成功として表示する |
| loginUser == null | ログイン失敗として表示する |
ログイン成功時だけLogin.javaでUserインスタンスをセッションスコープに保存しています。
そのため、loginResult.jspではloginUserが取得できるかどうかによって、ログイン結果を判断できます。
図3:loginResult.jspでログイン結果を表示する

この図から分かること
loginResult.jspでは、セッションスコープからloginUserを取得します。
loginUserがnullでなければ、ログイン成功として成功メッセージを表示します。さらに、loginUser.getNameを使って、利用者名を画面に表示します。
loginUserがnullの場合は、ログイン失敗として失敗メッセージを表示します。
ログイン成功時に表示するひとこと投稿・閲覧へのリンクは、次の記事で作成するMain.javaへアクセスするためのリンクです。
メイン画面へのリンクについて
loginResult.jspには、次のリンクがあります。
ひとこと投稿・閲覧へ
このリンクをクリックすると、MainというURLパターンへGETリクエストが送られます。
ただし、この時点ではまだMain.javaを作成していません。
そのため、今回の記事の段階でこのリンクをクリックすると、404ページが表示されます。
現時点での注意点
| リンク | 現在の状態 |
|---|---|
| Main | 次の記事で作成する |
| クリックした場合 | 今回の段階では404ページになる |
| 完成後 | メイン画面へ進めるようになる |
今回の記事では、ログイン結果画面まで表示できれば十分です。
Main.javaとメイン画面は、次の記事で作成します。
ログイン成功時の動作確認
ここまでのファイルを作成したら、ログイン成功時の動作を確認します。
ログイン成功時の確認手順
| 手順 | 内容 |
|---|---|
| 1 | ブラウザでhttp://localhost:8080/Hiroba/へアクセスする |
| 2 | 利用者名にuserAと入力する |
| 3 | パスワードに1234と入力する |
| 4 | ログインボタンをクリックする |
| 5 | ログイン結果画面が表示される |
| 6 | ログインに成功しましたと表示される |
| 7 | ようこそuserAさんと表示される |
パスワードが1234なので、LoginLogic.javaはtrueを返します。
その結果、Login.javaはUserインスタンスをセッションスコープに保存します。
loginResult.jspでは、セッションスコープからloginUserを取得できるため、ログイン成功の画面を表示します。
ブラウザの表示例

ログイン失敗時の動作確認
次に、ログイン失敗時の動作を確認します。
ログイン失敗時の確認手順
| 手順 | 内容 |
|---|---|
| 1 | ブラウザでhttp://localhost:8080/Hiroba/へアクセスする |
| 2 | 利用者名にuserAと入力する |
| 3 | パスワードに12345と入力する |
| 4 | ログインボタンをクリックする |
| 5 | ログイン結果画面が表示される |
| 6 | ログインに失敗しましたと表示される |
| 7 | トップへリンクが表示される |
パスワードが1234ではないため、LoginLogic.javaはfalseを返します。
その場合、Login.javaはUserインスタンスをセッションスコープに保存しません。
loginResult.jspではloginUserを取得できないため、ログイン失敗の画面を表示します。
ブラウザの表示例

セッションスコープを使うときの動作確認の注意
ログイン機能では、セッションスコープを使います。
セッションスコープにUserインスタンスが残っていると、前回のログイン状態が影響して、思った通りに確認できない場合があります。
特に、ログイン成功を確認したあとにログイン失敗を確認する場合、以前のセッションが残っていると結果が分かりにくくなることがあります。
確認時の注意点
| 状況 | 対応 |
|---|---|
| 動作結果が想定と違う | ブラウザをすべて閉じてから再実行する |
| 前回のログイン情報が残っているように見える | セッションスコープの状態を疑う |
| ログイン成功と失敗を続けて確認する | できればブラウザを閉じてから確認し直す |
セッションスコープは、リクエストをまたいで情報を保持できる便利な仕組みです。
その一方で、開発中は前回の実行結果が残っているように見えることがあります。動作確認で迷ったときは、ブラウザをすべて閉じてから確認し直すと、状態を整理しやすくなります。
今回作成したファイル
今回の記事では、ログイン機能に必要な4つのファイルを作成しました。
作成・修正したファイル
| ファイル | 保存場所 | 内容 |
|---|---|---|
| LoginLogic.java | src/main/java/model | パスワードを確認してログイン判定を行う |
| Login.java | src/main/java/servlet | ログインリクエストを受け取り、セッションスコープにUserを保存する |
| index.jsp | src/main/webapp | ログインフォームを追加する |
| loginResult.jsp | src/main/webapp/WEB-INF/jsp | ログイン結果画面を表示する |
前回作成したUser.javaを利用して、ログイン処理を行えるようになりました。
次の記事では、ログイン結果画面から進むメイン画面を作成します。メイン画面では、ログイン中の利用者名を表示し、未ログインで直接アクセスされた場合はトップ画面へ戻す処理を作成します。
