テストの基礎

テストの種類

一口にテストと言っても、さまざまなものがあります。
それぞれのテストには、役割、意味、意図があります。
それらを理解すると、テストの内容がより良くなり、また、局面に見合ったテストが講じられるようになります。

単体テスト・結合テスト・システムテスト

最初に、テストの話ではなくソフトウェアの構造に関して説明します。

  • ソフトウェアは、さまざまなプログラムの部品によって構成される。
  • それらプログラムの部品の最小単位は、「関数」などと呼ばれる。
  • その「関数」を組み合わせて、「機能」が作り上げられる。
  • 更に、その「機能」を組み合わせて、「システム」が作り上げられる。

ソフトウェアのテストは、最初は小さな単位で行い、少しずつ粒度を大きくしていきます。

  • まず、プログラムの最小単位である「関数」を対象に、「単体テスト」を行う。
  • その次に、いくつかの関数を組み合わせて、「結合テスト」を行う。
  • 最後に、いくつかの機能を組み合わせて、「システムテスト」を行う。

上記のように、「単体テスト」→「結合テスト」→「システムテスト」といったように、テスト対象の粒度を、最初は小さく、それからだんだんと粒度を大きくしていきます。
その理由は以下のとおりです。

  • テスト対象の粒度が大きくなるほど、プログラム上で未検証の部分が増えていくため
  • テスト対象の粒度が大きくなるほど、バグは見つけにくくなるため
  • テスト対象の粒度が大きくなるほど、テストでバグが見つけられても、原因調査がやりにくくなり、工数がかかるため。

また、手戻りが大きくなり、コスト的にも時間的にも無駄が生じるため。

これら単体テスト、結合テスト、システムテストのことを、テストレベルと呼びます。
テストレベルという用語は ソフトウェア開発プロジェクトで頻繁に使われるものです。しっかり覚えておきましょう。

機能テスト、非機能テスト

機能テストは、テスト対象で定義されている機能が仕様どおりに動作するかをテストするものです。
一方、非機能テストには、たとえば、以下のようなものがあります。

  • 性能テスト
  • 信頼性テスト(大容量テスト、エージングテストなど)
  • ユーザビリティテスト

ソフトウェアやシステムを開発する上で、どんな機能を持たせる必要があるか定義するものを「機能要件」と呼びます。
また、機能には直接的に関係しないものの、そのソフトウェアやシステムで具備すべき特性を「非機能要件」と呼びます。
テストでは、検証すべき対象は機能要件だけでなく、非機能要件も漏らさずテストするのが大切です。
非機能テストではどんなものを行う必要があるかを整理し定義するのは、多くの場合、「テスト計画」で行います。

ホワイトボックステスト、ブラックボックステスト

ホワイトボックステストとは、テスト対象のプログラムの構造を把握した上で行うテストのことです。
ホワイトボックステストの主な観点は、プログラムが設計したとおりに、実装したとおりに動作するか、確認することです。

一方、ブラックボックステストは、テスト対象のプログラムの構造は把握しない状態で、プログラムが仕様どおりに動作するかを確認するテストです。
文字どおり、テスト対象の構造が不明(ブラックボックス)である状況でテストすることから、このような呼び方がされています。
前述した「テストレベル」で言うと、ホワイトボックスとブラックボックスの使い分けは、多くは以下のように行われます。

  • 単体テスト:ホワイトボックステスト
  • 結合テスト:ホワイトボックステスト
  • システムテスト:ブラックボックステスト

ホワイトボックステストの狙いは、テスト対象のプログラムを細かいところを隅々まで検証することです。
対して、ブラックボックステストでプログラムの1行1行を細かく検証するのは非常に困難です。ブラックボックステストをいかに密に行っても、どうしても検証漏れが起きてしまいます。
では、ホワイトボックステストをしっかり行えばブラックボックステストは必要無いのかと言うと、そうではありません。
ホワイトボックステストは、前述したとおり、プログラムが設計したとおりに、実装したとおりに動作するかを主な観点としています。このため、プログラムの設計に漏れ抜けがあった場合や仕様の誤認があった場合、ホワイトボックステストでは検出できず、バグを見逃してしまう可能性があります。このため、ブラックボックステストも行う必要があります。
ホワイトボックステストとブラックボックステストは、それぞれに役割があり、双方が補い合っているのです。

検証と妥当性確認(V&V)

