Javaを鍛える
新人エンジニアが社内のチケット管理ツール「TicketCraft」を1年かけて育てていく物語で、OOP基礎からJava8モダン文法、DI・AOP、GoFデザインパターン全23種までを解説します。
OOP基礎編
- Javaを鍛える|OOP基礎編 #1
オブジェクト指向とは何か|TicketCraftを例に
配属先の古いチケット管理ツール『TicketCraft』のコードを読み解きながら、オブジェクト指向プログラミングの目的と4大原則(カプセル化・継承・ポリモーフィズム・抽象化)の全体地図をつかむ入門記事。
- Javaを鍛える|OOP基礎編 #2
カプセル化の基本と実践
フィールドが全部publicなTicketCraftのコードで実際に起きた事故を題材に、private化・getter/setter・不変条件の保護までカプセル化を実践的に学ぶ。
- Javaを鍛える|OOP基礎編 #3
継承の基本と実践
TicketCraftのTicketクラスからBugTicket・FeatureTicketを継承で分離し、extends・コンストラクタ連鎖・protectedの使い方を実践的に学ぶ。
- Javaを鍛える|OOP基礎編 #4
ポリモーフィズムの基本と実践
TicketCraftの一覧表示処理からinstanceofの型分岐を追放し、オーバーライド・インターフェース分離・実行時多態を実践的に学ぶ。
- Javaを鍛える|OOP基礎編 #5
抽象化の基本と実践
TicketCraftの通知処理を題材に、抽象クラスとインターフェースの使い分け、抽象メソッドによる実装強制を実践的に学ぶ。OOP基礎編の完結編。
Java8モダン文法
- Javaを鍛える|Java8モダン文法 #1
ラムダ式とStream API入門
TicketCraftのfor文だらけの一覧処理を、ラムダ式とStream APIで簡潔に書き直す。中間操作・終端操作の考え方から、遅延評価の落とし穴まで実践的に学ぶ。
- Javaを鍛える|Java8モダン文法 #2
関数型インターフェース徹底解説
前回のラムダ式が実は何の型なのかを掘り下げ、Predicate・Consumer・Function・Supplierの使い分けと、条件・処理を部品化して合成する方法をTicketCraftで実践する。
- Javaを鍛える|Java8モダン文法 #3
メソッド参照とJava8以降の新機能
既存メソッドを呼ぶだけのラムダ式をメソッド参照で簡潔にする4パターンを、TicketCraftのコードで実践。Java8以降の主要な新機能ダイジェストとレガシー環境での注意点も解説。
設計編(DI・AOP)
デザインパターン全23回
生成に関するパターン
Singleton:システム全体で共有する設定・ロガーを1つに保つ
TicketCraftの設定オブジェクトがあちこちで new され、状態がバラバラになっていた問題をSingletonパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Factory Method:チケット種別ごとの生成分離
TicketCraftのチケット生成コードが複数箇所に散らばったif分岐で書かれていた問題を、Factory Methodパターンで1箇所に集約する。Before/Afterの実コードとコンパイル確認付き。
Abstract Factory:通知チャネル一式の差し替え
TicketCraftの緊急通知で、通常用と緊急用の通知手段が食い違って組み合わさってしまう事故を、Abstract Factoryパターンで防ぐ。Before/Afterの実コードとコンパイル確認付き。
Builder:複雑な検索条件オブジェクトの段階的構築
TicketCraftのチケット検索条件が引数の多いコンストラクタで作られ、使わない項目にまでnullを渡す必要があった問題を、Builderパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Prototype:よく使うチケットテンプレートの複製
TicketCraftでテンプレートから新しいチケットを作る際、フィールドを手作業でコピーして1つ書き忘れるバグが起きた問題を、Prototypeパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
構造に関するパターン
Adapter:社外チケットサービスAPIとの接続変換
TicketCraftが社外のヘルプデスクAPIと連携する際、引数の順番や形式の違いをあちこちで変換していた問題を、Adapterパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Bridge:出力形式とチケット種別の分離
TicketCraftのレポート機能で、レポートの種類×出力形式の組み合わせごとにクラスが増殖していた問題を、Bridgeパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Composite:プロジェクト→サブタスク→チケットの階層
TicketCraftのプロジェクト集計処理が、チケットとサブプロジェクトを特別扱いして手動再帰していた問題を、Compositeパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Decorator:一覧表示への期限超過バッジ等の後付け装飾
TicketCraftの一覧表示で、バッジを追加するたびにクラス内のif文が増えていた問題を、Decoratorパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Facade:「作成+通知+履歴記録」の簡易窓口
TicketCraftのチケット登録処理で、3つのサブシステムを呼び出し側が正しい順番で呼ぶ必要があった問題を、Facadeパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Flyweight:大量のラベル(タグ)オブジェクトの共有
TicketCraftで大量のチケットに同じ名前のタグを付けるたびに、同じ内容のオブジェクトが何度も新規作成されていた問題を、Flyweightパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
Proxy:添付ファイルの遅延読み込み
TicketCraftのチケット一覧表示で、まだ必要ない添付ファイルの中身まで毎回読み込まれてしまっていた問題を、Proxyパターンで解決する。Before/Afterの実コードとコンパイル確認付き。
振る舞いに関するパターン
Chain of Responsibilityパターン|承認フローの分岐地獄を解消する
担当者→リーダー→マネージャーの承認フローがif-elseの分岐地獄になっていたTicketCraftを題材に、Chain of Responsibilityパターンで承認者を連鎖させ、拡張しやすい設計に書き直す。
Commandパターン|ステータス変更を「元に戻せる」ようにする
TicketCraftのステータス変更が履歴を残さず、誤操作を元に戻せなかった問題を題材に、Commandパターンで操作をオブジェクト化し、Undo機能を実現する。
Interpreterパターン|検索クエリの分岐地獄を解消する
TicketCraftの検索ボックス「status:open assignee:me」のようなクエリ解析がswitch文だらけになっていた問題を題材に、Interpreterパターンで項目ごとに解釈クラスを分離する。
Iteratorパターン|チケット一覧の並び替えを呼び出し側に漏らさない
TicketCraftの一覧表示で「最新順」「優先度順」を切り替える処理が、表示順ごとに別メソッドとして乱立していた問題を題材に、Iteratorパターンで巡回方法を差し替え可能にする。
Mediatorパターン|UI部品同士の直接参照を仲介者に集約する
TicketCraftのフィルタ欄・一覧パネル・詳細パネルが互いを直接参照し合うスパゲッティ状態だった問題を題材に、Mediatorパターンで部品間の依存を仲介者に一本化する。
Observerパターン|通知先が増えてもチケット本体を変更しない
TicketCraftのステータス更新通知が担当者へのメール送信とTicketクラスに密結合していた問題を題材に、Observerパターンで通知先を後から自由に追加できるようにする。
Mementoパターン|編集キャンセルで「元の内容」を復元する
TicketCraftの編集画面でキャンセルしても保存済みの内容が復元できなかった問題を題材に、Mementoパターンで編集前のスナップショットを保存・復元する。
Stateパターン|ステータスごとの「できる操作」をクラスで表現する
TicketCraftのチケット操作可否がif文200行超に膨れ上がっていた問題を題材に、Stateパターンでステータスごとの振る舞いをクラスに分離する。
Strategyパターン|チケット割り当てロジックを実行時に切り替える
TicketCraftのチケット自動割り当てロジックが単一クラスに固定され、要望のたびに条件分岐が深くなっていた問題を題材に、Strategyパターンでアルゴリズムを差し替え可能にする。
Template Methodパターン|クローズ処理の「共通の流れ」を固定する
TicketCraftのチケットクローズ処理がチケット種別ごとのswitch-case分岐で12箇所も修正が必要になっていた問題を題材に、Template Methodパターンで共通フローと差分を分離する。
Visitorパターン|階層構造を変えずに新しい集計処理を追加する
TicketCraftのプロジェクト階層に集計レポートやCSVエクスポートを追加するたび、Project・SubProject・Ticketの3クラスを毎回書き換えていた問題を題材に、Visitorパターンで操作を分離する。