学習26日目:ソルト文字列やハッシュ関数でパスワードを作成。

今日の学習時間。

  • Day:26
  • Today:12h
  • Total:167h

学習内容について。

昨日の続きをしていく。

Employee情報の管理機能を作成。

モデルを作成。

カラム名用途データ型
idリソース内での連番数値型
code社員番号文字列型
name社員名文字列型
passwordシステムへのログインパスワード文字列型
admin_flag管理者権限があるかどうか数値型(一般:0、管理者:1)
created_at登録日時日時型
updated_at更新日時日時型
delete_flag削除された従業員かどうか数値型(現役:0、削除済み:1)
Employeeに設定したプロパティ
@NamedQuery
  • getAllEmployees
    • すべての従業員情報を取得
  • getEmployeesCount
    • 従業員情報の全件数を取得
  • checkRegisteredCode
    • 指定された社員番号がすでにデータベースに存在しているかをチェック
  • checkLoginCodeAndPassword
    • 従業員がログインするときに社員番号とパスワードが正しいかをチェック
一意制約
  • 28行目:codeのプロパティにunique = trueという指定を追加
    • 一意制約という
    • すでに存在している社員番号は登録できない旨をデータベースに教えてあげるための設定
    • データベースにも制約を入れて重複を防止するのが一般的
  • idは単純にEmployee内での連続した番号という意味合いだけを持つ
length = 64の意味
  • 例えばlength = 64と入れることで、入力できる文字情報が最大64文字までになる
  • パスワードの情報についてはSHA256というハッシュ関数を利用
    • ハッシュ化した文字列をデータベースへ保存できるようにする
    • ハッシュ化されていない生のパスワード文字列をデータベースに保存するのはセキュリティ面から考えて危険
    • SHA256は、どんな文字数の文字列でも必ず、64文字のハッシュ化された文字列にする
      • なので固定で64文字までという設定を追記した

バリデーション用のクラスを作成。

  • 社員番号、氏名、パスワードの必須入力チェックを行う
  • 社員番号のみ「すでにデータベースに存在する社員番号かどうか」のチェック
  • 変更(update)の場合は、バリデーションが不要な場合もある(パスワードなど)
    • 社員番号とパスワードについては第2引数にBoolean型の引数を用意
    • trueであれば、パスワードの入力値チェックと社員番号の重複チェックを行う
ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee class"
[master 413438b] Add Employee class
 3 files changed, 185 insertions(+)
 create mode 100644 src/models/Employee.java
 create mode 100644 src/models/validators/EmployeeValidator.java

indexを作成。

アクションサーブレット名URLマッピングHTTPメソッド
indexEmployeesIndexServlet/employees/indexGET
newEmployeesNewServlet/employees/newGET
createEmployeesCreateServlet/employees/createPOST
showEmployeesShowServlet/employees/showGET
editEmployeesEditServlet/employees/editGET
updateEmployeesUpdateServlet/employees/updatePOST
destroyEmployeesDestroyServlet/employees/destroyPOST

上記の表に沿って7つのアクションを作成していく。

servletを作成。

JSPを作成。

ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee index"
[master c957b78] Add Employee index
 2 files changed, 118 insertions(+)
 create mode 100644 WebContent/WEB-INF/views/employees/index.jsp
 create mode 100644 src/controllers/employees/EmployeesIndexServlet.java

newを作成。

servletを作成

JSPを作成。

new.jspedit.jspで共通しているフォーム部分は_form.jspというファイルで共通化する。

ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee new"
[master 46b3958] Add Employee new
 4 files changed, 90 insertions(+)
 create mode 100644 WebContent/WEB-INF/views/employees/_form.jsp
 create mode 100644 WebContent/WEB-INF/views/employees/new.jsp
 create mode 100644 src/controllers/employees/EmployeesNewServlet.java

createを作成。

