0

テスト中のメソッドがあります。コールスタック内で、インターンがJDBCを使用してDBとチャットするDAOを呼び出します。JDBCレイヤーで何が起こるかを知ることにあまり興味がありません。私はすでにそのためのテストを持っています、そしてそれらは素晴らしく働きます。

DAOレイヤーであるJMockを使用してモックを作成しようとしているので、このメソッドのテストの詳細に焦点を当てることができます。これが私が持っているものの基本的な表現です。

@Test    
public void myTest()
{
     context.checking(new Expectations() {
          {
               allowing(myDAO).getSet(with(any(Integer.class)));
               will(returnValue(new HashSet<String>()));
          }
     });

    // Used only to show the mock is working but not really part of this test.
    // These asserts pass.
    Set<String> temp = myDAO.getSet(Integer.valueOf(12));
    Assert.assertNotNull(temp);
    Assert.assertTrue(temp.isEmpty());

    MyTestObject underTest = new MyTestObject();
    // Deep in this call MyDAO is initialized and getSet() is called.
    // The mock is failing to return the Set as desired. getSet() is run as 
    // normal and throws a NPE since JDBC is not (intentionally) setup. I want 
    // getSet() to just return an empty set at this layer.
    underTest.thisTestMethod();
    ...
    // Other assertions that would be helpful for this test if mocking 
    // was working.
}

このテストの作成で学んだことから、JMockを使用して間接オブジェクトをモックすることはできません。または、重要なポイントが表示されていません。後半が真実になることを願っています。

考えていただきありがとうございます。

4

1 に答える 1

0

スニペットから、MyTestObjectはコンストラクターパラメーターを持たないため、リフレクション、または静的メソッドまたはフィールドを使用してDAOを取得していると推測しています。JMockは、タイプによるオブジェクトの置換を行いません(そして、今のところ、そうする他のフレームワークを推奨する多くの人々がいるでしょう)。

これは意図的なものです。JMockの目標は、クリーンな依存関係と焦点を絞った動作を要求することにより、オブジェクト設計の弱点を明らかにすることです。DAO / JDBCアクセスをドメインオブジェクトに埋め込むと、最終的に問題が発生することがわかりました。これは、ドメインオブジェクトに秘密の依存関係があるため、理解や変更が困難になることを意味します。私はそれらの関係をコードで明示的にすることを好みます。

したがって、モックされたオブジェクトを何らかの方法でターゲットコードに取り込む必要があります。それができない、またはしたくない場合は、別のフレームワークを使用する必要があります。

PSスタイルの1つのポイントとして、このテストを少し簡略化できます。

context.checking(new Expectations() {{
  allowing(myDAO).getSet(12); will(returnValue(new HashSet<String>()));
}});

テスト内では、期待する値を実際に把握し、それを期待に反映させる必要があります。これにより、オブジェクト間の値の流れを簡単に確認できます。

于 2012-02-07T09:27:58.157 に答える