これは、モック オブジェクトを使用して Java クラスを単体テストする方法に関する一般的な質問です。
この例で問題を要約できます。
MyInterface.java というインターフェイスと、equals() をオーバーライドしない「TwoString」オブジェクトがあるとします。
"TwoString.java"
private String string1;
private String string2;
public TwoString(String string1, String string2) {
this.string1 = string1;
this.string2 = string2;
}
...getters..setters..
"MyInterface.java"
void callMe(TwoString twoString);
次に、「MyClass.java」オブジェクトがあります。そのコンストラクターは、MyInterface の具体的な実装を受け入れます。
MyClass methodToTest() には、何らかの方法で TwoString オブジェクトを作成するロジックが含まれています。として作成されるとしましょう
new TwoString("a","b")
したがって、 methodToTest() が呼び出されると、インターフェイス メソッドcallMe(TwoString twoString)に渡されるこの TwoString オブジェクトが作成されます。
私は基本的にインターフェースをモックしたいと思っています。このモックで MyClass オブジェクトを作成します。次に、モック メソッドが TwoString の特定のインスタンスで呼び出されることを確認します。
私はEasyMockを使用しています。これはJavaコードです
「MyClassTest.java」
public void test() throws Exception {
MyInterface myInterfaceMock = createMock(MyInterface.class);
MyClass myClass = new MyClass(myInterfaceMock);
myInterfaceMock.callMe(new TwoString("a","b")); <--- fails here
expectLastCall();
replay(myInterfaceMock);
myClass.methodToTest();
verify(myInterfaceMock);
ここで問題が発生します。呼び出しで期待している TwoString オブジェクト
myInterfaceMock.callMe(new TwoString("a","b"));
TwoString.java は equals をオーバーライドしないため、 MyClass.methodToTest() で生成されたものとは異なります。
を使用して TwoString インスタンスの問題をスキップできます
myInterfaceMock.callMe((TwoString)anyObject());
しかし、インターフェイス メソッドが、文字列 1 として "a"、文字列 2 として "b" を含む TwoString の特定のインスタンスで呼び出されることを確認したいと思います。
この場合、TwoString オブジェクトは非常に単純で、equals メソッドをオーバーライドするのは簡単ですが、より複雑なオブジェクトをチェックする必要がある場合はどうすればよいでしょうか。
ありがとう
編集:
この例で読みやすくしようとします
public class MyClassTest {
private MyClass myClass;
private TaskExecutor taskExecutorMock;
@Before
public void setUp() throws Exception {
taskExecutorMock = createMock(TaskExecutor.class);
myClass = new MyClass(taskExecutorMock);
}
@Test
public void testRun() throws Exception {
List<MyObj> myObjList = new ArrayList<MyObj>();
myObjList.add(new MyObj("abc", referenceToSomethingElse));
taskExecutorMock.execute(new SomeTask(referenceToSomethingElse, ???new SomeObj("abc", referenceToSomethingElse, "whatever"))); <--- ??? = object created using data in myObjList
expectLastCall();
replay(taskExecutorMock);
myClass.run(myObjList);
verify(taskExecutorMock);
}
}
???SomeObj = myObjList に含まれるデータを使用して myClass.run() によって作成されたオブジェクト。
SomeObj がサード パーティのライブラリから取得され、equals をオーバーライドしないとします。
その SomeObj の特定のインスタンスで taskExecutorMock.execute() メソッドが呼び出されていることを確認したい
myClass.run() が正しいインスタンスで taskExecutorMock メソッドを実際に呼び出していることをテストするにはどうすればよいですか