使用eq的Whitebox invokeMethod(" string")

时间:2017-12-15 10:20:38

标签: android testing mockito powermock

我有测试

 Document document = spy(new Document());
    Whitebox.setInternalState(documentReceiverInteractor, "document", document);

    String text= "string";

    Whitebox.invokeMethod(documentReceiverInteractor, "saveFields", anyString(), eq(text), anyString(),
            anyString(), anyString(), anyString(), anyString());

    verify(document).setText(text);

启动后,我收到此错误:

 Argument(s) are different! Wanted:
document.setText(
    <any string>
);
-> at ru.psbank.msb.dev.business.document.edit.receiver.DocumentReceiverInteractorTest.saveFields(DocumentReceiverInteractorTest.java:98)
Actual invocation has different arguments:
document.setText(
    null
);

eq适用于基元,没有对象。我该怎么办?

1 个答案:

答案 0 :(得分:2)

Whitebox.invokeMethod(documentReceiverInteractor, "saveFields",
    anyString(), eq(text), anyString(),
    anyString(), anyString(), anyString(), anyString());

This statement doesn't make sense. Calls to anyString() and so forth are signals to Mockito that only make sense within calls to when and verify. Their return values are null, 0, "", or other dummy values, and their side effects are to modify Mockito's internal state; they are not random or arbitrary values for testing, and do not have any special behavior for Whitebox.

(Under the hood, you are calling setText with the return value from eq(text), which is null, and matching it against one of the calls to anyString() that you've accidentally added to the argument matcher stack.)

Instead, pick specific values:

Whitebox.invokeMethod(documentReceiverInteractor, "saveFields",
    "string 1",
    text,
    "string 2",
    "string 3",
    "string 4",
    "string 5",
    "string 6");

...and rather than using Whitebox, which is in Mockito's internal package org.mockito.internal.util.reflection and is deleted in Mockito 2.2, you should consider making the method call more visible (package-private if your test is in the same package, public if not). Your test is a consumer of your class, after all. If you choose to go that route, consider adding @VisibleForTesting or some other documentation (like /** Visible for testing. */).