39

私は Spring MVC プロジェクトに取り組んでおり、ソース ツリー内のさまざまなコンポーネントすべての単体テストを行っています。

たとえば、コントローラーHomeControllerを挿入する必要があるLoginService場合、単体テストではHomeControllerTest、オブジェクトを通常どおり (Spring の外部で) インスタンス化し、プロパティを挿入します。

protected void setUp() throws Exception {
    super.setUp();
    //...
    controller = new HomeController();
    controller.setLoginService( new SimpleLoginService() );
    //...
}

これは、各コンポーネントを分離されたユニットとしてテストするのに最適です-プロジェクトに数十のクラスがあることを除いて、クラスを作成し、それに対して成功したユニットテストを作成した後、Spring MVC コンテキストファイルを更新するのを忘れ続けます展開されたアプリケーションでの実際の接続。プロジェクトを Tomcat にデプロイし、接続されていない Bean から多数の NullPointer を見つけたときに、コンテキスト ファイルを更新するのを忘れていたことに気付きました。

だから、ここに私の質問があります:

  1. これは私の最初の Spring プロジェクトです。私が行ったように、個々の Bean の単体テストを作成してから、2 番目のテスト スイート (統合テスト) を作成して、すべてが実際のアプリケーション コンテキストで期待どおりに機能することをテストするのは正常ですか? これに対する確立されたベストプラクティスはありますか?

  2. さらに、単体テストを統合テストからどのように分離しますか? すべてのソース コードはsrcにあり、ユニット テストはにあります。統合テスト ケース用にtest2 つ目のテスト フォルダ ( など) が必要ですか?test-integration

これは私の最初の Spring プロジェクトなので、他の人が通常この種のことをどのように行っているのか興味があります。車輪を再発明するのではなく、コミュニティの他のメンバーに尋ねます。

4

7 に答える 7

32

ベスト プラクティスとは言えませんが、過去に行ったことを以下に示します。

単体テスト:

  • 重要な Bean (つまり、ほとんどの Spring 関連 Bean) の単体テストを作成します。
  • 実用的な場合 (つまり、常にではないにしても、ほとんどの場合) に注入されたサービスにモックを使用します。
  • プロジェクトtestディレクトリ内のこれらのテストには、標準の命名規則を使用してください。Testorをクラス名の接頭辞または接尾辞として使用TestCaseすることは、広く実践されているようです。

統合テスト:

  • 統合テスト クラスで使用する をAbstractIntegrationTestCaseセットアップする を作成します。Spring WebApplicationContext
  • testディレクトリ内の統合テストには命名規則を使用します。これらのテストでは、接頭辞または接尾辞としてIntTestorを使用しました。IntegrationTest

test3 つの Antターゲットをセットアップします。

  1. test-all (または任意の名前): 単体テストと統合テストの実行
  2. test: 単体テストを実行します (単体テストtestの最も一般的な使用法と思われるため)
  3. test-integration: 統合テストを実行します。

前述のように、プロジェクトに適した命名規則を使用できます。

ユニットを統合テストから別のディレクトリに分離することに関しては、開発者とそのツールがそれらを簡単に見つけて実行できる限り、問題ではないと思います。

test例として、私が Spring で取り組んだ最後の Java プロジェクトでは、統合テストと単体テストが同じディレクトリにある、上記の内容を正確に使用していました。一方、Grails プロジェクトでは、一般的なテスト ディレクトリの下に、単体テスト ディレクトリと統合テスト ディレクトリを明示的に分離します。

于 2008-11-11T19:03:23.767 に答える
6

いくつかの孤立した点:

はい、Spring テストへの一般的なアプローチです。単体テストと統合テストを分離し、前者は Spring コンテキストをロードしません。

単体テストでは、モックを作成して、テストが 1 つの分離されたモジュールに集中するようにすることを検討してください。

テストが大量の依存関係に配線されている場合、それらは実際には単体テストではありません。これらは、依存関係の注入ではなく、新しいものを使用して依存関係を配線している統合テストです。プロダクション アプリケーションで Spring を使用すると、時間と労力の無駄になります。

Spring コンテキストを起動するための基本的な統合テストは役に立ちます。

@required アノテーションは、Spring 配線で必要な依存関係を確実にキャッチするのに役立ちます。

たぶん、単体テストと統合テストをバインドするための明示的なフェーズを提供するMavenを調べてください。Maven は、Spring コミュニティで非常に広く使用されています。

于 2010-08-15T07:53:37.937 に答える
4

@ Component、@ Controller、@ Service、および@RepositoryですべてのBeanに注釈を付ける純粋な注釈付きレジームに切り替えると、春の面倒な複式簿記の多くがなくなります。注入する必要のある属性に@Autowiredを追加するだけです。

スプリングリファレンスマニュアルのセクション3.11を参照してください。http://static.springframework.org/spring/docs/2.5.x/reference/beans.html#beans-annotation-config

関連する注記として、KenGが説明する部門ユニット/インテグラトリオンテストを使用しています。私の最近の体制では、テストの3番目の「クラス」である「ComponentTests」も導入しました。これらは完全なスプリング配線で実行されますが、ワイヤードスタブの実装で実行されます(スプリングでコンポーネントスキャンフィルターと注釈を使用)。

これを行った理由は、一部の「サービス」レイヤーでは、Beanを手動でワイヤリングするための膨大な量の手動でコーディングされたワイヤリングロジックと、場合によってはばかげた量のモックオブジェクトが発生するためです。5ラインのテストに対して100ラインの配線は珍しいことではありません。コンポーネントテストはこの問題を軽減します。

于 2008-11-11T19:18:30.273 に答える
2

InitializingBean インターフェイスを使用する (メソッド「afterPropertiesSet」を実装する) か、Bean の init-method を指定します。通常、init メソッドを Bean に追加することを覚えておく必要がないため、InitializingBean の方が簡単です。

afterPropertiesSet を使用して、すべてが非 null として注入されるようにし、null の場合は例外をスローします。

于 2008-11-11T20:28:38.820 に答える
0

Webアプリケーションの統合テストを作成したら、それらを別のディレクトリに配置しました。これらはjUnitまたはTestNGを使用して構築され、ユーザーであるかのようにWebページにアクセスするSeleniumなどを使用してテスト対象のシステムと対話します。サイクルは次のようになります。コンパイル、単体テストの実行、Webアプリのビルド、実行中のサーバーへのデプロイ、テストの実行、アプリのアンデプロイ、結果のレポート。アイデアは、システム全体をテストすることです。

于 2008-11-11T19:23:46.377 に答える
0

統合テストとは別に単体テストを実行することに関しては、後者をすべて統合テスト ディレクトリに配置し、IDE/Ant を使用して次のようなアプローチで実行します。私のために働きます。

于 2009-09-16T12:51:38.727 に答える
0

単体テストと統合テストの違いは、単体テストは必ずしもコンテキストをロードするわけではなく、記述したコードに焦点を合わせていることです-依存呼び出しをモックすることにより、例外の有無にかかわらず、高速に失敗します。ただし、統合テストの場合は、コンテキストをロードして、実際のシナリオのようにエンド ツー エンドのテストを実行します。

于 2013-03-17T18:09:57.690 に答える