統合テストとテストピラミッド
前の章では、部品を一つずつ確かめるユニットテストを紹介しました。最後に見たように、部品が単体で正しくても、つなぐと壊れることがあります。
この章では、部品をつないだ状態で確かめる統合テストと、アプリ全体をユーザーと同じ操作で確かめるE2Eテストを紹介します。そして、それぞれをどのくらいの割合で書けばよいかを表すテストピラミッドという考え方を見ていきます。
部品をつないだ状態で確かめる統合テストと、アプリを丸ごと通すE2Eテスト。それぞれが見ている範囲の違いから、テストの量のバランスを表すテストピラミッド、逆さまの失敗例、AIと組み合わせるときの役割分担まで。
前の章では、部品を一つずつ確かめるユニットテストを紹介しました。最後に見たように、部品が単体で正しくても、つなぐと壊れることがあります。
この章では、部品をつないだ状態で確かめる統合テストと、アプリ全体をユーザーと同じ操作で確かめるE2Eテストを紹介します。そして、それぞれをどのくらいの割合で書けばよいかを表すテストピラミッドという考え方を見ていきます。
アプリを「画面 → 割引の計算 → 決済 → データベース」という流れで描いてみました。ユニットテストが確かめるのは、この中の一つの部品だけです。図の青い枠がその範囲です。
まわりの部品やデータベースは、前の章で紹介したモック(ニセモノ)に置き換えています。だから速くて安定していますが、そのぶん「本物どうしをつないだらどうなるか」は分かりません。
統合テスト(インテグレーションテスト)は、いくつかの部品を本物どうしでつないだ状態で確かめるテストです。紫の枠のように、割引の計算から決済、そして本物のデータベースまでをまとめて動かします。
部品と部品の間を流れるデータの形や、データベースへの保存と読み出しが正しくできるかなど、「つなぎ目」で起きる問題を見つけるのが役目です。青い枠(ユニットテスト)よりも、見ている範囲がぐっと広がっています。
前の章の例をもう一度見てみましょう。割引の部品は「割引額の100円」を返し、決済の部品は「支払額」を受け取るつもりでした。統合テストで二つを本物どうしでつなぐと、決済に100円が渡ってしまい、テストが失敗します。
どちらの部品も、単体で見れば「自分の仕様どおり」に動いています。おかしいのは、部品どうしの約束のほうです。こうした問題は、つないで動かして初めて見つかります。
約束をそろえて、割引の部品が「割引後の金額900円」を返すように直しました。もう一度統合テストを実行すると、つなぎ目を通っても正しい金額が決済に届き、テストは合格します。
ここで大事なのは、一度この統合テストを書いておけば、将来だれかがこの約束を崩したときにも、すぐに気づけるということです。テストは、一度書けばずっと見張り番をしてくれます。
E2E(End to End=端から端まで)テストは、ユーザーが実際にやる操作を、画面からデータベースまで丸ごと通して確かめるテストです。たとえば「商品をカートに入れて、クーポンを入力して、購入ボタンを押す」という一連の流れを、ブラウザを自動で操作して再現します。
いちばん本物に近い確かめ方ですが、画面の表示を待ったりするので時間がかかり、ちょっとした画面の変更で壊れやすいという弱点もあります。図のように、三つのテストは、見ている範囲の広さが入れ子のように違うのです。
では、三種類のテストをどのくらいの割合で書けばよいのでしょうか。よく使われる目安がテストピラミッドです。
いちばん下の土台にユニットテストをたくさん置き、その上に統合テストをほどほどに、いちばん上のE2Eテストは少しだけにします。さっきまで範囲を表していた三つの枠が、そのままピラミッドの段に入れ替わったのに注目してください。範囲が狭かったユニットテストがいちばん広い土台に、範囲が広かったE2Eテストがいちばん小さな頂上になっています。見る範囲が狭いテストほど数を多く、広いテストほど数を少なく、という関係です。
ピラミッドの下のユニットテストは、一つ数ミリ秒で終わり、落ちたときには壊れた場所がすぐに分かります。だから、たくさん書いても負担になりません。
上に行くほど、本物の使われ方に近づいて安心感は増しますが、一つのテストに時間がかかり、落ちたときに原因を探すのも大変になります。速くて細かいテストで土台を固め、広いテストは要所だけに絞る。これがピラミッドの形をしている理由です。
よくある失敗が、このピラミッドを逆さまにした形です。ユニットテストがほとんどなく、手作業の確認やE2Eテストばかりに頼っている状態で、形がアイスクリームのコーンに似ていることから「アイスクリームコーン型」と呼ばれます。
この形だと、テストを一回流すのに何十分もかかり、落ちても「どこが悪いのか」がなかなか分かりません。結局みんなテストを流さなくなり、バグが本番まで届いてしまいます。
AIに開発を任せるときも、ピラミッドの形はそのまま役に立ちます。土台のユニットテストは、テスト駆動開発のサイクルの中でAIにどんどん書かせます。真ん中の統合テストは、本物のデータベースを使って、CIで毎回自動で流します。いちばん上のE2Eテストは、購入やログインのような大事な操作だけに絞ります。
ここで一つ疑問が残ります。統合テストで「本物のデータベース」を使うには、テストのたびにデータベースを用意しなければなりません。それを手軽に、しかも本番と同じ条件で実現してくれるのが、次の章で紹介するDockerです。
ログインするとコメントできます。
読み込み中…
権利侵害・不適切な内容の連絡: [email protected]