GAIO CLUB

2010年04月01日

要素分析による単体テストの標準化と定着運用

技術情報
ソフトウエア品質改善を目的に、コーディング後に行うソフトウエアの単体レベルでの検証「単体テスト」を開発プロセスに組込み、本格運用するケースが増えています。自動車制御ソフトはもとより、最近ではカーナビなど自動車ITS系の開発、デジタル家電製品などの開発にも採用が拡大しています。

本特集では、「単体テスト」をプロセス化し、定着運用させる際の大きな課題の1つである、単体テストデータ設計の標準化について取り上げます。ガイオは、「単体テスト代行サービス」により、数多くの関数テストをこなしており、この経験を元に確立した、単体テストデータ設計の標準化を行う方法「要素分析」について説明します。

ソフト品質改善のための「単体テスト」の採用が増加

  • ソフトウエア品質改善を目的に、コーディング後に行うソフトウエアの単体レベルでの検証「単体テスト」を開発プロセスに組込み、本格運用するケースが増えています。この「単体テスト」は、従来は、自動車制御ソフト、航空機分野、原子力プラント制御など、安全性に関わる分野で、特に要求が高い検証項目でしたが、最近では、カーナビなど自動車ITS系の開発、デジタル家電製品などの開発にも採用が始まっています。

    下の表は、ガイオの単体テストツールのユーザー数の変化を示しています。2008年ごろから、自動車ITS系、デジタル家電系のユーザーの割合が、急激に増えており、従来の限られた分野から他の分野にも「単体テスト」の採用が拡大していることが分かります。
  • ガイオ単体テストツール「カバレッジマスターwinAMS」のユーザー割合の変化

単体テスト実施には「標準化」が必要

単体テスト採用業種の拡大による課題

従来の自動車制御ソフト等の分野では、単体テストを始めとした検証は、要求される高い品質を維持することが主な目的で実施されてきました。ソフト品質の維持は、もちろん他の分野のソフトに対しても要求項目であることは間違いないのですが、最近になって採用が盛んになってきた自動車ITS系、デジタル家電系製品などにおいては、別の側面の課題が出てきました。

様々な技術者のスキルに依存しない「標準化」が必要

下の図は、V字開発プロセスを示しています。V字の上半分の工程(オレンジ色)である要求分析、基本設計、機能設計は、製品の性能などを決める競争領域に関わる部分です。ここは専門的な技術者が関わることが多く、技術者の人数は比較的少数です。

それに比べて、V字の下半分の工程(緑色の枠線)である詳細設計、コーディングのエリアは、上流で決められた仕様に対する作り込みの工程であり、多くのエンジニアが関わる領域です。自ずと様々な分野のソフト開発者が関わることが多くなり、開発者のスキルにバラツキが多くなる傾向があります。

コーディング後の検証工程として「単体テスト」を行う場合も、関数に潜む不具合の要因は様々であるため、これらの不具合漏れなく検出できるかどうかは、開発者のスキルに依存する傾向が強くなります。このままでは、プロジェクト全体のソフト品質を同じ指標で判断できなくなります。

単体テストを実施して正しくソフト品質の確認、検証を行うためには、技術者のスキルに依存しない単体テスト設計、標準化が必要です。
V字開発プロセス

単体テスト実施の課題

単体テストの実施、運用には、多くの課題があります。

・単体テストの工程を自動化、効率化し、工数を掛けないテストはどの様に実現するか?
・関数の不具合を検出するための単体テストデータを、どのようにして設計するか?
・単体テスト設計の工程をマニュアル化して、テスト実施者のスキルに依存しないテスト設計をどの様に行うか?

単体テスト実行工程の自動化や効率化に関しては、ガイオの「カバレッジマスターwinAMS」を始めとする単体テストツールを利用すれば、テスト実行の工程のほとんどは自動化され、工数削減が期待できます。

しかし、不具合を検出するための単体テストの入力データの設計については、現在のどのツールを利用しても、満足なテストデータを作成することは難しく、実際は、テスト担当者が関数の仕様情報やソースコードを参照しながらの手作業でテスト設計を行わなければなりません。単体テスト設計は、関数に含まれる様々な不具合要素を検出する作業であるため、作成されるテストデータは、テスト設計者の経験やスキルに依存しがちであり、プロジェクト全体で関数の単体評価を、同じ指標で行うことが難しいのが実情です。

単体テスト設計に必要なテストの「観点」

本来、関数に対する単体テストには2つの要因があります。1つは、コーディングしたソフト(関数)が、関数設計仕様に定義された動作を行うかどうかのテストで、「ブラックボックス」観点のテストと言われます。もう1つは、関数のソースコードを対象に、コーディング上のミスがないかどうかを調べるテストで、「ホワイトボックス」観点のテストと言われます。

・ ブラックボックス観点:仕様書に定義された正常動作の出力、例外条件動作、変数のレンジテストなど
・ ホワイトボックス観点:C言語コーディングで起こる不具合 → キャストミス、オーバーフロー、デッドコードなど

