レベル: 初級 山元 和斗志, , リコーテクノシステムズ株式会社
2004年 8月 06日 実際に動作する掲示板ソフトの開発をとおして、アプリケーション開発の上流過程からコーディングまでを実践的にご紹介します。
※この講座はリコーテクノシステムズ株式会社 山元和斗志様の投稿講座です。
0. はじめに
皆様いかがお過ごしでしょうか。掲示板システムをWebアプリケーションで構築するまでを、設計段階からご紹介するレポートの第3回が収穫される季節になりました。豊作だと良いのですが・・・。
第2回までの内容で、基本的な機能が実装されていますので、第3回レポートでは管理者用機能や、ユーザー登録の機能を開発し、その様子をご報告できればと考えています。よろしくおつきあいください。
今回のレポートではJavaMailを使用している場面があります。JavaMailについての基本的なことは触れませんので、SunのJavaMail APIを参照してください。
このJavaMailを用いて、メールを送るには、別途メールサーバーも構築する必要があります。
このレポートを書くに当たっては、ネットワーク上に存在するLinuxにQmailかSendMailを導入してあったものを、そのままうろ覚えの接続情報で利用していますので、環境については潔く割愛します。
SunのJavaMail API
1. ユーザー登録:分析フェイズ
ユーザー登録については、第1回レポートの「1.掲示板を設計する」の匿名性についてで考察した内容をおさらいしつつ、話を進めて行きます。まずは、ユーザー登録の流れについて考えて見ましょう。
ユーザー登録の流れ
- 掲示板を利用したい人(以下、申請者と呼びます)が、ユーザー登録に必要な情報を入力する
- 掲示板システムが入力された情報をチェックする
- 掲示板システムが入力された情報を元に、仮ユーザーを登録する
- 掲示板システムが仮ユーザー登録の完了をメールで申請者に通知する
- 申請者がメールに記載されたリンクから掲示板システムの正式登録画面にアクセスする
- 申請者がユーザー登録を完了する
- 掲示板システムがユーザー認証を行い、メニュー画面を表示する
漠然としている印象を持たれると思います。しかし、こんなものかな、と思う方もいらっしゃるでしょう。
正直なところ、ここではわざと漠然とした感じで書いています。
特に「1」の部分では「必要な情報」を入力すると記述されていますが、何が必要なのかは全く不明ですし、さらに「2」の部分では何をチェックするのか、明記してありません。
図1-1.ユースケース図

ユースケース図は、システム全体を表現しています。
個々のユースケースについて、開始から終了までの処理の流れについて記述したものが必要になってきます。そこで「ユースケース記述書」を作ります。
図.個々のユースケースに注目!

第2回のレポートでは、掲示板の分析から画面遷移図を作成し、そこからStrutsベースのクラスを割り出していきました。
今回のレポートではユースケース「ユーザー登録」に注目し、その処理の流れをユースケース記述書に書き出し、それを足がかりに、機能の関連から(主に)Strutsベースのクラスを割り出していきましょう。
ユースケース記述書 ユースケース記述書の定義については、少々曖昧な点があります。というのも、解説する書物によって書き方が微妙に違っていますし、必要に応じて○○を記述しましょう、という表現が散見されるからです。
明確なのは「システムとアクターのやりとりを記述する」のがユースケース記述書だということです。
ユースケース記述書を「どこまで書くか」または「どのように書くか」を定義することは不可能であると考えています。アプリケーションの開発において、各種ドキュメントにどの程度まで詳しい記述を行うか、という判断はプロジェクト毎(あるいはプロジェクトの管理者の考えによって)に違うという経験則もありますし、これについて議論が始まると、最低3時間があっという間に消費され、しかも結論が出ないのです。
実は3回目ぐらいで、その議論が不毛だということを学習しましたので、議論が始まるとほかの事を考えるようにしています。大きな声では言えませんけど。顔だけ真面目にしています。
そういったわけで、私のユースケース記述書は、多様に定義される「ユースケース記述書」の、たった1つの亜種に過ぎないことは、忘れずにいてください。このレポートを書いている時点での、私なりの定義であるに過ぎませんし、なにより「ここまで書けばいいかな」という妥協の産物でもあるのです。
図1-2.ユースケース記述書

