【问题标题】:Is there any way to inject MockBean inside another MockBean有没有办法将 MockBean 注入另一个 MockBean
【发布时间】:2021-11-09 13:27:33
【问题描述】:

我有课

@Service
@RequiredArgsConstructor
public class UserService {
    private final WalletService walletService;

    public void increaseBalance() {
      walletService.increaseBalance();
    }
}

@Service
@RequiredArgsConstructor
public class WalletService {
    public void increaseBalance() {}
}

和测试类

@RunWith(SpringRunner.class)
@SpringBootTest()
public class UserServiceTest {
  @MockBean
  private UserService userService;

  @Test
  public void testIncreaseBalance_realMethod() {
    //here I want to call real UserService method
    doCallRealMethod().when(userService).increaseBalance();

    userService.increseBalance();
  }

  @Test
  public void testIncreaseBalance_mockedMethod() {
    //here I don't want to call real UserService method

    userService.increseBalance();
  }

}

在这种情况下,WalletService 没有被注入到 UserService 中。如我所见,原因是 UserService 是一个@MockBean。因此,我在测试中有 NullPointerException。

但是,当我创建 UserService @SpyBean 时,WalletService 被注入到 UserService 中。

有什么方法可以在 UserService 中注入 WalletService 并且仍然将其作为@MockBean?

【问题讨论】:

  • 您是想测试UserService 本身的行为,还是需要在完整的应用程序运行时进行测试?
  • 我想通过完整的应用程序运行来测试 UserService 的行为。我的主要目标是灵活地指定我是要调用 bean 的真实方法还是模拟此方法(如您在两个测试方法中所见)
  • 我强烈建议不要在单个测试中混合使用。使用@SpringBootTest 的测试通常是使用实际bean 的集成测试。如果您想对UserService 的行为进行单元测试,则只需手动创建WalletService 的模拟并将其传递给您也手动创建的UserService 实例。
  • 我同意你的看法。但是想象一下,如果我在多个测试之间共享相同的 UserService 对象。我这样做是为了保持相同的 ApplicationContext(因为我有很多测试并且不想在每个测试中重新加载上下文)。在某些测试中,我希望 UserService 充当模拟对象,而在其他测试中 - 充当普通的真实对象。有没有办法在不重新加载 ApplicationContext 的情况下做到这一点?
  • 如果你在模拟 UserService 类,你怎么能测试它?

标签: java spring spring-boot mocking spring-test


【解决方案1】:

你需要使用指定调用方法后的返回值,当主动被调用时,会被Mockito拦截,返回你指定的值,如:

Mockito.when(userService.increaseBalance()).thenReturn(1);
userService.increaseBalance() // print :1

【讨论】:

  • 感谢您的回答,但在这种情况下,我希望 MockBean 具有灵活性。例如,在第一个测试方法中,我想调用真正的 bean 方法。在第二种测试方法中,我想模拟 bean 方法。
  • 如果要真正的调用,需要通过Spring容器注入。对于Mockito,他只是拦截回来,你可以看看他的源码。
猜你喜欢
  • 2020-02-19
  • 2017-05-11
  • 2022-10-20
  • 2020-11-03
  • 2019-07-27
  • 1970-01-01
  • 2019-11-18
  • 1970-01-01
  • 2019-04-30
相关资源
最近更新 更多