従って、関数に含まれる不具合を網羅的に検証するためには、この2つの観点の要素を漏れなく抽出して、テストデータ(テストベクター)に含めておくことが必要です。

しかしながら、これらのテスト要素は種類が多く、また、テスト設計者のスキルやセンスによってテスト要素の抽出内容が変わってしまうため、予め、要素抽出方法を明確に定義して設計方法を標準化しておく必要があります。また、各開発者が設計した単体テストデータに含まれる要素を、後から客観的に判断できるようにすることも必要です。

テスト設計者のスキルに依存しにくい設計手法を自ら確立

  • ガイオは、みなさまのソースコードを受託して、単体テスト業務を代行して行う「単体テスト代行サービス」を2005年から継続して提供してきました。ここでもテスト作業を行うに当たり、テスト設計者の経験やスキルに依存しない設計方法を確立することが必要でした。
  • 要素分析
そこで、ガイオでは、単体テストの熟練者、経験の浅い担当者、協力会社の担当者など、どのような人でも同じテスト設計が可能な手法を、単体テスト代行サービスの経験を通して試行錯誤を繰り返し確立してきました。単体テスト設計を標準化するこの手法を「要素分析」と名付けてマニュアル化しました。

単体テスト設計に必要な 「テスト設計指針」を標準化する「要素分析」手法

  • 単体テスト設計には、テストの設計方法を明記した「テスト指針」が必要です。
  • テスト指針書
ここに「要素分析」の手法を用いると、テスト指針が単純化され明確になります。その結果、技術者が自分の経験やスキルを基に判断する要素が少なくなり、テスト設計のマニュアル化や、テスト指針の遵守が容易になります。

要素分析とは、多種にわたるテスト要素を整理して一覧表にすることで、関数の各要素(変数、引数、戻り値など)に含めなければならないテスト要因を明確にする手法です。例えば、次のような関数の単体テスト設計を例に説明します。※この例は、ブラックボックス観点のみに絞ったものです。

関数仕様サンプル

関数「func()」の仕様が次の様に定義されていたとします。

func() 関数仕様

機能概要:2つの引数の加算値を求め、戻り値として返す。ただし、下の例外条件に従う。

入力:unsigned char型 引数 inA, inB
入力値レンジ 0~150

戻り値: unsigned char型、2入力inA, inBの加算値

例外条件:
入力値の何れかがレンジ外の時は、戻り値として0を返す
加算値が200以上の時は、戻り値として200を返す

この要求仕様に対して、ある技術者が下のようなコーディングを行ったとします。今回は、この関数に対して要素分析を行い、単体テストにより、作り込まれている不具合を抽出する例を挙げてみます。

この様な簡単なサンプルであれば、「勘の良いエンジニア」の方ならソースコードを眺めただけで、不具合が特定できるかも知れません。ただし、実際のプロジェクトでは、不具合はソースに埋もれて潜在する可能性が高く、発見が困難です。

ここで示す例は、作成したテスト指針に従ってテスト設計を行えば、「エンジニアのスキルに依存せず」、不具合を発見できることがポイントです。
func() 関数仕様

テスト指針書に定義された 要素分析方法のサンプル

単体テスト実施前に、単体テスト設計が設計者のスキルに依存しないように、テスト方法を定義した「テスト指針」を作成します。例えば、以下のように「テスト設計指針」を作成したとします。

要素分析を行う際の指針

・変数が境界条件を持つ場合、境界値に対して、[境界値-1], [境界値], [境界値+1]の3値を付与すること
・変数の型に対して、[最大値], [最小値]を付与すること
・同値分割により範囲が定められたときは、有効なレンジの中心値を代表値として付与する

この指針書に基づきこの関数の入力要素分析表を作成します。この関数の入力要素は2つの引数(inA、inB)のみです。以下のように、テスト指針書の指示に従って各要素への付与値を決定します。この作業はテスト指針に従って行う作業であり、テスト設計者の判断を入れず、「機械的」に行うことが重要です。
要素分析を行う際の指針

要素分析表に抽出した付与値を組み合わせて 単体テストデータを作成

要素分析表にまとめた各要素への付与値を組み合わせて、実際の単体テストデータを作成します。この組合せ方法も、テスト方法を定義した「テスト指針」に従います。例えば、以下のように「テスト指針」を作成したとします。

組合せを作成する際の指針

・境界条件値は、対象付与値の全数組み合わせを作成する
- カバレッジの観点で全パスを網羅するために境界条件をすべて組み合わせる

・最大値、最小値は、対象付与値の全数組み合わせを作成する
- 演算のデータカバレッジを網羅するため、最大最小値の組合せで起こる不具合を検出するため

・代表値がある場合は、少なくとも1度はテストパターンに含まれるようにする
- 正常系のテストサンプルとして含める

