やぼったい開発 > ウォータフォールモデルによる開発手法の基礎 > 試験工程(補足)

UTとFTの違い:試験工程(補足)

UTとFTの違いは、わかっているようでわかりにくい箇所なのでもう少し具体的に説明したいと思います。

UTとFTの違いがわかるとシンプルになる

まずUTとFTで工程を分離した時と、指定ないときのそれぞれの場合における複雑度の違いを説明します。

想定サンプルの実装内容:
機能Xを実現するために、A〜Eを処理するモジュールが必要。A〜Eはそれぞれ、全パス(複雑度)が10であるとする。機能Xからは A〜Eを順番に呼び出す。

まず、工程を分離した場合。

UTの試験は
A〜Eの 10*5 = 50 パターン(処理内試験)
A〜Eが順番に呼び出される1パターン(処理間試験または機能前の呼び出しモジュール内試験、上記の試験の後に行う)

FTの試験は
前提条件でテスト環境をセットアップし
Xを呼び出すと ファイルやDBが 〜〜になって、返値または画面が〜〜になることを確認する1パターン。(メッセージやパラメータのやりとりの仕方によってパターンは増えることもある)

モジュール UT試験行程 FT試験行程
A 10パターン
(モジュール内のパスなどをすべて網羅する)
1〜5パターン
(A〜Eを一通り通す)
B 10パターン
C 10パターン
D 10パターン
E 10パターン
51〜55パターン

図 試験パスルート(分離)イメージ

工程が一緒になった場合。

Aのパス1を通ってEのパス3の試験を通る前提条件が〜で、そのように通すと Aのモジュールの返値が〜〜で・・・画面が〜になることを確認するパターン。
Cのパス7を通るためにはEのパス3がまた通るけどその前提条件で
〜〜〜画面は〜〜〜。
この前提条件だと、また同じ画面の同じメッセージ確認するなぁ。
あれっ?Xから Cを呼び出していくと パス4は絶対通らないなぁまあいいか。
もうそろそろ Dの戻り値確認しなくてもいいんじゃないかなぁ・・・

・・・がずーと続く。結局機能レベルの動作まで考えないと何パターンになるか説明できない(昔自分もこれやって あ〜難しい!と嘆いていたもんです)。

うまくいけば、それぞれのモジュールを1回づつ通る(10パターン)ですむかもしれないが、試験するときはいっぺんに行うような試験項目なのでA〜E全てが本物である必要性がある上に、どのパターンが網羅され、網羅されていないかわかりずらいし、レビューでも指摘しづらい。

パターン モジュール UT試験行程 &FT試験行程の条件と確認項目
1 A Aの a1 を通し、返り値は0
B .....
C .....
D .....
E Eのe3が通ること
ファイル/DB .....
画面 正常に終了する
2 A Aの a3 を通して、返り値を -1で返す。
B
C Cのモジュールで ファイルを出力する
D (確認不要)
E .....
ファイル/DB .....
画面 .....
想定不能



図 試験パスルート(一緒)イメージ

今説明した二つの点の特徴を整理

どっちがメリットが多い?か 分離した時としていない時の特徴を再確認します。

分離されていれば、網羅しているところと網羅していないところが把握しやすいだけでなく、どれほど試験に時間がかかるか、どれくらいの項目になるか見積もりやすい

一方、工程が一緒になってしまうと、パターンを網羅するだけでも一苦労(スキルが必要になるかもしれない)。また、いっぺんに実モジュールで試験するためstubが使えなく、網羅できないパターンが発生するかもしれない。また、項目が重複しやすいので、テスト作成、レビュー、テスト実施全てにおいて余分な作業が発生してしまう。 10パターンで済むように設計されていたり、そういうパズルが好きな人は別だが、万人向けに行えるようなの開発手法としてのシステムにはほど遠い(試験仕様書に項目全てを把握せずに、その試験全体を理解させるような記載ができると思えないし、それができないと、いざというとき引継ができない)。


