从内存数据库版本 1.4.X 更新到 2.1.x 中的 H2 后出现异常
Exceptions after updating from H2 in memory db version 1.4.X to 2.1.x
我使用 H2 内存数据库进行集成测试,而不是将 Oracle 用于实时系统。
在我更新到新的主要 H2 版本 2 后,测试会抛出如下异常:
Syntax error in SQL statement "select test0_.ID as id1_1_3_, test0_.TEST_ID as test_2_1_3_, test0_.PU_ID as pu8_1_3_, testpar1_.TEST_ID as test_4_2_5_, testpar1_.ID as id1_2_5_, testpar1_.ID as id1_2_0_, testpar1_.TEST_ID as test_4_2_0_, testpar1_.NAME as name2_2_0_, testpar1_.[*]VALUE as value3_2_0_, from testschema.TEST test0_ left outer join testschema.PU pu2_ on test0_.PU_ID=pu2_.ID where test0_.ID=?"; expected "identifier";
这是一个示例实体:
@Entity
@Table(name = "TEST")
@SequenceGenerator(name = "TEST_SEQUENCE_GENERATOR",
sequenceName = "TEST_SEQ",
allocationSize = 1)
public class Test {
@Id
@Column(name = "ID")
@GeneratedValue(generator = "TEST_SEQUENCE_GENERATOR", strategy = GenerationType.SEQUENCE)
private Long id;
这些是设置的属性:
properties.put("javax.persistence.jdbc.driver", "org.h2.Driver");
properties.put(
"javax.persistence.jdbc.url",
"jdbc:h2:mem:testschema;DB_CLOSE_ON_EXIT=FALSE;INIT=CREATE SCHEMA IF NOT EXISTS TESTSCHEMA");
properties.put("javax.persistence.jdbc.user", "testschema");
properties.put("javax.persistence.jdbc.password", "");
properties.put("hibernate.default_schema", "testschema");
properties.put("hibernate.show_sql", "false");
properties.put(
"hibernate.cache.region.factory_class",
"org.hibernate.cache.ehcache.SingletonEhCacheRegionFactory");
properties.put("hibernate.hbm2ddl.auto", "create-drop");
properties.put("hibernate.order_by.default_null_ordering", "last");
properties.put("hibernate.dialect", "org.hibernate.dialect.H2Dialect");
我查看了H2网页上的迁移指南,但没有找到失败的原因。
VALUE
是 H2 中的关键字,并且是 SQL 标准中的保留字(即使在古老的 SQL-92 中也是如此)。当它用作标识符时,需要将其引用为"VALUE"
。 Hibernate ORM有一个hibernate.globally_quoted_identifiers
设置,可以设置为true
引用所有标识符,你可以启用它。
如果你因为某些原因不想全部引用,你可以在H2的JDBC URL中加上;NON_KEYWORDS=VALUE
,但是这个设置可能不会全部生效案例。
对于 Hibernate ORM 5.6.4 和更早的版本,您还需要 ;MODE=LEGACY
,因为其中的 H2Dialect
会产生无效的 SQL,默认情况下会被 H2 2.x 拒绝。它已在 5.6.5 中修复。
我使用 H2 内存数据库进行集成测试,而不是将 Oracle 用于实时系统。 在我更新到新的主要 H2 版本 2 后,测试会抛出如下异常:
Syntax error in SQL statement "select test0_.ID as id1_1_3_, test0_.TEST_ID as test_2_1_3_, test0_.PU_ID as pu8_1_3_, testpar1_.TEST_ID as test_4_2_5_, testpar1_.ID as id1_2_5_, testpar1_.ID as id1_2_0_, testpar1_.TEST_ID as test_4_2_0_, testpar1_.NAME as name2_2_0_, testpar1_.[*]VALUE as value3_2_0_, from testschema.TEST test0_ left outer join testschema.PU pu2_ on test0_.PU_ID=pu2_.ID where test0_.ID=?"; expected "identifier";
这是一个示例实体:
@Entity
@Table(name = "TEST")
@SequenceGenerator(name = "TEST_SEQUENCE_GENERATOR",
sequenceName = "TEST_SEQ",
allocationSize = 1)
public class Test {
@Id
@Column(name = "ID")
@GeneratedValue(generator = "TEST_SEQUENCE_GENERATOR", strategy = GenerationType.SEQUENCE)
private Long id;
这些是设置的属性:
properties.put("javax.persistence.jdbc.driver", "org.h2.Driver");
properties.put(
"javax.persistence.jdbc.url",
"jdbc:h2:mem:testschema;DB_CLOSE_ON_EXIT=FALSE;INIT=CREATE SCHEMA IF NOT EXISTS TESTSCHEMA");
properties.put("javax.persistence.jdbc.user", "testschema");
properties.put("javax.persistence.jdbc.password", "");
properties.put("hibernate.default_schema", "testschema");
properties.put("hibernate.show_sql", "false");
properties.put(
"hibernate.cache.region.factory_class",
"org.hibernate.cache.ehcache.SingletonEhCacheRegionFactory");
properties.put("hibernate.hbm2ddl.auto", "create-drop");
properties.put("hibernate.order_by.default_null_ordering", "last");
properties.put("hibernate.dialect", "org.hibernate.dialect.H2Dialect");
我查看了H2网页上的迁移指南,但没有找到失败的原因。
VALUE
是 H2 中的关键字,并且是 SQL 标准中的保留字(即使在古老的 SQL-92 中也是如此)。当它用作标识符时,需要将其引用为"VALUE"
。 Hibernate ORM有一个hibernate.globally_quoted_identifiers
设置,可以设置为true
引用所有标识符,你可以启用它。
如果你因为某些原因不想全部引用,你可以在H2的JDBC URL中加上;NON_KEYWORDS=VALUE
,但是这个设置可能不会全部生效案例。
对于 Hibernate ORM 5.6.4 和更早的版本,您还需要 ;MODE=LEGACY
,因为其中的 H2Dialect
会产生无效的 SQL,默认情况下会被 H2 2.x 拒绝。它已在 5.6.5 中修复。