首页 > 解决方案 > 如何使用 Hibernate 将 JSON 格式的字符串插入 H2 数据库?

问题描述

我有一个 PostgresSQL 生产数据库,但我正在尝试针对内存中的 H2 运行一些自动化测试。我正在尝试将 JSON 格式的数据保存到表中,但是虽然我能够毫无怨言地写入数据,但当我读回它们时会出现转换异常。我在生产 Postgres 数据库中这样做没有问题。

我坚持的对象的结构类似于以下内容:

@Entity
public class Record {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;

    @Column(columnDefinition = "jsonb")
    @Convert(converter = PersonalInfoConverter.class)
    private PersonalInfo personalInfo;

    public Record() {}

    public Record(PersonalInfo personalInfo) {
        this.personalInfo = personalInfo;
    }

}

PersonalInfoConverter只是使用杰克逊将ObjectMapper对象从/序列化到一个(带有, 和的String非常标准的东西)。为了让 jsonb 与 H2 一起工作,我使用了这个技巧,它基本上将 jsonb 设置为 H2 的 JSON 的别名。writeValueAsStringreadValue

从数据库中读取记录时,我一直遇到转换错误,直到我偶然发现了这个问题,这与Github 上关于将 JSON 格式的字符串插入 H2 表的进一步讨论相关联。听起来好像能够让它正常工作,我需要专门注释插入到H2数据库中的字符串。我认为,如果是这种情况,那么 Hibernate 应该自己正确处理这个问题,但它似乎不是开箱即用的。如何配置我的代码以使其正常工作?

与此同时,我正在通过使用 jsonb 作为 H2 文本类型的别名来解决这个问题:

CREATE TYPE "JSONB" as text;

我创建了一个项目来演示这个问题

标签: javahibernatejpah2

解决方案


Hibernate 不知道“JSON”SQL 数据类型以及它需要如何处理。像现在这样使用文本,这完全没问题。AFAIU H2 中的 JSON 数据类型就像具有验证的域类型,即您可以将其替换为TEXT CHECK is_json(..),因此使用该特定数据类型没有太大价值。你可以告诉 hibernate 用来@ColumnTransformer附加 this FORMAT JSON,但是你会再次遇到 PostgreSQL 的问题。总的来说,这种使用 Hibernate 没有抽象出来的专有特性的跨数据库测试简直是一团糟。我建议您简单地删除 H2 并使用 fsync=off 的 PostgreSQL 进行测试,这已经相当快了。


推荐阅读