重要なポイントは以下の2点です。
- 主語は「システム」と「アクター」のみ(が、望ましい)
- 処理の流れは明確に記述するが、実現手段はできる限り記述しない
ここまでで、ユーザー登録という処理の流れが大まかに決まりましたので、次はより詳細に処理の流れを考えていきましょう。分析フェイズが一旦終わり、設計フェイズの始まりです。
2. ユーザー登録:設計フェイズ
分析フェイズでシステムの要件が大まかにきまったと仮定します。完璧な設計は必要ない、というスタンスで進めていますが、基本的に分析も完璧を求める必要はありません。
なぜなら、分析フェイズで完璧を目指すと、設計フェイズでやるべきことを分析フェイズでやってしまうだけで、まったく意味がないからです。ウォーターフォール・モデルの開発が前提にあって、後戻りが絶対悪と考える方は納得がいかないかもしれませんが、経験上、後戻りをなくそうとする努力がプロジェクトの(フェイズレベルでの)進行を止めてしまう場面がよく見受けられます。
肩の力を抜きましょう。後で直せばよい、この辺にして次行こう、と考えてください。手直しは少ないに越したことはありませんが、決して絶対悪ではありません。
個人的な目安ですが、分析フェイズと設計フェイズの成果としてのドキュメントを比較して、もしもその内容が大きく変わらなかったら、それは分析フェイズに力を入れすぎか、設計フェイズで手を抜きすぎの、どちらかの可能性があります。ちょっと、過去を振り返ってみてください。
ちなみに、筆者は心当たりが多すぎます。そういうわけで、最近は肩の力を抜くようにしています。
設計フェイズ、始まる
早速、分析フェイズで作成したユースケース図を元に、設計を行っていきましょう。
図2-1.設計第1段階

ユースケース図の、メインフローの番号が「M」に対応しています。見比べてみてください。例外は、メインフロー同様に「E」で表現しています。矢印は処理の流れを表現しています。
楕円形に向かう矢印は画面からの入力を伴いますので、最後にまとめてFormクラスの設計をします。
ユースケース図と、処理の流れを見比べてみてください。現状、矛盾や過不足はないと思います。
JSPによる画面2つ(最後のひとつはメニュー画面なので、この機能のために作るものではない)と、各段階で処理を行うActionクラス2つで実現できそうな見通しです。
しかし、第1回レポートの「1.掲示板をデザインする」の匿名性についての段落を参照すると、以下のことが定義されていることがわかります。
- 利用に当たってはユーザーIDとパスワードを要求する
- ユーザーIDの取得にはメールアドレスが必須(メールアドレスは非公開)
- メールアドレス1個につき1個のユーザーIDを取得できる
- メールアドレスのドメイン(またはアドレスそのもの)によっては、ユーザーIDを取得できない
この制限に対して、図2-1の設計は安全でしょうか?
設計フェイズ、進む!
図2-1から、筆者が考えた問題点は次の2点に関係します。
- ユーザーIDの取得にはメールアドレスが必須(メールアドレスは非公開)
- メールアドレス1個につき1個のユーザーIDを取得できる
図2-1の設計では「存在しないメールアドレスによるIDの取得」が防げないのです。これを防ぐような設計にしなければ、ユーザーIDの取得にはメールアドレスが必須、という制限が有名無実になってしまいます。
そこで、図2-2のように一旦メールの送信を処理の中に組み込むことで、存在するメールアドレスでしか登録ができないようにすることにしました。
図2-2.設計第2段階

M6のメールの本文にはM7の画面にアクセスできるリンクが記述されている、ということです。
しかし、まだ完璧とはいえません。なぜなら、メールの本文に存在するリンクの記述次第では、M7の画面に直接アクセスすることも可能であるということです。
例えば、http://<<server_name>>/JadeCircuit/account/formal_user.jspなどとなっている場合は、まず間違いなく直接アドレスを入力してアクセスする利用者が存在するでしょう。利用者ならまだしも、悪意を持った存在が攻撃の手段に利用する可能性を考えると、安全とは言いがたいと思います。
さらに重要なのは、M7の画面が、アクセスするユーザー個々にカスタマイズされた内容、つまり、ユーザーIDやユーザー名を二度入力する必要がない状態であるべきであるということです。この点はアドレスにデータを付加すればよいのでhttp://<<server_name>>/JadeCircuit/account/formal_user.jsp?user_id=GENのようにすれば良いのですが、user_id=GENの部分を容易に変更できるので、やはりjspへのリンクそのものが好ましくないように思われますので、ここはActionクラスの追加を検討することにしましょう。
図2-3.設計第3段階

