この本について
本書のスコープは欲張りなもので、放置されたレガシーコードベースを、あなたの組織に価値をもたらす保守が可能で十全に機能するソフトウェアへと変身させるのに必要なことを、すべて伝授しようというのです。もちろん、1冊の本で、すべてを完全に網羅しようとする試みは、達成できるわけがないのですが、私はレガシーソフトウェアの問題点に対して、さまざまな角度からアプローチすることで、それに挑んでいます。
コードがレガシーに(というのは、大ざっぱに言って、保守が困難に)なるには、多くの理由がありますが、ほとんどの原因は、技術ではなく人間に関係しています。もし人々のコミュニケーションが十分でなければ、人が組織を離れるとき、コードについての情報が失われます。同様に、開発者、管理者、そして組織全体が、仕事の優先順位を正しく設定しなければ、「技術的負債」(technical debt)が蓄積して維持できないレベルに達し、開発のペースが、ほとんどゼロにまで低下しかねません。このため、本書は折に触れて(とくに、時の経過に従って情報が失われるという問題を論じるときは)組織に関する側面を取り上げます。問題を意識することが、それを解決するための、重要な第一歩となるのです。
ただし、この本に技術的な内容がないというのでは、まったくありません。本書は、Jenkins、FindBugs、PMD、Kibana、Gradle、Vagrant、Ansible、Fabricなどといった、広範囲なテクノロジーとツールを扱います。数多くのリファクタリングパターンを詳細に取り上げ、モノリスからマイクロサービスにいたるさまざまなアーキテクチャにおける関連メソッドを論じ、コードをリライトするときにデータベースを扱う戦略も見ていきます。
第1部 はじめに
もしあなたが、それなりに大きなレガシーコードベースのリエンジニアリング(再設計)を計画しているのなら、時間をかけて下調べを行い、正しい方法で着手していることを確認すべきだ。この本の第1部では、大量の下準備を行うが、それは、あとで十分に報われる作業だ。
第1章では、「レガシー」とはどういう意味なのかを調べ、保守が困難なソフトウェアが、どのような原因で作られるかを探る。第2章では、ソフトウェアの現状を数量的に検査して、リファクタリングの構造とガイドを提供するように、検証(インスペクション)の基盤(インフラストラクチャ)を設定する。
あなたのソフトウェアの品質を計るのに、どのツールを使うかは、あなたが決めることだ。その選択は、実装に使う言語や、あなたが使った経験のあるツールなどに依存するだろう。第2章で使うのは、Javaで人気のあるソフトウェア品質検証ツール、FindBugs、PMD、Checkstyleだ。また、継続的インテグレーション(CI)サーバーとしてJenkinsをセットアップする方法も示す。このJenkinsについては、本書の随所で触れることになる。
第1章 レガシープロジェクトの難題を理解する
この章で学ぶこと
レガシープロジェクトとは何か
レガシーコードとレガシー基盤の例
レガシープロジェクトを作り出す組織の要素
改善計画
こういうシーンに覚えがないだろうか。あなたは仕事場に出勤し、コーヒーを手に、最新の技術的ブログに目を通す。最初に読むのは、シリコンバレーのヒップな若い起業家が、ファッショナブルなプログラミング言語Xと、NoSQLデータストアのYと、ビッグデータツールのZを組み合わせて世界を変えるという話。けれども、あなたの気分は沈み込む。これらのテクノロジーを、自分の仕事に使ってみるような時間は、取れないだろう。製品を改善するために使うことなど、なおさら無理だろう、と思って。
どうして、できないのか? それは、あなたが何億行もありそうな、テストもされず、ドキュメントもなく、とうてい理解できそうにないレガシーコードの保守を任されているからだ。そのコードは、あなたが最初にHello Worldを書いたときよりも前から製品化されていて、もう何十人もの開発者が入れ替わり立ち替わり、手を染めている。就業時間の半分は、コミットを検査して、何かリグレッションを起こしていないかチェックすることに費やされ、残りの半分は、避けようのないバグが侵入したため、その消火作業に費やされる。そして、一番気が滅入るのは、時間が経過するにつれて、コードベースにもっとコードが追加され、どんどん壊れやすくなり、問題が悪化していくことだ。
けれども、絶望してはいけない。まず最初に、あなたが孤独ではないことを思い出そう。平均的な開発者は、新しいコードを書くよりも、ずっと多くの時間を、既存のコードの仕事に費やしている。そして開発者の大多数は、何らかの形でレガシープロジェクトを扱わなければならないのだ。第2、レガシープロジェクトには、最初はどれほど朽ち果てて見えても、必ず蘇生する希望があることを思い出そう。本書の目的は、まさにそれを行うことである。
この最初の章では、我々が解決しようとしている各種の問題のサンプルを見て、蘇生のためのプランを立て始める。
第2章 スタート地点を見つける
この章で学ぶこと
リファクタリングの努力を、どこに集中させるかの判断
レガシーソフトウェアに対するポジティブ思考
ソフトウェア品質の計測
FindBugs、PMD、Checkstyleでコードベースを検査するインスペクション
Jenkinsによる継続的インスペクション
第1章で、レガシーソフトウェアとは何であり、なぜそれを改善すべきなのかは明確になったと思う。この章では、改善策の立てかたと、その策を実施するときに進捗を測る方法を見ていく。
第2部 コードベース改良のためのリファクタリング
第2章ではインスペクションの基盤技術をセットアップした。これで、レガシーソフトウェアの「リエンジニアリング」を開始するための準備が整った。
第3章では、コードベースをリファクタリングするか、それとも捨て去ってゼロから書き直すリライトかという、非常に重要な選択について論じる。その判断は、ガイドとなる情報が足りないプロジェクトの初期段階で下されるので、しばしばリスクを伴う。そこで、よりインクリメンタルなアプローチによって、そのリスクを軽減する方法も学ぶ。
第4章、第5章、第6章では、ソフトウェアのリエンジニアリングを行う3つの選択肢について詳しく述べる。その3つとは、リファクタリングと、リアーキテクティング(re-architecting)と、ビッグリライト(Big Rewrite)だ。これらは、ある意味では互いの変種みたいなものだが、作業対象のスケールが異なる。リファクタリングは、コードの構造をメソッドやクラスのレベルで変更する。リアーキテクティングは、モジュールやコンポーネントのレベルで行うリファクタリングだ。そしてビッグリライトは、可能な限り高いレベルで行うリアーキテクティングだ。
第4章では、私がこれまでにしばしば自分で使って成功したか、あるいは成功するのを見たことがある、数々のリファクタリングパターンを紹介する。第5章では、モノリシックなJavaアプリケーションを、いくつもの相互に独立したモジュールに分割するケーススタディを提供するほか、モノリスとマイクロサービスのメリットを比較する。最後に第6章では、大きなソフトウェアのリライトを成功させるためのヒントを提供する。
第3章 リファクタリングの準備
この章で学ぶこと
あなたのリファクタリング計画に皆を参加させる
リファクタリングか、ゼロ(スクラッチ)から書き直すかを決める
リファクタリングする価値があるものとないものを区別する
この章では、現実のコードベースに大規模なリファクタリングを実行するとき直面することが多い「技術的ではない問題」に目を向けよう。理想的な世界なら、美しいコードを作るのに完全な自由と無制限の時間を使えるだろうが、ソフトウェア開発の現実は、しばしば妥協を強いられるものだ。もしあなたがチームのメンバーとして働いていて、そのチームが、(計画と目標、予算と期限を持つ)大きな組織の一部であれば、あなたの同僚である技術者たちと、技術者ではない関係者たち(stakeholders)の両方から、進むべき最良の道についての同意を得るため、あなたの交渉術を発揮する必要があるのだ。
親身に忠告するのだが、リファクタリングは常に、組織の目標を念頭に置いて行う必要がある。言い換えると、誰があなたに給料を払っているのかを忘れてはいけない。リファクタリングは、それがビジネスに長期的な価値をもたらすと、あなたが証明できるときにだけ行うべきだ。
大きな改良プロジェクトに乗り出す前に、答えなければならない重要な質問のひとつは、リファクタか、それともリライト(書き直し)か、である。ソフトウェアの品質を、リファクタリングだけで、本当に満足できるレベルまで上げられるだろうか。それとも、ゼロからの書き直しのほうが賢明な選択だと言えるほど、そのソフトウェアは、どうしようもない状態なのだろうか。これは、最後には、あなたとあなたのチームが自分で答えなければならない質問だが、私もできるだけ、あなたが判断を下す助けになるように序言を提供しよう。また、完全なリライトにつき まとうリスクを軽減させるハイブリッドなアプローチも論じる。
第4章 リファクタリング
この章で学ぶこと
リファクタリングで規律を維持する方法
レガシーコードの「気になる匂い」と、それぞれの消臭術
自動テストでリファクタリングをサポートする
この章では、レガシーコードとの戦いで最も重要な武器となるリファクタリングを見ていく。効果的なリファクタリングを行うために一般的なヒントを提供するほか、私が現実のコードで使うことの多い個々のリファクタリング技術も、いくつか紹介する。さらに、レガシーコード用にテストを書くためのテクニックも見ていくが、これはリファクタリング後に何も壊していないことを確認するうえで欠かせないものだ。
第5章 リアーキテクティング
この章で学ぶこと
モノリス的なコードベースを複数のコンポーネントに分割する
1個のWebアプリケーションをサービスのコレクションに分散する
マイクロサービスの長所と短所
前章で見たリファクタリングのテクニックは、コーディングの段階で行う改善だった。リファクタリングでは、そこまでしか到達できないが、ときにはもっと大きく考える必要がある。この章では、ソフトウェアの構造全体を改善する方法を見ていこう。つまりソフトウェアを、より小さく保守しやすいコンポーネントに分割する方法だ。また、1個のアプリケーションを複数のサービス(ネットワークを介して通信するサービスあるいはマイクロサービス)に分割する方法についても、長所と短所を論じる。