【问题标题】:spring boot test unable to inject TestRestTemplate and MockMvcspring boot 测试无法注入 TestRestTemplate 和 MockMvc
【发布时间】:2017-01-05 21:56:56
【问题描述】:

我正在使用弹簧靴1.4.0.RELEASE。我正在为我的控制器类编写测试。我得到以下异常。

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'com.concur.cognos.authentication.service.ServiceControllerITTest': Unsatisfied dependency expressed through field 'restTemplate': No qualifying bean of type [org.springframework.boot.test.web.client.TestRestTemplate] found for dependency [org.springframework.boot.test.web.client.TestRestTemplate]: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [org.springframework.boot.test.web.client.TestRestTemplate] found for dependency [org.springframework.boot.test.web.client.TestRestTemplate]: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}

这是我的测试课

public class ServiceControllerITTest extends ApplicationTests {

    @Autowired
    private TestRestTemplate restTemplate;

    @Autowired
    private MockMvc mvc;

    @Test
    public void exampleTest() throws Exception {
         // test
    }
}

ApplicationTests.java

@RunWith(SpringRunner.class)
@SpringBootTest
@WebAppConfiguration
//@DirtiesContext
public class ApplicationTests {

    @Autowired
    Environment env;

    @Test
    public void contextLoads() {

    }

}

【问题讨论】:

    标签: spring-mvc spring-boot spring-test


    【解决方案1】:

    TestRestTemplate 只有在 @SpringBootTest 配置了 webEnvironment 时才会自动配置,这意味着它会启动 Web 容器并侦听 HTTP 请求。例如:

    @SpringBootTest(webEnvironment=WebEnvironment.RANDOM_PORT)
    

    【讨论】:

    • 我添加了。现在我得到java.lang.IllegalStateException: Failed to load ApplicationContext at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContext
    • 您还在尝试自动连接TestRestTemplateMockMvc 吗?这样做没有意义。您应该使用其中一种。
    • @AndyWilkinson 我发现了相同的行为(注入其中一个或两个),并且文档明确指出 @SpringBootTest 的默认值是 MOCK
    • @chrylis 正如我上面所说,你需要使用RANDOM_PORT 才能注入TestRestTemplate
    • @avinesh 其他 cmets 已经解释了为什么它没有解决 MockMvc。在同一个测试中使用TestRestTemplateMockMvc 是没有意义的。一种是使用嵌入式 servlet 容器通过 HTTP 测试服务,另一种是使用模拟 servlet 容器在没有 HTTP 的情况下测试服务。
    【解决方案2】:

    如果您阅读 SpringBootTest 注解的 java 文档,它会说注解提供以下功能(此处未列出所有功能,仅列出与问题相关的功能。)

    • 提供对不同 webEnvironment 模式的支持,包括启动在定义或随机端口上侦听的完全运行的 Web 服务器的能力。
    • 注册 TestRestTemplate 和/或 WebTestClient bean 以用于 Web 测试,这些测试使用完全运行的 Web 服务器侦听定义或随机端口。

    所以 @SpringBootTest(webEnvironment=WebEnvironment.RANDOM_PORT) 提供了自动装配 TestRestTemplate 的能力,因为它启动了一个完全运行的 Web 服务器 [正如 @AndyWilkinson 的回答中提到的那样]。

    但是如果你想在同一个 TestClass 中自动装配 MockMvc 然后使用 @AutoConfigureMockMvc 在 TestClass 上注解。

    这是一个测试类的样子:

    @RunWith(SpringRunner.class)
    @SpringBootTest(webEnvironment=WebEnvironment.RANDOM_PORT)
    @AutoConfigureMockMvc
    public class SBTest {
        @Autowired
        private TestRestTemplate restTemplate;
    
        @Autowired
        private MockMvc mvc;
    
       // tests
    }
    

    【讨论】:

      【解决方案3】:

      要使用它,请不要使用已弃用的 TestRestTemplate。

      已弃用:

      import org.springframework.boot.test.TestRestTemplate;
      

      正确:

      import org.springframework.boot.test.web.client.TestRestTemplate;
      

      然后你可以在你的类中使用@Autowired注解:

      @Autowired
      private TestRestTemplate restTemplate;
      

      不要使用:

      @Autowired
      private MockMvc mvc;
      

      两者一起不起作用。

      【讨论】:

        【解决方案4】:

        根据Spring boot documentation

        您还可以在非@WebMvcTest(例如SpringBootTest)中自动配置MockMvc,方法是使用@AutoConfigureMockMvc 对其进行注释。

        【讨论】:

        • 这个答案帮助了我的@WebMvcTest(Spring Boot 2.5.5)。我刚刚在我的测试课上添加了@AutoConfigureWebClient,然后我遇到的UnsatisfiedDependencyException 不见了,谢谢。
        猜你喜欢
        • 2014-08-12
        • 2018-02-09
        • 2020-06-22
        • 2019-06-01
        • 1970-01-01
        • 2018-07-28
        • 2019-01-14
        • 2019-01-20
        • 2015-01-01
        相关资源
        最近更新 更多