【问题标题】:HibernateException: Wrong column type:x, expected: y on SybaseHibernateException:错误的列类型:x,预期:y 在 Sybase
【发布时间】:2015-01-02 15:33:12
【问题描述】:

我对以下技术没有太多背景知识,因此我们将不胜感激。如果有不清楚的地方,请随时提出问题。

我目前正在进行一个迁移项目,我们正在更新多项技术,包括:

  1. Sybase - 从 12.x 到 15.7
  2. JConnect - 从多个版本到 7.0.7_SP130

现在,我们的应用部署到 JBoss 4.x 并使用 Hibernate 3.2.4.sp1。在旧数据库中,我们有许多看起来像这样的自定义数据类型(对不起,我很想把它放在表格格式中,但我不知道如何在这里......):

  • 自定义数据类型:TYPE1,基本数据类型:图像
  • 自定义数据类型:TYPE2,基本数据类型:tinyint

我们的 DDL 中的某些列使用自定义数据类型:

CREATE TABLE y (
   our_column_name TYPE1,
   ...
);

当服务器启动时,我收到以下错误消息:

... javax.persistence.PersistenceException: org.hibernate.HibernateException:错误的列类型:our_column_name, 预期:图片

这不是旧设置中发生的情况。请注意,在我们定义的所有自定义数据类型中,只有具有 imagetinyint 的数据类型存在问题;其他的都被识别并且不会抛出错误。

我们在 JConnect 驱动程序上运行了跟踪,它似乎正在检索正确的数据类型,这就是我现在关注 HibernateException 的原因。我看过一些类似的帖子(发生在不同的数据库上),但基本上,他们给出了类似的解决方法:

  1. this one 这样的站点,建议我们更改数据库表的列以使用基本数据类型而不是自定义数据类型。我们通过将 our_column_name 的数据类型更改为 image 来完成此操作。完成此操作并重新启动服务器后,错误就会消失。但是,它没有解释为什么或导致问题的原因。

  2. This 建议使用 JPA 注释的@Column(columnDefinition='image')。我们也试过这个,但它似乎对启动没有任何影响(即仍然发生错误)。

  3. 在与 #2 相同的链接中,建议扩展 SQL 方言。但是,我认为这是不可行的 - 只有 2 个自定义数据类型(image 和 tinyint)似乎导致了我们这边的问题,所以这可能是矫枉过正。

  4. This site 建议从 persistence.xml 中删除 hibernate.hbm2ddl.auto=validate。没有尝试过,因为我们需要验证。

  5. 改用数据类型“LOB”

自从这里抛出异常后,我也尝试检查 Hibernate 的代码 - org.hibernate.mapping.Table.validateColumns(Table.java:261),这几乎指向了这一行:

boolean typesMatch = (col.getSqlType(dialect, mapping).startsWith(columnInfo.getTypeName().toLowerCase())) || (columnInfo.getTypeCode() == col.getSqlTypeCode(mapping));

但是,Hibernate 的 API 文档在细节方面有些欠缺,所以我目前在追踪它时遇到了一些困难......

关于导致异常的原因有什么想法吗?如果它在旧版本中工作,想知道 Hibernate(或 Sybase 中的哪些变化)会导致这种情况?

This 文档表明 Hibernate 已针对 Sybase 15.7 进行了测试,因此我不知道该去哪里继续寻找。上面的#1会是最好的解决方法吗?如果是这样,任何想法为什么应该使用基本类型而不是自定义数据类型(本质上,这会使自定义数据类型变得无用......)

再次提前致谢!

编辑

尝试了以下方法:

  1. 如果使用@Column(columnDefinition='my_custom_datatype'),则错误消失。
  2. 如果从persistence.xml 中删除hibernate.hbm2ddl.auto=validate,错误就会消失。

我真的怀疑这是一个休眠问题...

【问题讨论】:

    标签: java hibernate sybase


    【解决方案1】:

    这在本质上与this question on SO 相似,即上面查询中的代码中的typesMatch 将是错误的,因为colcolumnInfo 返回的值不同 - 一个是返回基本数据类型,即其他正在返回自定义用户类型。

    所以,为了解决这个问题,有很多变通方法是可能的(我在上面的帖子中已经提到过)-

    1. 如果可以,请删除 hibernate.hbm2ddl.auto=validate
    2. 直接在 DB 中更改列数据类型,我认为这是下一个最快的方法。
    3. 在 Java 类中使用 @Column(columnDefinition='my_custom_datatype')

    【讨论】:

      【解决方案2】:

      如果你使用@DiscriminatorColumn,记得也放在那里。 像这样:

      @DiscriminatorColumn(name = "MyTableName", discriminatorType = DiscriminatorType.STRING, columnDefinition = "char")
      

      进入属性

          @Column(name="MyColumnName",nullable = true, insertable = true, updatable = true, length = 1, columnDefinition = "char")
          private String type;
      

      【讨论】:

        猜你喜欢
        • 2021-01-18
        • 2015-08-14
        • 1970-01-01
        • 2018-01-22
        • 2023-04-06
        • 2022-01-10
        • 1970-01-01
        • 1970-01-01
        • 2014-09-10
        相关资源
        最近更新 更多