設計フェイズ続く! 図2-3で、ユースケース記述書に記述されたメインフローが割り当てられないクラスが追加されたわけですが、これは間違っていないのでしょうか?結論から言いますと、これは間違っていません。
なぜなら、分析フェイズでは奥歯に物が挟まったような物言いで、曖昧に、処理の流れを重視して記述しましたので、メールを使用するとか、IDに制限があるとかは、考慮されていないのです。
分析フェイズの内容を具体化し、肉付けしていく設計フェイズにおいて、分析フェイズの結果に追加していくことはごく普通のことです。
では、この追加されたActionクラスで実行する処理について考えて見ましょう。M6からM7の間を繋ぐクラスの、筆者の期待する役割は以下の通りです。
- M7をカスタマイズされた内容にしたい
- 正しいアクター(=「仮ユーザー」状態のユーザー)のみ、M7への移動を許したい
- 付加しているデータを改変しても、M7に割り込めないようにしたい
このぐらいが実現できれば良いでしょう。
まず、上から2つですが、これは付加するデータを元に、仮ユーザーを検索することで、解決できそうです。
正式にユーザー登録が終わっても、メールの本文はユーザーの手元に残るわけですから、処理の対象を検索する条件に「仮ユーザーである」ことを盛り込むことで、より堅牢になります。
最後のひとつは、いろいろ考えましたが、改変されたデータか否かを判断することが非常に難しい、というか筆者が方法を考え付かなかったことと、データの改変が「ほぼ無意味」のレベルに引き上げられれば良い、と考え直し、付加するデータを増加させることで対応することにしました。
例えば、http://<<中略>>/formal.do?user_id=GEN&password=i36ahsyetzgsirun10ayemzhsyr75kzuです。
ランダムに生成される32桁のパスワードを破ること自体が困難ですし、破るために使用できる時間は「仮パスワード発行から、正式パスワード決定まで」の時間です。ほとんどの場合、わずかな時間であると思われます。
仮パスワードの存在によって、仮ユーザー状態でログインを試みるユーザーの可能性を考慮しなければなりませんが、これは「正式パスワードは20桁まで&ログイン画面の入力フィールドのmaxlength=20」とすることで対応できるでしょう。仮パスワードを入力できなくした、ということですね。
ユーザー認証(ログイン)の処理に「対象ユーザーが仮ユーザーではない」という条件を入れることでも対応は可能でしょうが、追加・変更になる可能性のある要素を加えるのは控えておきましょう。いずれその条件を変更して「ユーザーと管理者と・・・」などとしなければならないのは手間ですから・・・。
入力項目の分析
次に、処理を進める上で、画面からシステムに入力される項目を分析します。
表2-4.入力項目分析結果
| 1.登録申請(M3) | 2.メール本文リンクの付加情報 | 3.正式登録(M8) |
|---|
ユーザーID
ユーザー名
メールアドレス
メールアドレス(確認) | ユーザーID
パスワード | ユーザーID
パスワード
パスワード(確認) |
上記表2-4より、共通のFormクラスを作ることができます。名前はUserFormとするのが良いでしょうか。
ユーザー認証や、パスワード再発行の処理でも利用できそうな見込みですので、大切に扱いましょう。
このぐらいまで機能を実現する具体的な形が決まれば、設計フェイズも終わりに近づいています。
このまままとめに行っても良いのですが、参考のため、少々分析フェイズに目を戻してみることにします。
分析フェイズ、手直し ここまで設計を進めて、どうやら設計も一段落した感があります。設計がおおまかに終わったら、分析フェイズで作成したユースケース記述書に修正を加えましょう。
ただし、注意していただきたいのは「修正しなければならない」という意味ではない、ということです。
設計フェイズに伴って、分析フェイズの内容を修正するかどうかは、プロジェクト(あるいはプロジェクト・リーダーの意向)によって決定されることですので、どちらがいいとか悪いとかいう問題でもありません。
システムが完成した後で、ドキュメントを見直すと、きれいにまとまっていて気分が良い、程度の満足感が得られるぐらいのものだと、筆者は考えています。
ここでは、修正するとしたらどのように修正するか?をちょっと見ていただくために修正します。
図2-5.ユースケース記述書(改訂版)

