如何在@DatabaseSetup的XML数据集插入PostgreSQL复合类型数据?
解决PostgreSQL复合类型在DBUnit XML数据集中的插入问题
方案1:改用SQL脚本替代XML数据集
这是最直接的解决方式,既然你已经能通过SQL正常插入数据,直接把测试数据写成SQL脚本,让@DatabaseSetup加载.sql文件即可:
- 创建测试用SQL文件(比如
test-data.sql):
INSERT INTO my_table (id, ds) VALUES (1, ('2025-04-03 09:38:08'::timestamptz, 2)); INSERT INTO my_table (id, ds) VALUES (2, ('2025-04-04 10:00:00'::timestamptz, 5));
- 在测试类中指定加载该SQL文件:
@DatabaseSetup("/test-data.sql") public class MyTableTest { // 测试逻辑 }
方案2:自定义DBUnit的DataTypeFactory支持复合类型
DBUnit默认的PostgreSQL数据类型工厂未处理复合类型逻辑,需扩展它来识别自定义复合类型:
- 实现自定义DataTypeFactory:
import org.dbunit.ext.postgresql.PostgresqlDataTypeFactory; import java.sql.Types; public class CustomPostgresDataTypeFactory extends PostgresqlDataTypeFactory { @Override public int getSqlType(String sqlTypeName) { // 识别自定义复合类型my_type,映射为DBUnit的OBJECT类型 if ("my_type".equalsIgnoreCase(sqlTypeName)) { return Types.OTHER; } return super.getSqlType(sqlTypeName); } }
- 在测试类中配置DBUnit使用该自定义工厂:
@DbUnitConfiguration(dataTypeFactory = CustomPostgresDataTypeFactory.class) @DatabaseSetup("/test-data.xml") public class MyTableTest { // 测试逻辑 }
- 对应的XML数据集写法(使用PostgreSQL复合类型文本格式):
<dataset> <my_table id="1" ds="('2025-04-03 09:38:08', 2)" /> <my_table id="2" ds="('2025-04-04 10:00:00', 5)" /> </dataset>
方案3:拆分复合类型字段,插入时重组(适合需单独维护子字段的场景)
如果需要在XML里单独维护复合类型的子字段,可以先将子字段作为普通字段写入XML,再通过SQL在插入后组合成复合类型:
- XML数据集写法:
<dataset> <my_table id="1" ds_ts="2025-04-03 09:38:08" ds_val="2" /> </dataset>
- 在测试类中执行SQL重组复合类型:
@DatabaseSetup("/test-data.xml") @BeforeEach void afterSetup() { // 将拆分字段组合为复合类型列 jdbcTemplate.update("UPDATE my_table SET ds = (ds_ts::timestamptz, ds_val::int) WHERE ds IS NULL"); // 可选:删除临时拆分字段 jdbcTemplate.update("ALTER TABLE my_table DROP COLUMN ds_ts, DROP COLUMN ds_val"); }
注:此方案需要先给表临时添加ds_ts和ds_val字段,确保XML能正常插入。
内容的提问来源于stack exchange,提问作者elcye
相关产品推荐
相关产品推荐

