当前位置: 首页 > 知识库问答 >
问题:

@SpringBootTest:@MockBean在多个测试类时未注入

辛可人
2023-03-14

我想编写控制器测试,也测试我的注释。到目前为止,我所读到的是,这是一条出路。

当我只有一个控制器可以顺利工作时。然而,当有两个或更多控制器测试类时,@mockbean似乎没有被正确使用。根据测试执行顺序,第一个测试类中的所有测试都会成功,而其他所有测试都会失败。

在下面的测试运行中,首先执行PotatoControllerTest,然后执行FooControllerTest。

@ExtendWith(SpringExtension.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@ActiveProfiles({"test", "httptest"})
class FooControllerTest {

    @MockBean
    protected FooService mockFooService;

    @MockBean
    protected BarService mockBarService;

    @LocalServerPort
    protected int port;

    @BeforeEach
    public void setup() {
        RestAssured.port = port;
        RestAssured.authentication = basic(TestSecurityConfiguration.ADMIN_USERNAME, TestSecurityConfiguration.ADMIN_PASSWORD);
        RestAssured.requestSpecification = new RequestSpecBuilder()
                .setContentType(ContentType.JSON)
                .setAccept(ContentType.JSON)
                .build();
    }

    @SneakyThrows
    @Test
    void deleteFooNotExists() {
        final Foo foo = TestUtils.generateTestFoo();
        Mockito.doThrow(new DoesNotExistException("missing")).when(mockFooService).delete(foo.getId(), foo.getVersion());

        RestAssured.given()
                .when().delete("/v1/foo/{id}/{version}", foo.getId(), foo.getVersion())
                .then()
                .statusCode(HttpStatus.NOT_FOUND.value());
        Mockito.verify(mockFooService, times(1)).delete(foo.getId(), foo.getVersion());
    }

...
}
@ExtendWith(SpringExtension.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@ActiveProfiles({"test", "httptest"})
class PotatoControllerTest {

    @MockBean
    protected PotatoService mockPotatoService;

    @LocalServerPort
    protected int port;

    @BeforeEach
    public void setup() {
        RestAssured.port = port;
        RestAssured.authentication = basic(TestSecurityConfiguration.ADMIN_USERNAME, TestSecurityConfiguration.ADMIN_PASSWORD);
        RestAssured.requestSpecification = new RequestSpecBuilder()
                .setContentType(ContentType.JSON)
                .setAccept(ContentType.JSON)
                .build();
    }

...

}
Wanted but not invoked:
fooService bean.delete(
    "10e76ae4-ec1b-49ce-b162-8a5c587de2a8",
    "06db13f1-c4cd-435d-9693-b94c26503d40"
);
-> at com.xxx.service.FooService.delete(FooService.java:197)
Actually, there were zero interactions with this mock.

我试图用一个通用的ControlllerTestBase来修复它,它配置所有模拟和所有其他扩展基类的控制器测试。它在我的机器上运行良好,但例如不在管道中。所以我猜它不是很稳定。

为什么Spring没有用mock重新加载上下文?这是测试我的html" target="_blank">控制器的“最佳”方法吗?

共有1个答案

仲孙超
2023-03-14

只使用MockMvc会更容易、更快。

您只需为所需的控制器创建一个独立设置,并进行其他配置(如设置异常解析程序)。此外,您还可以轻松地注入模拟:

@Before
public void init() {
  MyController myController = new MyController(mock1, mock2, ...);
  MockMvc mockMvc = 
  MockMvcBuilders.standaloneSetup(myController)
                 .setHandlerExceptionResolvers(...)
                 .build();
}

之后,您可以轻松调用endpoint:

MvcResult result = mockMvc.perform(
            get("/someApi"))
             .andExpect(status().isOk)
             .andReturn();

可以像您已经知道的那样对响应进行额外验证。

编辑:作为附带说明-这旨在显式测试您的Web层。如果您想在应用程序堆栈中进一步进行某种联调,同时涵盖业务逻辑,这不是正确的方法

 类似资料:
  • 我有这个类定义 其中保留是一个简单的Pojo ........ 原因:com.fasterxml.jackson.databind.exc.InvalidDefinitionException:找不到类org.mockito.internal.debugging.locationImpl的序列化程序,也找不到创建BeanSerializer的属性(若要避免异常,请禁用SerializationFe

  • 我用TestNG类创建了一个Maven项目。在TestNG。xml我已经给出了套件的名称。我使用了多个浏览器Chrome和Firefox来并行运行。仅使用setup类和一个以上的类就可以了,但是当我使用注释包含多个类时,我会得到一个注入错误,并给出一个错误。 我将提供我尝试过的代码 设置。JAVA 我得到的错误如下: 无法使用[class org.openqa.selenium.remote.De

  • 我在使用@mockbean注释时遇到了麻烦。文档说MockBean可以替换上下文中的bean,但我在单元测试中得到了一个NoUniqueBeanDefinitionException。我看不出如何使用注释。如果我可以模拟回购,那么显然会有不止一个bean定义。 错误消息:

  • 知道为什么@Context注入在单元测试时不起作用吗?

  • 我有一个SpringBootTest集成测试,用于我正在开发的某个框架,该框架使用与SpringBootApplication内置的jpa。我添加了支持在没有jpa的情况下使用框架,为此我需要创建一个不使用jpa的不同的SpringBootApplication。 现在,单独运行时的测试类工作得很好,但是当我一起运行它时(运行不同Spring应用程序的不同测试类),第二顺序测试类失败,因为我似乎没

  • 我想测试我的Spring应用程序。当我将@SpringBootTest添加到我的测试类中时,即使我等待了一个多小时,测试也会挂起并且不会开始!删除SpringBootTest注释会导致初始化@Value字段失败,并且我无法测试任何组件类。我的配置类代码: 我的测试类: 运行测试类时的堆栈跟踪: 当我运行该测试时,该测试处于挂起状态: