【问题标题】:Mock get request with Junit tests using data from h2 database使用来自 h2 数据库的数据通过 Junit 测试模拟获取请求
【发布时间】:2020-05-05 19:42:50
【问题描述】:

我知道我们可以模拟获取请求。我们可以模拟一个 get 请求并从 h2 数据库返回数据吗?

我的主要应用程序使用 Oracle 数据库。我能够填充一个 h2 数据库并编写一个 Junit 测试。但我只是打电话给服务。我想发出一个 get 请求并让它从 h2 数据库中提取数据。如何为此编写 Junit 测试?

感谢您的时间和帮助。

【问题讨论】:

标签: java spring-boot junit h2


【解决方案1】:

最简单的方法是TestRestTemplate。

使用 TestRestTemplate 和 @SpringBootTest 进行测试

我认为,这是测试您正在尝试做的事情的最简单方法之一。它会启动您的整个 Spring Boot 应用程序,并让您能够通过TestRestTemplate 与您的 REST Api 进行交互。

您需要为您的项目配置一些 maven 依赖项:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
    <scope>test</scope>
    <exclusions>
        <exclusion>
            <groupId>org.junit.vintage</groupId>
            <artifactId>junit-vintage-engine</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
</dependency>

然后,创建一个测试类。此类将启动您的 Spring Boot 应用程序并执行您的测试。

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
class ApplicationTest {

    @Autowired
    private TestRestTemplate testRestTemplate;

    @Test
    void testApplication() {
        int resourceId = 3;
        ResponseEntity<MyResponseObject> response = testRestTemplate.getForEntity("/myEndPoint/{resourceId}", MyResponseObject, resourceId);
        assertThat(response.getStatusCode()).isEqualTo(200);
        MyResponseObject  body = response.getBody();
        // then do what you want
    }
}

基本上,就是这样。以下是需要考虑的事项:

  • @SpringBootTest 将查找您的 @SpringBootApplication 或 @SpringBootConfiguration 注释。然后,它将加载您拥有的所有内容(包括服务和 h2 访问权限)。
  • SpringBootTest.WebEnvironment.RANDOM_PORT 将在您计算机上的任何可用端口上启动您的服务器。然后,您可以同时运行多个实例。
  • 通过在测试环境中将 h2 添加到您的类路径中,Spring 将自动创建数据源以与您的 h2 数据库通信。无需额外配置(通常我的意思是)。
  • TestRestTemplate 由 Spring Boot 自动提供。正如您在我的测试中注意到的那样,我既没有提供被测 SpringBoot 应用程序的主机也没有提供端口。 Spring 自动连接到良好的服务器......魔术。

如果你想要一个 tuto,请按此操作:https://www.baeldung.com/spring-boot-testresttemplate。
如果您想要 Spring Boot Test 文档,请按照以下说明操作:https://docs.spring.io/spring-boot/docs/current/reference/html/spring-boot-features.html#boot-features-testing-spring-boot-applications

你应该什么时候使用TestRestTemplate:

  • 跨应用程序的所有层进行测试时
  • 当您希望进行非常接近生产环境的测试时

什么时候不应该:

  • 当您的应用程序太长而无法启动时。当它加载有关您的应用程序的所有内容时,如果通常需要 20 秒才能启动,那么您的测试将至少需要 20 秒才能执行。很长。
  • 当您与根本无法控制的系统有依赖关系时,您也必须使用@MockBean。它不是银弹。它可以在您的本地机器上运行,但不能在您的 CI 服务器上运行。小心点。

使用 MockMvc 进行测试

使用MockMvc,您还可以模拟对控制器的测试,也可以模拟请求。这比全局@SpringBootTest 更具限制性,因为您不会启动整个应用程序,而只是启动一小部分,用于测试 Web 控制器层。大多数时候,您不会通过模拟其余部分来使用它来测试应用程序的所有层,而只是测试 Web 部件。

总有一种方法可以测试所有层,但显然,您需要添加要自己触发的类。

如果你想看看它的样子,去看看这个:https://www.baeldung.com/integration-testing-in-spring

如果您还有其他问题,请随时提问。

【讨论】:

  • 非常感谢鲁阿罗。如果我有任何问题,我会试试这个并回复你。
  • 当我更改我的 sql 文件中的值时,测试不会立即反映更改。为此我需要做什么?
  • 您所说的«不立即反映更改»是什么意思?你想解决什么问题?
  • 嗨 Ruaro 该解决方案效果很好。我有这个文件 data.sql,它为测试创建并填充 H2 中的表。我有一个创建表语句和插入语句。如果我更改插入的值并重新运行测试。如果我选择重新运行测试,这些更改不会得到反映。我意识到我必须关闭并重新打开junit窗口。有时不止一次。感谢您的帮助
猜你喜欢
  • 2015-11-20
  • 1970-01-01
  • 2018-09-12
  • 2013-07-13
  • 1970-01-01
  • 1970-01-01
  • 2019-07-08
  • 2021-07-09
  • 2015-05-01
相关资源
最近更新 更多