不具合にテストを書いて立ち向かう

テストを行っている品質保証チームや、実際にシステムを使っているお客様から不具合が報告されたとき、あなたはどう思いますか? 悲しんだり、恥ずかしいと思い、不具合修正にすぐに着手したいと気がはやるのが人情というものです。しかし、焦っているときに行う作業はしばしば視野が狭く、一つの不具合修正が三つの新たな不具合を生んでしまうようなことになりがちです。

テスト駆動開発(TDD : Test Driven Development)は、プログラマが自分の不安を克服し、自分が書くコードに自信を持ちながら一歩一歩進んでいくための手法です。不具合の発生は、端的に言えばこれまでの「自信」を揺らがせる事態です。テスト駆動開発者は不具合にどう立ち向かうのでしょうか?

やはりテストを書いて立ち向かってゆくのです。私はテスト駆動開発を数年間実践してきた中で、心がけているひとつの「掟」があります。それは「不具合の修正時には必ず先に不具合を再現する自動テストを書いてから修正する」というものです。これはもちろん私の発案ではなく、 XP(eXtreme Programming) や TDD の先達から学び、それを実践するうちに私にも身についてきたものです。例えば『テスト駆動開発入門』では、次のように記されています。

欠陥が報告されたときに最初にすべきことは何か。→ 失敗する最小のテストを作成し、実行した後に修正する。

回帰テストは、完全な先見があれば、最初のコーディング時に作成していたテストである。回帰テストを作成するたびに、どうすれば、最初にそのテストを作成できたかを考えよう。

ーー 『テスト駆動開発入門』 p.136 回帰テスト

不具合修正時のテストは、次のような手順で行います。

  1. 手元で不具合を再現させる
  2. コードを注意深く調べ、不具合を発生させている最小の部分を絞り込む
  3. 最小レベルで不具合を再現させ、不具合が修正されたら通るような自動テストコードを書く
  4. 書いたテストコードを実行し、落ちることを確認する
  5. 不具合を修正する
  6. 書いたテストコードが通ることを確認する
  7. 全てのテストを実行し、不具合修正が他の部分を壊していないことを確認する

こう書くと面倒に感じるかもしれませんが、不具合修正時のテストには、さまざまなメリットがあります。

不具合が本当に自分の考えた原因で発生しているかが明らかになる

バグ修正は「当てもの」です。どんな原因で不具合が発生しているのかを、プログラマは推理しなくてはなりません。不具合を再現させるテストが落ちることを確認することで、「ここが原因だろうと考えて修正したら、全然違う場所が原因だった」というような事故を避けることができます。また、不具合修正に未着手のうちにテストが成功した場合、テストにバグがあるか、考えている不具合の原因が異なるのか、とにかく自分の理解がまだ浅いことを意味しています。

対象コードと対象領域に対する理解が深まる

最小単位を探すという行為は原因を深く追い、考えることにつながります。不具合はなぜ発生したのでしょうか。対象領域の理解が浅かったのかもしれません。コードが読みにくかったのかもしれません。不具合修正は新機能の追加とは異なり、既存コードに対する調査の割合が大きくなります。それは既存のコードと対象領域に対する理解を深める良い機会になります。

自分の弱点、気づきにくい点がわかる

自分ではしっかりとテストを書いているつもりなのに不具合を世に出してしまったということは、自分の思い至らなかったテスト、視点があるということです。自分の弱点や気づきにくい点は、普段コードを書いているだけでは得られない視点であり、非常に貴重です。不具合修正時のテストを書くときには、同様の過ちを犯している箇所は無いかを必ずチェックしましょう。プログラマも人間ですから、同じような過ちを犯している場合があるのです。

テストの堅牢さ、価値が上がる

自動テストの利点は、いつでも同じように実行できることです。不具合修正を自動テストの形にすることで、不具合が本当に直ったか即座に確認できます。さらにその自動テストを残しておくことで、今後不具合が再発した場合でも、テストが落ちることによってすぐに分かるようになります。不具合を克服して立ち上がるたびに、テストコードの網羅性は上がり、既存コードに対する自信も深まります。

「テストを書いている時間は無い」と言われたり、不具合修正時にテストを書くことをひどく遠回りに感じることがあるかもしれません。しかし、患部の絞り込み、修正中の確認、他の部分への影響の確認、再発防止などを考えると、不具合にテストを書いて立ち向かうのは合理的かつ効率的な手法なのです。

テストを友として自信を持ちながらコードを書く。それがテスト駆動開発を身につけたプログラマの仕事のやり方です。

一番の近道は遠回りだった。遠回りこそが俺の最短の道だった。

ーー ジャイロ・ツェペリ(STEEL BALL RUN スティール・ボール・ラン 21巻)

このエントリについて

このエントリは TDD Advent Calendar 2013 - Qiita の 25 日目の参加エントリであり、はてな blog に私が引っ越して書く最初のエントリでもあります。

記事本文は『プログラマが知るべき97のこと』に収録された私のエッセイの収録前原稿を出版社了承の下でライセンス CC BY 3.0 で公開したものです。最後の引用をスペースの都合で書籍に載せられなかった無念さが伝われば幸いです。

もう既に多くの方に気付かれてしまいましたが、寄稿したエッセイのタイトルは五七五のリズムになるように工夫しました。

『プログラマが知るべき97のこと』には、プログラミングに関する沢山の良質なエッセイが寄稿されています。まだお読みでない方は、この機会に是非お手にとってみてください。

プログラマが知るべき97のこと

プログラマが知るべき97のこと

  • 発売日: 2010/12/18
  • メディア: 単行本(ソフトカバー)

https://creativecommons.org/licenses/by/3.0/