テストには大きく分けて、「検証」と「妥当性確認」の2つの視点があります。
「検証」とは、仕様通りに動作するか、製品が正しく動作するかを確認することです。
「妥当性の確認」とは、その製品によって目的としていたものは達成できているか、正しい製品が開発できているかを確認することです。
検証はVerification、妥当性確認はValidationと言い、「Verification and Validation」または「V&V」 と呼ばれることがあります。
ここでポイントとなることは、検証(Verification)の視点でのテストでバグがゼロであったとしても、品質が高いとは一概には言えない、ということです。
たとえば、ユーザビリティが悪く、使い勝手が悪かったらどうでしょうか。業務を遂行する上でしばしば起きる例外処理に対処するのに、非常に煩雑な手順が必要だった場合はどうでしょうか。
その製品がたとえ仕様で定義したとおりに動作していても、その製品を使うことで本来やりたかったことが十分できなかったとしたら、それはユーザーにとって品質が良いものとは言えません。
検証(Verification)の視点でテストするか、妥当性確認(Validation)の視点でテストするのか、またはその両方なのか。テスト計画 策定などの早期の段階で、テストの指針や目的をはっきりさせておくことが重要です。 そのテストに求められているものが抜け落ちた状態で先に進んでしまうと、大きな手戻りや作業追加が発生し、リカバリするのが非常に困難になるためです。

動的テスト、静的テスト

テスト対象のプログラム または システムを実際に動かして検証するのを、「動的テスト」と言います。
対して、テスト対象を動作させないで検証するのを「静的テスト」と言います。静的テストの代表的ものとしてレビューがあり、その他にも、静的解析や形式手法といったものもあります。
レビューや静的解析といった静的テストの利点は以下のとおりです。

  • 動的テストで再現させるのは困難な、微妙なタイミングなどで発露するバグは、レビューなどであれば比較的 発見しやすい
  • 動的テストであれば、バグの発見から修正まで、バグ票の起票と原因解析で相応の時間と労力がかかる。対して静的テストのレビューなどでは、不具合箇所がピンポイントで見つけられ、対処できる。

品質管理、品質保証する手段は、動的テストの他にも静的テストという手段もあります。
その組織や・プロジェクトで、静的テストと動的テストをどう実施していくか、戦略を講じるのが必要です。

手動テスト、自動テスト

マウスクリックやテキスト入力、実施結果の良否判定などのテストのオペレーションを、人の手で行うのを「手動テスト」と呼びます。
対して、テストのオペレーションをコンピュータで行うものを「自動テスト」と呼びます。
自動テストの利点はいくつかあり、導入する組織が増えています。

  • テストのオペレーションが迅速で正確(誤操作・誤認識などのヒューマンエラーが無い)
  • 繰り返し何度も実施することでコスト的なメリットが得られる

ただし、自動テストを導入・運用するにあたって、いくつか前提条件もあります。

  • テスト対象が自動テストを実施できる構造になっていること
  • 自動テストの環境を開発し、セットアップするコストと労力がかかること
  • 仕様変更・設計変更が生じたら、それを自動テスト環境にも反映する必要があること

スクリプト型テスト、非スクリプト型テスト

テストを実施するパターンとして、「スクリプト型テスト」と「非スクリプト型テスト」があります。
スクリプト型テストとは、テストオペレータがテスト手順書を参照しながら、テストの操作を実施するものです。
自動テストも、予め実施手順がプログラム化されているため、スクリプト型テストの一つと言えます。

対して非スクリプト型テストは、テストの実施手順が予め定まっていないものを指します。
たとえば、ランダムに操作を行うモンキーテストや、テストの熟練者が仕様の把握とテスト対象の動きを観察しながら行う探索的テストは、非スクリプト型テストに分類されます。
スクリプト型テストの利点は、以下のとおりです。

  • テスト設計の質が担保しやすい。テスト設計の内容を文書化すればレビューもしやすい
  • テストの再利用がしやすい

非スクリプト型の利点は、以下のとおりです。

  • テスト設計の手間をスキップできるので、テストの期間を短縮できる
  • テストの内容を臨機応変に変えられる

スクリプト型テストと非スクリプト型テストは、双方とも目的が別のものなので、どちらが優れているかという議論は成り立ちません。
そのテスト対象とプロジェクトの状況に応じて、スクリプト型テストと非スクリプト型テストを、どこでどのように使うのか、戦略を講じることが必要です。