java - 如何解决“要创建一个新的mock,必须注销现有的mock注册”
问题描述
尝试模拟静态方法时出现以下异常:
org.mockito.exceptions.base.MockitoException:对于de.msggillardon.system.UserContext,静态mock已经注册在当前线程要创建一个新的mock,现有的静态mock注册必须注销
对于以下代码:
@ExtendWith(MockitoExtension.class)
// @PrepareForTest(UserContext.class)
public class KonfigurationCopyServiceTest {
public static final String CONFIGURATION_NAME = "Standard-Konfiguration";
@Mock
public TriggeringKonfigurationService triggeringKonfigurationService;
@Mock
public ReportKonfigService reportConfigurationService;
@Mock
public BuchungsschemaService buchungsschemaService;
public KonfigurationCopyService copyService;
@BeforeEach
public void init() {
Mockito.mockStatic(UserContext.class);
Mockito.when(UserContext.getUsername()).thenReturn("superuser");
copyService = new KonfigurationCopyService(triggeringKonfigurationService,
reportConfigurationService, buchungsschemaService);
}
有人可以帮忙吗?
谢谢!
编辑:UserContext.java
package de.msggillardon.system;
/**
* This class contains the username and IP-address of the logged in user. It is initialized for each
* session.
*
* @author wildp
*/
public class UserContext {
private static final ThreadLocal<UserContext> userContext = new ThreadLocal<>();
private final String username;
private final String clientIPAddress;
/**
* Constructor.
*
* @param username Username of the user who is logged in
* @param clientIPAddress IP Address of the user who is logged in
*/
public UserContext(String username, String clientIPAddress) {
this.username = username;
this.clientIPAddress = clientIPAddress;
}
/**
* Initializes the threadLocal
*
* @param userContext
*/
public static void initialize(UserContext userContext) {
UserContext.userContext.set(userContext);
}
/**
* Removes the current thread's value for this thread-local variable.
*/
public static void remove() {
userContext.remove();
}
/**
* Returns the username of the current thread.
*
* @return
*/
public static String getUsername() {
return userContext.get().username;
}
/**
* Returns the IP address of the client of the current thread.
*
* @return
*/
public static String getClientIPAddress() {
return userContext.get().clientIPAddress;
}
public static UserContext getThreadLocalUserContext(){
return userContext.get();
}
}
新编辑:我再次编辑了我的代码,因此您现在可以看到,我正在使用 @ExtendWith(MockitoExtension.lass) 来模拟。
我还在网上找到了以下提示:https : //javadoc.io/static/org.mockito/mockito-core/3.4.3/org/mockito/MockedStatic.html 所以看来我必须做一个 MockedStatic.close( ); 也许作为@AfterEach 但是当我尝试时它给了我例外
无法从 ScopedMock 类型对非静态方法 close() 进行静态引用
还是行不通 :(
解决方案
因此,当我使用 Junit 5 时,我无法使用 @Before 注释,因此我将 @BeforeEach 替换为 @BeforeAll。所以我这样做如下:
- 步骤:导入
import static org.junit.jupiter.api.TestInstance.Lifecycle.PER_CLASS;
步骤:添加 @TestInstance(PER_CLASS) 注释(在您的课程之前)
步骤:@BeforeAll 而不是 @BeforeEach
这解决了我的问题。
推荐阅读
- angularjs - 由于未知提供程序而使用角度仪表板时出错:widgetDefinitionsProvider
- mysql - 自定义快速验证器
- node.js - 使用 nodejs 在 GCloud Postgres SQL 中连接
- java - Selenium,Java,if-else 语句无法正常工作,NoSuchElementException
- c++ - 自定义 QTreeWidget 的子指示器
- css - 在本地网页上找不到图像和字体 (404)
- php - 将图像保存在数据库中并在视图 laravel 5.6 中显示
- javascript - 在 textarea 中输入的 HTML 代码未保存在数据库中
- javascript - 你可以在mixpanel中有子属性吗?
- macos - macOS WindowServer 和 CoreGraphics API 使用