追加・変更の部分を赤で示してあります。変更のポイントはアクターが「ユーザー」から「未登録ユーザー」になったことと、前提条件が追加されたことです。アクターへの通知は、メールを使用しますので、アクターが固有のメールアドレスを持っていなければ、このユースケースを開始できない(開始しても、意味がない)ということを表現しています。
今回は主な修正が追加の内容でしたので、きれいに片付きましたが、筆者にとっては珍しい部類に入ります。
分析フェイズの内容を設計フェイズの過程で変更する場合、主な修正の内容が追加の時はいい傾向だと、筆者は経験的に思っています。
削除がある場合には、分析が甘かったり正しくなかったりということを示唆していますので、注意です。
設計フェイズ、まとめ
図2-5のユースケース記述書にあわせて、設計の最終段階を図にまとめました。
図2-6.設計最終段階
なにやら分割されていますが、この理由は「システムはメールソフトを起動しない」ということです。
システムとアクターのやりとりを記述するユースケース記述書としては見逃せない間隙です。メインフローの6は、実は図2-6の左から2番目のJSPであり、同時に左から3番目の「メール本文」でもあるのです。
Webアプリケーションは「入力画面」と「サーバー処理」と「結果画面」の複合体です。仮ユーザー登録が成功した場合は、成功したことがわかる「結果画面」を表示する必要があるのです。
「また分析フェイズの変更か!」と思われるかもしれませんが、そのために「この辺にして、次」というスタンスを取っている側面もありますので、しばしご辛抱ください。
図2-7.ユースケース図改訂(一部) 
図1-2のユースケース記述書の中身に「仮ユーザー」がありました。
さらに図2-5のユースケース記述書では加えて「未登録ユーザー」が出てきました。
このような、アクターの持つ特殊な側面はアクターの候補であることが多々あります。
事実、既に掲示板を利用しているユーザーは新規ユーザー登録を行うことができません。新規登録を同1人物が行ったとしても、ユーザーID、ユーザー名、メールアドレスを重複できないためシステムは別人(別ユーザー)として扱います。
これが「ユーザーは新規登録を行うことができない」という意味になります。
そこで、未登録ユーザーと仮ユーザーというアクターを追加したところ、必然的にユースケースが分割されなければなりませんでした。未登録ユーザーは仮ユーザーとなって初めて、正式登録を行うことができるのです。
新規アクターの追加と、ユースケース記述書から設計した内容によるユースケースの分割は、相互に矛盾しないことが図2-7からもわかります。
この変更で、ユースケース記述書がどのように変化するか、次の段落でご覧いただきます。
また、ユースケース分割が、結果としてシステムの設計・開発にどのような影響を与えるかも考えてみることにしましょう。
ユースケース記述書 - 改訂
図2-8.仮ユーザー登録 - ユースケース記述書
図2-9.ユーザー正式登録 - ユースケース記述書
過不足なく分割できているか、いつの間にかなくなっている処理がないかどうか、確認してみてください。
次に、パスワード初期化について考えます。
パスワード初期化のユースケース記述書
図2-10.パスワード初期化 - ユースケース記述書
パスワード初期化という機能を「仮パスワードを生成し、ユーザーを仮ユーザーに変更する」ことであるとした場合のユースケース記述書ですので、これを見て「なるほど!すばらしい!」とお考えになった方は、筆者に少々乗せられています。筆者は「ユースケースを分割することで機能が分割され、パスワード初期化を○○と定義すれば、先ほど分割した機能が再利用できて、もう最高!」と考えつつ設計を行っているからです。
つまり、図2-10のユースケース記述書の場合は、機能が再利用できる設計になったので、システムにとって良い影響であるように見えます。しかし、パスワード初期化がもっと独自の処理である場合には、先ほどの分割はシステムに影響を与えないことになります。
その場合は「無意味な変更を分析フェイズのドキュメントに加えて時間を消費した」ということで、システム的にはともかく、プロジェクトに「悪い影響」を与えたことになるのです。
分析フェイズと設計フェイズの関係はこのように、非常に奥が深いものなのです。深すぎて困ります。
最後に、Strustsベースのクラスを洗い出して、終わりにしましょう。
表2-11.Strutsベースのクラス一覧
| アクション名 | Actionクラス | Formクラス | ビジネスロジック |
|---|
| /entry | RegistEntryAction | UserForm | 仮ユーザー登録
仮パスワード生成&メール送信 | | /formal | RegistUserAction | UserForm | 仮ユーザー検索
正式登録画面表示 | | /regist | RegistPassAction | UserForm | 正式ユーザー登録
メニュー画面表示 | | /forget_pass | ForgetPassAction | UserForm | 仮ユーザーに変更
仮パスワード生成&メール送信 |
あとは、コーディングです。
3. サンプルコード
申し訳ありませんが、今回は特にご紹介に値するものがありません。
4. 今回までの成果
今回はユーザー登録と、パスワードの再発行を作成しました。
図4-1.ログイン画面
図4-2.新規登録申請
図4-3.仮ユーザー登録完了
図4-4.メール本文 
図4-5.正式登録画面 
図4-6.メニュー画面
結局、分析や設計は、それを実行する人のスタイルやスタンスで無限に変化します。
良いとも悪いとも決められないスタイル(生き様)とそれまでの経験に裏打ちされたスタンス(やり方)が設計・開発の大きな部分を占めていると言って差し支えないでしょう。
今回は長い時間、筆者のスタイルに付き合わせてしまいまして、申し訳ありませんでした。
よろしければまた次回、お会い致しましょう。
おつかれさまでした。
参考文献
著者について  | |  | 山元 和斗志,リコーテクノシステムズ株式会社 |
記事の評価
|