【问题标题】:Mockito/Spring: mock only one function from Autowired ServiceMockito/Spring:仅模拟 Autowired Service 中的一项功能
【发布时间】:2021-01-25 15:46:38
【问题描述】:

我只想在真实服务上模拟一个功能,这是通过@Autowired(集成测试)注入的 ->

@SpringBootTest(classes = OrderitBackendApp.class)
@ExtendWith(MockitoExtension.class)
@AutoConfigureMockMvc
@WithUserDetails
public class OrderResourceIT {

    @Autowired
    private OrderRepository orderRepository;
    
    ...mor Injections and Tests

这里是模拟功能 ->

    @BeforeEach
    public void initTest() {
        MockitoAnnotations.initMocks(this);
        order = createEntity(em);
        OrderService spy = spy(orderService);
        when(spy.priceIsIncorrect(any())).thenReturn(false);
    }

但是我尝试过的这个和其他一些事情没有奏效。正确的做法是什么?

【问题讨论】:

  • this and a few other things didn't work 到底是什么意思?
  • 我尝试使用诸如 (@Autowired @InjectMocks) (@Autowired @Mock) (@Autowired @Spy) 之类的注释。我认为这个注释不能与@Autowired 一起使用
  • 您的间谍OrderService 是从哪里注入的?这就是我在这里缺少的一点。间谍服务需要进入您的测试系统(sut)是什么?
  • OrderService 在测试中被注入,我更新了描述。我希望它现在更容易理解。

标签: spring junit mockito


【解决方案1】:

如果您使用 Mockito,请尝试使用 @InjectMocks 和 @Mock 注释。 看下面的例子 https://www.springboottutorial.com/spring-boot-unit-testing-and-mocking-with-mockito-and-junit

【讨论】:

【解决方案2】:

假设我们有一个有两个方法的类

    public class OrderService {

    public String priceIsIncorrect(){
        return "price";
    }

    public String someOtherMethod(){
        return "other price";
    }
}

以下测试类将模拟一种方法并使用第二种方法的实际实现:

public class SomeRandomTest {
    private OrderService orderService = new OrderService();
    @Test
    public void test(){
        OrderService spy = Mockito.spy(orderService);
        Mockito.when(spy.priceIsIncorrect()).thenReturn("Spied method");
        System.out.println(spy.priceIsIncorrect()); //will return "Spied method"
        System.out.println(spy.someOtherMethod()); //will return "other price"

    }
}

【讨论】:

  • 这不适用于@Autowired :(。我需要它,因为它是一个集成测试
  • 可能是您在每一步的步骤之前创建本地间谍,但在测试后期您引用的是真实(全局)自动装配对象
【解决方案3】:

我缺少的是您的 OrderService 被注入到被测系统 (sut) 的关键点。

所以有两种选择:

  1. 使用反射将OrderService spy 实例设置为sut
  2. 恕我直言,最好的方法是在您的OrderService 实例上尝试@SpyBean,AFAIR 允许在您的应用程序上下文中使用间谍。试试看。稍后我需要研究文档。也许我错了。

进一步:在您的应用程序中,订单服务在哪里被调用? 对我来说,根据提供的代码,这并不清楚。

【讨论】:

    猜你喜欢
    • 2022-07-06
    • 2021-10-18
    • 2019-01-28
    • 1970-01-01
    • 1970-01-01
    • 2020-04-06
    • 1970-01-01
    • 2019-06-29
    • 1970-01-01
    相关资源
    最近更新 更多