配置@PrepareForTest(Log.class)后仍遇Log.w()抛出Stub!异常
问题排查与解决办法
一、PowerMock和JUnit 5不兼容,你用错了注解
@RunWith(PowerMockRunner.class)是JUnit 4的运行器注解,JUnit 5根本不识别,所以你之前的PowerMock配置等于没生效。要在JUnit 5里用PowerMock,得换用扩展类:
- 先引入PowerMock的JUnit 5依赖(版本根据你用的Mockito调整,比如2.0.9)
- 把
@RunWith换成@ExtendWith(PowerMockExtension.class),保留@PrepareForTest(Log.class) - 还要在测试初始化时静态Mock Log类,示例代码:
@ExtendWith(PowerMockExtension.class) @PrepareForTest(Log.class) public class YourTestClass { @BeforeEach void setUp() { PowerMockito.mockStatic(Log.class); // 给Log.w()指定返回值,避免Stub异常 PowerMockito.when(Log.w(anyString(), anyString())).thenReturn(0); } // 你的测试方法 }
二、returnDefaultValues配置没生效
- 检查这个配置是不是写在app模块的build.gradle里的
android块下,别写到根目录的gradle文件中:
android { // 其他配置... testOptions { unitTests { returnDefaultValues = true } } }
- 配置完一定要同步gradle,并且重新运行测试,缓存会导致配置不生效
- 注意这个配置只对
src/test/java下的本地单元测试有用,src/androidTest/java的Instrumented测试不适用
三、间接调用的类没被正确Mock
如果Log.w()是被别的类(比如你的工具类)间接调用的,光Mock Log本身可能没用:
- 把
@PrepareForTest的参数改成实际调用Log的那个类,比如@PrepareForTest(YourUtils.class) - 嫌PowerMock麻烦的话,用Mockito 3.4+自带的静态Mock功能,不用额外引入PowerMock:
import static org.mockito.Mockito.mockStatic; public class YourTestClass { @Test void testYourMethod() { // 用try-with-resources自动关闭静态Mock try (MockedStatic<Log> mockedLog = mockStatic(Log.class)) { mockedLog.when(() -> Log.w(anyString(), anyString())).thenReturn(0); // 执行你的测试逻辑 } } }
四、搞混了测试类型
确认你的测试是src/test/java下的本地单元测试,如果是src/androidTest/java的Instrumented测试,returnDefaultValues不生效,也不能用PowerMock,只能用AndroidX Test的框架配合Mockito静态Mock。
内容的提问来源于stack exchange,提问作者WebViewer
相关产品推荐
相关产品推荐

