Java Spring引导-测试类在完成后不释放数据库连接

Java Spring引导-测试类在完成后不释放数据库连接,java,database,spring-boot,performance,testing,Java,Database,Spring Boot,Performance,Testing,我有一个Spring Boot应用程序,需要在其中测试所有内容。我遇到了这个问题 当我启动测试时(例如从Gitlab管道),测试从一开始就运行得很快。但测试越多,速度就越慢。为另一个测试类加载Spring应用程序上下文的速度越来越慢。我还发现,在测试期间,数据库连接保持活动状态,而应用程序在所有测试完成后会放开它们,即使大多数类很久以前就已经完成了。请问以前有没有人遇到过这个问题并找到了解决办法 我在测试中使用的注释: // Service test class example @ExtendW

我有一个Spring Boot应用程序,需要在其中测试所有内容。我遇到了这个问题

当我启动测试时(例如从Gitlab管道),测试从一开始就运行得很快。但测试越多,速度就越慢。为另一个测试类加载Spring应用程序上下文的速度越来越慢。我还发现,在测试期间,数据库连接保持活动状态,而应用程序在所有测试完成后会放开它们,即使大多数类很久以前就已经完成了。请问以前有没有人遇到过这个问题并找到了解决办法

我在测试中使用的注释:

// Service test class example
@ExtendWith(SpringExtension.class)
@DataJpaTest
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
@Import({SomeService.class})
@Sql("classpath:testdata/some_test_data.sql")
public class SomeServiceTest {

我通过两个步骤解决了此问题:

步骤1:DirtiesContext注释-这在完成特定类的测试后释放了DB连接,因此如果我设置
最大池大小:5
,它现在将只使用这5个连接

用法:

@DirtiesContext(classMode = ClassMode.AFTER_CLASS)
步骤2:为测试增加内存-我还必须为单元测试增加内存,这样我就不会从内存异常中得到
MAVEN_OPTS
对我不起作用,所以我必须在pom.xml中为此使用并配置插件

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-surefire-plugin</artifactId>
  <version>3.0.0-M5</version>
  <configuration>
    <argLine>-Xmx2048m</argLine>
  </configuration>
</plugin>

org.apache.maven.plugins
maven surefire插件
3.0.0-M5
-Xmx2048m
在此之后,我的测试管道时间要快得多。从大约20-30分钟开始,现在花了8分钟

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-surefire-plugin</artifactId>
  <version>3.0.0-M5</version>
  <configuration>
    <argLine>-Xmx2048m</argLine>
  </configuration>
</plugin>
非常感谢AndyWilkinson提供的好建议

编辑 在这之后,我的测试报告声纳的覆盖率为0%。经过一段时间的搜索,我也找到了解决方案:

步骤3:定义属性sonar.surefire.argLine

<properties>
  ...
  <sonar.surefire.argLine>-Xmx2048m</sonar.surefire.argLine>
</properties>

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-surefire-plugin</artifactId>
  <version>3.0.0-M5</version>
  <configuration>
    <argLine>@{argLine} ${sonar.surefire.argLine}</argLine>
  </configuration>
</plugin>


...
-Xmx2048m
步骤4:重写插件

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-surefire-plugin</artifactId>
  <version>3.0.0-M5</version>
  <configuration>
    <argLine>@{argLine} ${sonar.surefire.argLine}</argLine>
  </configuration>
</plugin>


org.apache.maven.plugins
maven surefire插件
3.0.0-M5
@{argLine}${sonar.surefire.argLine}

这里的问题是,jacoco插件需要访问surefire的argLine,但是手动添加后,就不可能了。这就是为什么我必须添加
@{argLine}
,这是jacoco使用的
${sonar.surefire.argLine}
只是为了更好的代码外观,所以我可以用其他定义的属性设置
-Xmx2048m
参数。

我无法确定您迄今为止共享的内容,但听起来好像您正在启动多个不同的应用程序上下文(当您的测试具有不同的配置时会发生这种情况)每个上下文都在创建一个数据库连接池。这些上下文被缓存(以允许在具有相同配置的测试之间重用),并且在缓存填满或JVM关闭之前不会被关闭。听起来你看到的是后者。@AndyWilkinson你觉得这些注释有什么问题吗?控制器测试配置在整个项目中几乎相同(当然,只有Sql文件不同)。在服务测试中,当然是Sql文件,但在导入注释中也有不同的类(但有可能用ComponentScan注释替换它,就像在控制器测试中一样,但我想这会延长加载时间)。这两个测试类将创建两个不同的上下文。如果你有更多不同的配置,那么这可能是你的问题的原因。如果不能在测试类中使用公共配置来最小化创建的上下文数量,则可以使用
@DirtiesContext
来防止缓存。或者,您可以调整连接池以减少它们创建的连接数。1可能足够了,因为您的测试可能是单线程的。@AndyWilkinson由于
@DirtiesContext
,问题的一半得到了解决。在完成类中的所有测试之后,它将释放DB连接。然而,另一个问题仍然存在。应用程序上下文似乎仍然处于活动状态,因为测试越多,速度就越慢。我现在也得到了java内存不足的异常。我使用的注释如下
@DirtiesContext(classMode=classMode.AFTER\u CLASS)
。你知道会出什么问题吗?不,对不起。不是从你到目前为止所分享的。我需要看到足够的东西来重现问题,以诊断我认为的那个问题。听起来好像你的某个地方有内存泄漏。探查器可以帮助您确定原因。