パスワードのソルト文字列をリスナーを使って登録。

  • createを作成する前に、パスワードのハッシュ化に関する新しいクラスを2つ用意
    • 入力されたパスワード文字列に何らかの文字列を連結させたものをSHA256でハッシュ化
    • ハッシュ化した文字列をデータベースに登録
  • 上記はパスワード文字列をそのままハッシュ化するよりも安全にパスワードデータを保管するための工夫
  • パスワードに連結させる文字列のことをソルト文字列という
  • パスワードのソルト文字列をリスナーを使って登録(下記)
    • イベントはjavax.servlet.ServletContextListenerのみにチェック
  • このファイルが外部から見えてしまうとセキュリティ対策が無意味になる
    • GitHubにpushする場合を考えて、このファイルのパスを .gitignoreに追加してGit管理の対象外した

文字列をSHA256でハッシュ化するクラスを作成。

getPasswordEncrypt(src)のようにメソッド名をひとつ記述すれば実行できるハッシュ化メソッドを用意(下記)してユーティリティにする。

  • getPasswordEncryptメソッド
    • 引数で受け取った文字列にソルト文字列を連結させたものをSHA256でハッシュ化
    • 引数の文字列が何もなければ、空の文字列を返す
ここまでをGitにコミット
$ git add .

$ git commit -m "Add password encryption"
[master aa8d566] Add password encryption
 2 files changed, 83 insertions(+)
 create mode 100644 src/listeners/PropertiesListener.java
 create mode 100644 src/utils/EncryptUtil.java

create用のservletを作成。

  • 59行目
    • 新規登録の場合、パスワードの入力値チェックと社員番号の重複チェックは必ず実施
    • 第2と第3引数を両方ともtrueで指定
ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee create"
[master fe1bc7f] Add Employee create
 1 file changed, 81 insertions(+)
 create mode 100644 src/controllers/employees/EmployeesCreateServlet.java

showを作成。

ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee show"
[master bdfeb60] Add Employee show
 2 files changed, 101 insertions(+)
 create mode 100644 WebContent/WEB-INF/views/employees/show.jsp
 create mode 100644 src/controllers/employees/EmployeesShowServlet.java

editを作成。

ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee edit"
[master 20d950c] Add Employee edit
 2 files changed, 82 insertions(+)
 create mode 100644 WebContent/WEB-INF/views/employees/edit.jsp
 create mode 100644 src/controllers/employees/EmployeesEditServlet.java

updateを作成。

  • 社員番号は現在と異なる内容が入力された(変更を希望した)場合に重複チェック
  • パスワードは入力欄に入力された際、入力値チェックを実行
    • 今後このシステムを拡張していく場合のことを考慮した実装
ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee update"
[master bc29e2c] Add Employee update
 1 file changed, 96 insertions(+)
 create mode 100644 src/controllers/employees/EmployeesUpdateServlet.java

destroyを作成。

論理削除
  • 今回はremoveメソッドは使用していない
    • 代わりにEmployeeプロパティのひとつであるdelete_flagが1になっている従業員情報は削除されているとみなすルールでシステムを作成
  • 理由:日報を残したまま従業員だけ削除されてしまうと、提出者が不明の日報情報が溜まってしまうから
  • 論理削除
    • destroyした従業員情報は削除したとみなしてシステム上で扱う
    • 従業員情報そのものはデータベースへ残す
  • deleteでデータ自体を削除するか、delete_flagで論理削除をするかは状況判断が必要
ここまでをGitにコミット
$ git add .

$ git commit -m "Add Employee destroy"
[master e4e5b94] Add Employee destroy
 1 file changed, 53 insertions(+)
 create mode 100644 src/controllers/employees/EmployeesDestroyServlet.java

ログイン機能を実装。

  • システムに登録されている従業員だけが利用できるように、ログイン機能を追加
  • 従業員管理のページは管理者(admin_flag1になっているアカウント)のみが閲覧可能に

ログインとログアウトのサーブレットを作成。

