Hibernate列名中的特殊字符

时间:2015-07-11 21:18:47

标签: java hibernate postgresql

我有一个名为@id的列的表 我想执行此查询:

select DISTINCT "@id" from "osm_art_center"

在Java(Hibernate)中。

问题是Hibrernate无法理解@id并返回错误,即id列不存在。

修改

导致错误的代码:

String columnName="@id";
String tableName="osm_art_center";
ResultSet polygonSearch;
polygonSearch = st.executeQuery("select DISTINCT "+columnName+" from "+tableName);

抛出的错误:

SQL Error: org.postgresql.util.PSQLException: ERROR: column "id" does not exist

2 个答案:

答案 0 :(得分:3)

尝试引用列名:

String sql ="select DISTINCT \"@id\" from osm_art_center;
ResultSet polygonSearch = st.executeQuery(sql);

Java语言没有剥离或改变" @"你的字符串。但是,完全可能的是,您使用的JDBC驱动程序的行为与PostgreSQL命令解释程序的行为不同。

无论哪种方式,请尝试转义特殊字符。

答案 1 :(得分:3)

我在这里发生的事情是Hibernate在传递给数据库时没有引用标识符,因此PostgreSQL将不带引号的@id解释为应用于标识符@的运算符id。前缀运算符之前不需要空格;就像你可以写a+b而不是a + b一样,所以你可以写@id@ id来将运算符@应用到列id

演示:

test=> CREATE TABLE iddemo("@id" integer);
CREATE TABLE
test=> SELECT @id FROM iddemo;
ERROR:  column "id" does not exist
LINE 1: SELECT @id FROM iddemo;

如果您引用标识符,则会生成预期结果:

test=> SELECT "@id" FROM iddemo;
 @id 
-----
(0 rows)

这是IMO的一个Hibernate错误。它应该引用它传递给数据库的所有标识符。如果不这样做意味着用户必须手动引用标识符,如果他们想要任何大写,包含空格,使用保留字等等。看起来他们已经修复了这个但是默认情况下没有启用修复以实现向后兼容;见Automatic reserved word escaping for Hibernate tables and columns

您可以通过在定义中插入引号来解决此错误,但它可能会在其他地方产生副作用。

String columnName="\"@id\"";

或通过在hibernate.globally_quoted_identifiers(或Hibernate配置文件或其他)中将true设置为persistence.xml来全局修复Hibernate项目配置。