Mockito 3.4.0以降、静的メソッドをモックするための実験的なAPIが導入されました。
次のサンプルコードは、Mockito 4.3.1(testImplementation("org.mockito:mockito-inline:4.3.1
)、およびJUnit Jupiter 5.8.2、OpenJDK11でテストされています。
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.mockito.MockedStatic;
import org.mockito.Mockito;
import java.util.UUID;
public class StaticMockTest {
@Test
void showCaseStaticMock() {
try (MockedStatic<StaticMockTest> staticMock = Mockito.mockStatic(StaticMockTest.class)) {
staticMock.when(StaticMockTest::getUUIDValue).thenReturn("Mockito");
Assertions.assertEquals("Mockito", StaticMockTest.getUUIDValue());
}
// Regular UUID
UUID.fromString(StaticMockTest.getUUIDValue());
}
public static String getUUIDValue() {
return UUID.randomUUID().toString();
}
}
前の回答、おそらくMockito 1.x/2.xとPowermock1.x/ 2.x
実際のインスタンスでMockitoを使用する場合と同じ方法で実行できます。たとえば、スタブをチェーンすることができます。次の行では、最初の呼び出しは何も行わず、2番目以降の呼び出しgetResources
は例外をスローします。
// the stub of the static method
doNothing().doThrow(Exception.class).when(StaticResource.class);
StaticResource.getResource("string");
// the use of the mocked static code
StaticResource.getResource("string"); // do nothing
StaticResource.getResource("string"); // throw Exception
Matt Lachmanの発言のおかげで、モックの作成時にデフォルトの回答が変更されない場合、モックはデフォルトでは何もしないことに注意してください。したがって、次のコードを書くことは、書かないことと同じです。
doNothing().doThrow(Exception.class).when(StaticResource.class);
StaticResource.getResource("string");
そうは言っても、この特定のコードには何も期待しないというテストを読む同僚にとっては興味深いかもしれません。もちろん、これは、テストの理解可能性がどのように認識されているかに応じて適応させることができます。
ちなみに、私の謙虚な意見では、新しいコードを作成する場合は、静的コードをモックすることは避けてください。Mockitoでは、これは通常、悪い設計のヒントであり、保守性の低いコードにつながる可能性があると考えています。既存のレガシーコードはさらに別の話ですが。
一般的に、プライベートメソッドまたは静的メソッドをモックする必要がある場合、このメソッドはあまりにも多くのことを行うため、テスト対象のオブジェクトに注入されるオブジェクトに外部化する必要があります。
お役に立てば幸いです。
よろしく