品質を保証するなら、網羅されている事が特に重要。プロジェクト作業の品質を確認するために網羅されていることを簡単に把握できることも重要。
また、必要な部分に必要なリソース(人・時間・お金)だけ力をかけたい場合は分けて考えたほうがいいわけです。

まとめ:ポイントはUTとFTの違いを意識すること

違いをわかるためには各工程で何をしなければいけないかをわかることが大事。上工程で業務レベル、機能レベル、処理レベルと順次大枠を意識した設計をし、それを保証するための試験を考える。UTでしかできないことは機能試験ではできなく、逆に機能試験でしかできないことはUTでできないことを知ってほしい。

具体的に言うと(ほとんど上で説明してしまったが・・・)、UT試験では機能間連携のことを意識する必要が無く、基本は、コードに近いレベルで(例えば関数の中に閉じて)思った通りの動作をするかをテストする。つまり呼び出し側、呼び出し先側は正しいパラメータで呼ばれてさえいればよく、ダミーとしてstubなどを利用しても問題ない。

ここが混じっている人の試験仕様書の特徴は、細かいところと、おおざっぱな機能レベルの確認項目が混じり、肝心なUT部分が抜けていたり、機能部分をUT的に確認しようとしてパターンや確認項目とも複雑になり過ぎることがよくある。


一方機能試験では、機能に関する点だけ確認すればよく、処理やモジュールの細かい点は確認しなくて良い(前のUT工程で確認しているはずなので)。テスト項目として考えやすくするこつは、INPUTとしてDBや前提条件と、OUTPUTとしてのDB、ファイル状態、返値、画面状態を機能的に整理しておくとすっきりしてくる(UTで似た様なことをやっていても、機能の観点では再度試験する必要が出てくることが多い)。

このようにそれぞれ、試験観点が違うので、確認項目をぱっと見ただけで、必然的にどちらの工程の試験かわかるはず。


あと、あいだの細かい連携部分についてどの試験工程で行うかは、開発の設計部分を担当していないとなかなかわかりづらいかもしれない。試験工程で保証する各レベルから漏れたり曖昧な部分については最初からメインとして考える必要はなくて、あとで、チーム内で製品のタイプや試験のしやすさを考慮して決めればいい。

UTとFTの試験範囲と試験ポイント

表:UTとFTの試験範囲と試験ポイント

対象 工程 テスト範囲 補足
機能X FT INPUT/OUTPUT(ファイルなども含む)だけテストする A,Bの中はテストしない。
A,Bを正しく呼ぶことと、Xの機能としての観点でX全体の包括的な出力結果(Aのモジュールが出力するファイルなども含む場合がある)はテストする。
※モジュールという言葉に惑わされないように、機能として工程の保証対象を意識する。
モジュールA UT Aの中と AからみたINPUT/OUTPUTだけテストする B側のテストはしないので、AをテストするときBはダミーモジュールでOK
普通、BのダミーモジュールにAから何を受け取ったか確認できるように細工しておき、試験ではその表示の確認結果をもってAの出力確認とする。
モジュールB UT Bの中と BからみたINPUT/OUTPUTだけテストする 上と同様

※ちなみに、AとBの橋渡しのテストは、(以上を理解していると仮定して)Xの試験の時に行うか、A,Bのテストが終わった後に行う。

図:UTとFTの試験は範囲試験ポイントイメージ

類似コンテンツ



なぜ自動化するのか?単体テスト自動化のメリットとデメリット

JUnitの役割はどこまで? 試験工程内で 単体テストのできることとできないこと

早わかり Junit 30分講座


類似コンテンツ

ウォータフォールモデルではテストファーストは当たり前?

なぜ自動化するのか?単体テスト自動化のメリットとデメリット

JUnitの役割はどこまで? 試験工程内で 単体テストのできることとできないこと

早わかり Junit 30分講座

仕様変更に強くなるには


<< ウォータフォールモデル 目次へ 戻る