spring 如何在使用bpchar的h2数据库中执行单元测试?

xqkwcwgp  于 2024-01-05  发布在  Spring
关注(0)|答案(4)|浏览(146)

我有一个使用postgres数据库的spring + hibernate应用程序。我需要为控制器编写单元测试。对于测试,我想使用h2数据库,但不幸的是,测试崩溃时,bpchar数据类型无效。我想知道如何解决这个问题,这样我就可以运行测试。
我不能用bpchar将我的列更改为varchar,它需要保持原样。我也试图设置postgresql模式,但它没有帮助。我唯一的解决方案是使用嵌入式postgres数据库来执行测试,还是有其他方法可以使用?

iq0todco

iq0todco1#

实际上,你可以在你的 application.properties 中这样做,让H2知道:

spring.datasource.url=jdbc:h2:mem:testdb;INIT=CREATE TYPE BPCHAR AS CHARACTER NOT NULL

字符串
另外,请确保为您的测试关闭了数据库的自动配置。您可以通过添加:

@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
public class MyTestForTableWithBpcharColumn {

ltqd579y

ltqd579y2#

我唯一的解决方案是使用嵌入式postgres数据库来执行测试,或者还有其他方法可以使用,我是对的吗?
你尝试在h2中使用postgres-specific数据类型(h2没有),当然,它不起作用。
如果你不能改变这个字段的类型-在测试中使用嵌入式postgres。

jogvjijk

jogvjijk3#

解决此问题的一种有趣方法是Test Containers
由于Postgres没有嵌入式模式,但您可以使用上述框架在测试前启动Docker容器,如果您使用的是Flyway或Liquibase或集成自定义解决方案,则可以创建模式并应用迁移。
这个想法是容器将准备好并在测试运行时可用。在测试通过后(无论实际结果,成功或失败),您可以停止容器。
启动容器可能非常昂贵(几秒钟),但是您可以在测试期间利用spring缓存配置,因此当模块中的第一个测试开始时,容器实际上已经启动,但是,它在测试和测试用例之间被重用,因为应用程序上下文不会重新启动。
由于Spring的@Transactional annotation,在测试之间保持数据库干净也成为一项微不足道的任务,因此Spring会在每次测试后人为地回滚transaction。因为在Postgres中,即使是transaction命令也可以是transactional的,这应该足够好了。
这种方法的唯一限制是,如果你打算在本地运行这些测试,你应该在构建机器或本地开发机器上有一个可用的docker(在Linux和Mac OS上这不是问题,但在Windows上,你至少需要有Windows 10专业版才能安装docker环境)。
我在真实的项目中使用过这种方法,发现它对于集成测试非常有效。

2guxujil

2guxujil4#

我尝试了上面的解决方案,但它不工作。然后我发现了一个新的修复如下,它的工作。改变了以下在application.properties的单元测试资源

//Common properties for using the H2 database
spring.jpa.hibernate.dialect=org.hibernate.dialect.PostgreSQLDialect

字符串
在resources下为名为“schema.sql”的测试文件夹添加了一个新文件,内容如下:CREATE TYPE IF NOT EXISTS bpchar as varchar;
实体类注解看起来像这样
@Column(name = "XXXXX", length = 1, columnDefinition = "bpchar")
这两个变化对我来说很有用。

相关问题