1. ホーム
  2. unit-testing

[解決済み】ユニットテスト初心者、優れたテストを書くには?[クローズド]

2022-04-17 12:10:16

質問

私はユニットテストの世界ではかなり新参者ですが、今週、既存のアプリにテストカバレッジを追加することにしました。

テストするクラスの数が多いからですが、テストを書くのが初めてなので、これは大変な作業です。

すでにたくさんのクラスのテストを書きましたが、いまは「これでいいのか?

メソッドのテストを書いていると、メソッド自体にすでに書いてあることをもう一度書き直すような感覚になるんです。

私のテストはメソッドにとても強く結びついているように見えます (すべてのコードパスをテストし、いくつかの内部メソッドが特定の引数で何度も呼び出されることを期待します) が、もし私がメソッドをリファクタリングしたら、たとえメソッドの最終動作が変化しなかったとしてもテストは失敗するでしょう。

これはあくまで感覚的なもので、先ほども言ったように私はテストの経験がないのです。もし、経験豊富なテスターの方がいらっしゃいましたら、既存アプリの優れたテストの書き方についてアドバイスを頂ければ幸いです。

編集 : Stack Overflowに感謝します。15分以内に素晴らしいインプットを得ることができ、何時間もかけてオンラインで読んだことよりも多くの答えが得られました。

解決方法は?

<ブロッククオート

私のテストはメソッドに非常に強く結びついているようです (すべてのコードパスをテストし、いくつかの内部メソッドが特定の引数で何度も呼び出されることを期待します)、 もし私がメソッドをリファクタリングするなら、たとえメソッドの最終動作が変化しなかったとしてもテストは失敗するでしょう。

やり方が間違っているのでは?

ユニットテストは、そうでなければならない。

  • 1つのメソッドをテストする
  • そのメソッドにいくつかの特定の引数を与える
  • 期待通りの結果であることをテストする

このテストは、メソッドの内部を調べて何をしているかを確認するものではないので、内部を変更してもテストが失敗することはないはずです。プライベートメソッドが呼び出されていることを直接テストするべきではありません。もし、プライベートなコードがテストされているかどうかを調べたいのであれば、コードカバレッジツールを使ってください。しかし、このことにこだわってはいけません。100%のカバレッジは必要条件ではありません。

もしあなたのメソッドが他のクラスのパブリックメソッドを呼び出し、その呼び出しがインターフェイスによって保証されているなら、モッキングフレームワークを使用することで、これらの呼び出しが行われていることをテストすることができます。

メソッド自体 (またはメソッドが使用する内部コード) を使用して、期待される結果を動的に生成するべきではありません。期待する結果は、テストケースにハードコーディングして、 実装が変わっても変化しないようにしなければなりません。以下は、ユニットテストが行うべきことの単純化された例です。

testAdd()
{
    int x = 5;
    int y = -2;
    int expectedResult = 3;
    Calculator calculator = new Calculator();
    int actualResult = calculator.Add(x, y);
    Assert.AreEqual(expectedResult, actualResult);
}

結果がどのように計算されたかはチェックされず、結果が正しいかどうかだけがチェックされることに注意してください。できるだけ多くのシナリオをカバーできるようになるまで、上記のような単純なテストケースをどんどん追加していってください。コードカバレッジツールを使って、何か面白いパスを見逃していないか確認してみましょう。