アクションサーブレット名URLマッピングHTTPメソッド
loginLoginServlet/loginGET, POST
logoutLogoutServlet/logoutGET
  • ログイン画面の表示はGET、認証処理はPOST
  • doPost()
    • ログインページで入力された社員番号とパスワードをもとにデータベースへ照合
    • 情報に間違いがなければセッションスコープにその従業員情報のオブジェクトを格納(login_employeeへ)
    • セッションスコープにlogin_employeeという名前で従業員情報のオブジェクトが保存されている状態がログイン状態
  • パスワードはハッシュ化されてデータベースに登録されている
    • フォームから入力されたパスワードを67行目でソルト文字列に連結した文字列をハッシュ化する
    • そのデータとデータベース上のデータで照合を行う
  • セッションスコープからlogin_employeeを除去することでログアウトした状態にする(31行目)
  • ログアウトしたら、自動でログインページにリダイレクトされる(34行目)
  • hasErrorという変数がリクエストスコープにtrueでセットされていればエラーメッセージを表示する
  • サーブレットからメッセージをリクエストスコープにセットするのではなく、あらかじめJSPに記述
ここまでをGitにコミット
$ git add .

$ git commit -m "Add login / logout"
[master b59c7b9] Add login / logout
 3 files changed, 170 insertions(+)
 create mode 100644 WebContent/WEB-INF/views/login/login.jsp
 create mode 100644 src/controllers/login/LoginServlet.java
 create mode 100644 src/controllers/login/LogoutServlet.java

ログインチェック用のフィルタを作成。

  • filtersパッケージにLoginFilterフィルタを追加
  • フィルター・マッピングは/*
  • ログイン状態のチェックは、サーブレットの処理よりも前に実行
  •  ログインチェック用のフィルタを実装する前に、必ず管理者 (admin_flag1になっているアカウント) を1つ作成しておく
    • フィルタ実装後は管理者しか従業員管理 (/emploees) のページにアクセスできない
ここまでをGitにコミット
$ git add .

$ git commit -m "Add LoginFilter"
[master 1a7306c] Add LoginFilter
 1 file changed, 50 insertions(+)
 create mode 100644 src/filters/LoginFilter.java

画面を調整。

  • ログイン後のトップページにフラッシュメッセージを表示
  • 画面にログアウトへのリンクを表示する

上記でリクエストスコープにフラッシュメッセージを設定した。下記はそのビュー。

ログイン中の画面にログアウトへのリンクなどを表示するように下記を修正した。

ここまでをGitにコミット
$ git add .

$ git commit -m "Add login / logout link"
[master 9ece3ec] Add login / logout link
 4 files changed, 58 insertions(+), 13 deletions(-)

今日の反省と明日の目標。

プログラミングしてるとあっという間に1日が終わってしまうことに毎度驚いているところです。先週に痛めた首が未だに痛くてジムに行けてない分、コードを書く活力へと変換しています。さすがに病院に行くべきかな。そろそろ温泉も行きたいな。

さて、計画では明日でカリキュラムが終わりそうです。学習を通じて、前よりも自分が何を勉強していくべきかがより鮮明になった気がしています。ポートフォリオを作るにあたってはフロントエンドの技術も必要でしょうし。Javaの一連の流れは掴めてきたと思っていますが、これをどう応用していくかが悩ましいですね。いろいろ作ってみたいものはあるにはあるんです。しかし、それを自分の実力で作れるか。。まあ、その分からないところをメンターの方に聞くために早めにカリキュラムを終わらせてるので、大丈夫だろうと思います、そう信じたい。

明日はDTOを使った日報情報の管理機能について学習していきます。

一応ですが、今のところ興味があるのは、JavaScript、Linux、AWS、Dockerです。それらの技術も並行して学習していく予定。というよりも、そんなに時間がないので作りたいものだけ調べて引っ張ってくる形で。

閉じる