Hibernate,Postgresql:列“x”的类型为oid,但表达式的类型为byte

时间:2010-12-20 10:21:19

标签: hibernate postgresql annotations bytearray oid

在不同数据库之间切换时,我对包含大对象(BLOB)的hibernate映射有一个奇怪的问题。

@Lob
private byte[] binaryData;

上面的字段在MySQL和Oracle中创建了一个字节数组字段,但在PostreSQL中它创建了一个oid类型的字段。

现在,当我尝试访问此字段时,它在其他数据库中工作正常,但在PostgreSQL中它失败并出现以下错误

Column "binaryData" is of type oid but expression is of type bytea.

所以我试着简单地删除“@Lob”注释,它将解决PostgreSQL的问题,但是在没有这个注释的MySQL中,hibernate创建了一个类型为“tinyblob”的字段,在我们的大多数情况下它都很小。而且,由于我们希望在多个环境中使用此项目,因此需要切换两个不同的映射是很烦人的。

对于使用@Lob注释的字段,是否有任何注释强制postgreSQL使用bytea而不是oid?或者是否有可能省略@Lob并放置其他内容以强制MySQL使用更大的数据类型分配它,就像使用@Lob一样?

我甚至可以想象有这样的解决方案

if (field is of type oid)
  store it as oid
else if (field is of type bytea)
  store it as bytea
else
  // not storable

和getter一样,如果有办法做到这一点

修改

以下声明正在发挥作用。它将列分配为oid,但是使用它的hibernate知道如何从这样的字段存储和检索数据

@Lob
@Type(type="org.hibernate.type.PrimitiveByteArrayBlobType")
private byte[] binaryFile;

3 个答案:

答案 0 :(得分:10)

此字段映射在org.hibernate.dialect.PostgreSQLDialect中定义,可以通过子类化并配置应用程序以在使用postgres运行时使用修改后的方言来更改。

子类中的相关咒语可能是

    registerColumnType( Types.BLOB, "bytea" );
调用super()后,在构造函数中

答案 1 :(得分:0)

对我而言,这可能意味着“将你的postgres jdbc版本恢复为9.3-1101.jdbc4”

  <dependency>
    <groupId>org.postgresql</groupId>
    <artifactId>postgresql</artifactId>
    <version>9.4-1200-jdbc41</version>
  </dependency>

工作得很好。比失败更新......

答案 2 :(得分:0)

从Hibernate 3.6开始不推荐使用该类。现在使用最新的Hibernate,我们需要改为使用@Type(type="org.hibernate.type.MaterializedBlobType")。请检查https://docs.jboss.org/hibernate/core/3.6/javadocs/deprecated-list.htmlhttps://docs.jboss.org/hibernate/core/3.6/javadocs/org/hibernate/type/MaterializedBlobType.html了解更多信息。