この指針書に基づき、正しく組合せを作成します。この組合せも、テスト指針に従った「機械的」作業に徹します。これにより、各テスト要素が正しくテストデータに含まれます。

組合せを作成する際の指針

関数設計仕様情報から期待値を設定

要素分析表に抽出したテスト要素を含めたテストパターンが作成できたら、テストデータに期待値を設定します。この期待値は、関数の設計仕様を基に正しく設定する必要があります。この期待値設定作業は、基本的には手作業です。

この工数削減を狙って、「テスト対象のソースコードから、期待値を自動的に出せるのではないか?」と言う方もいますが、これはナンセンスです。不具合が作り込まれているかも知れない実装ソースを基に期待値を出したところで、正しい期待値が出るはずはありません。関数が仕様通りに設計されているかの検証には、正しい仕様情報である「関数設計仕様」を基に期待値を設定する必要があります。

下の図は、上で設計したテストパターンに、最初に挙げた「func() 関数仕様」を基に期待値を設定した物です。
関数設計仕様情報から期待値を設定

テスト実行は単体テストツールで自動化

単体テスト実行は、「カバレッジマスター」の様な単体テストツールで運用すれば、ほとんどが自動化されます。ICEとデバッガを使用して、手作業で単体テストを行っている例も少なくないのですが、テスト実行の人的ミスや工数削減のためには、単体テスト自動化ツールの採用は、今や必須事項となっています。

このテストパターンを「カバレッジマスターwinAMS」を使用して単体テスト実行を行った結果を下に示します。
テスト実行は単体テストツールで自動化

実行結果の評価

テスト実行結果、期待値と異なった結果になったテストベクターが、赤でマーキングされています。エラーは、2つの入力が最大値に近い値の組合せで起こっていることが分かります。

この不具合の原因としては、最大値付近の値の組合せから考えれば、オーバーフローが思いつきます。この観点でソースコードのレビューを行えば、以下の原因が特定できると思います。
実行結果の評価

要素分析を通じて 「最大値同士の組合せ」がテスト要因に入っていることがポイント

今回の例におけるポイントは、「最大値同士の組合せ」の入力要因がテスト入力に含まれていなければ、この不具合は発見できないと言うことです。もしも、この設計をテスト担当者の判断に任せていると、担当者によっては、この「最大値同士の組合せ」の要因をテストに含めないかも知れません。

この要因は技術者の判断でなく、「テスト指針」により機械的に設計されたものです。この手法により、テスト設計者の判断やスキルへの依存度が低くなり、誰が行っても、ほぼ同じ品質の単体テスト設計が可能です。

この様に、要素分析の考え方を基に、要素の抽出方法、組合せ方法を「テスト指針」として定義して、定義した方法は必ずテストに含めるようにすることで、単体テスト設計の「標準化」が実現できます。

単体テストの評価と テスト指針の改善

  • 要素分析による単体テスト設計の品質は、「テスト指針」により決まります。もしも「テスト指針」に従って正しく設計したにもかかわらず、不具合の検出ができなかった場合には、「要素分析表」のレビューを行い、次のテスト改善項目として、その不具合を抽出するためのテスト要因を、「テスト指針」に加えて改善を行うことで、より網羅性の高い単体テストが可能です。
  • テスト漏れを防ぐためのテスト指針の改善
不具合の種類や傾向は、開発プロジェクトの設計スタイルや、開発者自身のスタイル、スキルに依存します。このため、単体テスト指針は、開発部署や製品のジャンルなどにより異なります。レビューの容易な「要素分析表」をテストの評価に用いて、単体テスト指針を改善してゆくことで、不具合を次の工程に流出させない、品質の高いソフト品質維持が可能になります。

要素分析により 単体テストを標準化し 定着運用を加速

本特集では、要素分析により技術者のスキルに依存しない単体テスト設計が可能なこと、要素分析表のレビューにより、欠けているテストの観点を評価し追加することで、単体テストプロセスの改善が可能であることを述べました。最後に、要素分析表を作成することのメリットは、次の通りです。

・テスト担当者のスキルや判断に依存しない テストの標準化を実現する

テスト設計指針書を定義し、(データの設計方法)を明確に定めることで、テスト担当者のスキルやセンスに依存しない、標準的なテスト設計を可能にします。
テスト設計は、指針書に従い「機械的に」行うことがポイントです。

・設計時に見逃してしまう入力条件を 確実にテストに含めることができる

指針書に従い「機械的に」テスト設計を行うことで、テスト担当者の判断により、テストの網羅性を低下させてしまうことを防ぐことができます。

・要素分析表を参照することで テスト設計のレビューを容易にする

要素分析表は、実施した単体テストに含まれているテスト要因を客観的に判断するためのエビデンスとして利用可能です。
テスト設計後のレビューに置いて、単体テスト品質を正しく計ることを可能にします。
※組合せ後のテストデータだけでは、テスト要因の判断は困難です。

人気のコラム

最新のコラム