ソフトウェアテストには、システムやプログラムの内部構造に視点をあてた「ホワイトボックステスト」と、内部構造を考慮せずにデータのインプットとアウトプットに視点をあてた「ブラックボックステスト」があります。ここでは、ホワイトボックステストについて、その目的や具体的な手法をご紹介します。
ホワイトボックステストとは
ホワイトボックステストは、プログラム内部の論理構造に着目して行うテストで、「クリアボックステスト」「グラスボックステスト」と呼ばれる場合もあります。
システムの内部構造を理解した上で、意図した通りに動作しているかを確認するテストとなるため、プログラムの知識が必要とされることから、単体テストフェイズに開発者自身の手で行われることが多いテストです。いつだれが行うかはプロダクトによっても異なり、単体テスト以外のフェイズ(統合テストやシステムテスト)で実施されることもあります。
ホワイトボックステストとブラックボックステストの違い
ホワイトボックステストがソフトウェアの内部構造をベースとしたテスト手法であるのに対し、ブラックボックステストは仕様ベースのテストです。ブラックボックステストでは、システムの要件や仕様をもとに入力を決め、それに対して期待する出力が得られるかを確認することでシステムが仕様通りに動作しているかをテストします。ブラックボックステストは内部構造を考慮しないため、プログラムの知識を必要としません。
ホワイトボックステストとブラックボックステストはアプローチが異なり、ホワイトボックステストでは確認できないような仕様の不備、設計漏れや抜けをブラックボックステストで検出するなど、互いが補完しあう関係にあります。
ホワイトボックステストのメリット
仕様ベースのブラックボックステストを実施することで、機能品質はある程度確認することができます。しかし、内部構造的には潜在的な不具合が残存している可能性があり、システムの拡張や改修、その他予期しないタイミングで重篤な不具合が露呈する可能性が依然として残ります。この、ブラックボックステストでは見つからない潜在不具合を見つけ出すのに有効なのが、ホワイトボックステストです。
ホワイトボックステストはコードが膨大になるほど適用が困難になってきますが、単体テストの段階でモジュール単体に対してホワイトボックステストを実施すれば、不具合を他への影響が少ない早期の段階で発見・修正することができます。このように、ホワイトボックステストを行うことで、システムの品質と安定性をより向上させることが可能になります。
ホワイトボックステストの技法
ホワイトボックステストには、プログラムコードのモジュールを構成する要素に着目してそれらが正しく実行されるかを確認する「制御フローテスト」と、ソフトウェアの中で使用されているデータや変数が正しいフローで使用されているかを確認する「データフローテスト」という2つの技法があります。ここでは、現在主流となっている「制御フローテスト」について紹介します。
制御フローテストは、プログラム上の「命令」「分岐」「条件」を指標とするテストです。どこに着目するかによって、さらに以下のように分けられます。
命令網羅=C0=ステートメントカバレッジ
分岐網羅=C1=デシジョンカバレッジ(ブランチカバレッジ)
条件網羅=C2=条件カバレッジ
それぞれの指標での網羅率を「カバレッジ」と呼びます。以降では、代表的なカバレッジの考え方を紹介します。
ステートメントカバレッジ(命令網羅/C0カバレッジ)
制御フローテストとして着目する要素に「命令文」を選択した場合のカバレッジ基準を、「ステートメントカバレッジ(statement coverage)」といいます。プログラム内の命令文をどの程度テストしたかが指標となり、コード内のすべての命令文を少なくとも1回ずつテストするとステートメントカバレッジ100%が達成できます。
例えば、
if(A=真{
“Aは真”;
}else{
”Aは偽”
}
とした場合は、if文が実行されるとステートメントカバレッジが100%となります。
デシジョンカバレッジ(分岐網羅/C1カバレッジ)
コード内の「分岐」に着目した場合のカバレッジ基準で、「デシジョンカバレッジ(decision coverage)」、のほかに、「ブランチカバレッジ(branch coverage)」とも呼ばれます。コード内の判定条件をどの程度テストしたかが指標となり、コード内のすべての判定条件について真/偽をテストするとデシジョンカバレッジが100%になります。
例えば、
if(A=真{
“Aは真”;
}else{
”Aは偽”
}
とした場合は、
・A=真
・A=偽
の2パターンのテストを行うことによってデシジョンカバレッジが100%になります。
デシジョンカバレッジとブランチカバレッジ
C1カバレッジは、「デシジョンカバレッジ」や「ブランチカバレッジ」と呼ばれます。
「デシジョンカバレッジ」はコード内の判定条件(decision)の判定結果がそれぞれ少なくとも1回出力されるようにテストを実施するのに対し、「ブランチカバレッジ」はコード内の分岐(branch)の真と偽の結果が少なくとも1回は出力されるようにテストを実施します。
”やっていることは同じでは?”と思ったあなた、正解です。両者は内容的に同じと考えて差し支えないため、ここでも同じものとみなして説明しています。
条件カバレッジ(条件網羅/C2)
コード内の「条件」に着目した場合のカバレッジで、「コンディションカバレッジ(condition coverage)」とも呼ばれます。デシジョンカバレッジがコード内のすべての判定条件を通った結果の「真/偽」をテストするのに対して、条件カバレッジではコード内の条件それぞれの真/偽の結果を網羅するようにテストします。そのため、条件カバレッジを100%にしても、デシジョンカバレッジが100%にならないケースがあります。
例えば、
if(A & B){
“AとBは真である”;
}else{
”AとBは真ではない”
}
とした場合、
・A=真 B=偽
・A=偽 B=真
で条件カバレッジ100%を達成できますが、2パターンともに結果は偽判定になるため、デシジョンカバレッジは50%となります。
マルチコンディションカバレッジ(複合条件網羅)
C0、C1、C2以外にも、さらに網羅性を挙げたカバレッジ基準があります。「マルチコンディションカバレッジ(複合条件網羅)」はコード内の条件の真/偽の組合せをすべてテストするカバレッジ基準で、「マルチコンディションカバレッジ(複合条件網羅)」を満たせば、デシジョンカバレッジ、ステートメントカバレッジも満たせます。ただし、テスト工数が膨大になるため、次に紹介する「改良条件判定カバレッジ(MC/DC)」に置き換えて実施されることが多い手法です。
改良条件判定カバレッジ(MC/DC)
デシジョンカバレッジと条件カバレッジを満たす手法で、各判定条件の真/偽すべてと、ある条件を変更した場合に複合条件の判定(最終的な結果)がかわるケースをすべてテストします。「改良条件判定カバレッジ(MC/DC)」は、自動車/航空/宇宙ソフトウェアなど、セーフクリティカルなソフトウェアに採用された事例があります。
以上のように、制御フローテストには様々な手法がありますが、どのようなシステムにはどのカバレッジ基準を採用する、ということは一概には言えません。 コードカバレッジ(コードをどの程度網羅したか)が高いほど担保される品質は高水準になりますが、当然ながらカバレッジに比例してテストにかかる工数(時間、コスト)が増加します。そのため、どのカバレッジ基準を採用するかは、対象が何をするシステムなのか、障害発生時の影響度はどの程度か(例えば、人命にかかわる、大きな経済損失を生むなど)を考慮して選択します。
さらに、テスト対象とするモジュールがシステム内でどの程度の重要度を持つかなどの観点も加え、モジュールやシステム単位で選択するカバレッジ基準と目指すカバレッジ率を定義していく必要があります。
ホワイトボックステストで悩んだら
ホワイトボックステストを実際に行うためにはこれらの技法を理解し、最適なカバレッジを選択する必要があるため、ハードルが高いと感じる方も多いと思います。テストのプロに相談してみてはいかがでしょうか?