Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Using cast in a empty string with createNativeQuery arises an exception [JDBC298] #344

Closed
firebird-automations opened this issue Feb 8, 2013 · 16 comments

Comments

@firebird-automations
Copy link

Submitted by: Edilmar Alves (edilmar)

Is related to JDBC260
Is related to JDBC162
Is duplicated by JDBC303

I have a SQL with use of "cast" like this:

select cast(c.historico as varchar(2000)) as historico from conhecimento c where c.numero = 1

When I use Jaybird2.1.6, there is no problems.

However, with Jaybird2.2.2, it arises this exception:

SEVERE: Empty string does not identify column.
javax.persistence.PersistenceException: org.hibernate.exception.GenericJDBCException: could not execute query
at org.hibernate.ejb.AbstractEntityManagerImpl.throwPersistenceException(AbstractEntityManagerImpl.java:637)
at org.hibernate.ejb.QueryImpl.getResultList(QueryImpl.java:74)
at dao.ConhecimentoJpaDAO.getConhecimentoImp(ConhecimentoJpaDAO.java:670)
at dao.ConhecimentoJpaDAO.main(ConhecimentoJpaDAO.java:142)
Caused by: org.hibernate.exception.GenericJDBCException: could not execute query
at org.hibernate.exception.SQLStateConverter.handledNonSpecificException(SQLStateConverter.java:103)
at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:91)
at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
at org.hibernate.loader.Loader.doList(Loader.java:2223)
at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2104)
at org.hibernate.loader.Loader.list(Loader.java:2099)
at org.hibernate.loader.custom.CustomLoader.list(CustomLoader.java:289)
at org.hibernate.impl.SessionImpl.listCustomQuery(SessionImpl.java:1695)
at org.hibernate.impl.AbstractSessionImpl.list(AbstractSessionImpl.java:142)
at org.hibernate.impl.SQLQueryImpl.list(SQLQueryImpl.java:152)
at org.hibernate.ejb.QueryImpl.getResultList(QueryImpl.java:65)
... 2 more
Caused by: org.firebirdsql.jdbc.FBSQLException: Empty string does not identify column.
at org.firebirdsql.jdbc.AbstractResultSet.findColumn(AbstractResultSet.java:1038)
at org.firebirdsql.jdbc.AbstractResultSet.getField(AbstractResultSet.java:675)
at org.firebirdsql.jdbc.AbstractResultSet.getString(AbstractResultSet.java:719)
at com.mchange.v2.c3p0.impl.NewProxyResultSet.getString(NewProxyResultSet.java:3342)
at org.hibernate.type.StringType.get(StringType.java:18)
at org.hibernate.type.NullableType.nullSafeGet(NullableType.java:163)
at org.hibernate.type.NullableType.nullSafeGet(NullableType.java:189)
at org.hibernate.loader.custom.CustomLoader$ScalarResultColumnProcessor.extract(CustomLoader.java:474)
at org.hibernate.loader.custom.CustomLoader$ResultRowProcessor.buildResultRow(CustomLoader.java:420)
at org.hibernate.loader.custom.CustomLoader.getResultColumnOrRow(CustomLoader.java:317)
at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:606)
at org.hibernate.loader.Loader.doQuery(Loader.java:701)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:236)
at org.hibernate.loader.Loader.doList(Loader.java:2220)
... 9 more

@firebird-automations
Copy link
Author

Commented by: Edilmar Alves (edilmar)

I tried to use "case" workaround (that works with 2.1.6), but it didn't work:

select case when c.historico = '' then 'teste' else cast(c.historico as varchar(2000)) end as historico from conhecimento c where c.numero = 1

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

In Jaybird 2.2 we changed what is reported for the ResultSetMetaData properties columnName and columnLabel for compliance with the JDBC 4.x spec (see JDBC162) The Hibernate class org.hibernate.loader.custom.CustomLoader is using the columnName to find the column instead of the columnLabel as they should.

The solution/workaround is to use the connection property columnLabelForName=true (see JDBC260 and the release notes under "Changes and fixes in Jaybird 2.2.1" and "Compatibility with com.sun.rowset.*")

This property can be added to the connection properties:
* Through a properties object (with value true)
* In the connection URL (columnLabelForName=true)
* On a (Jaybird) DataSource by setting setNonStandardProperty("columnLabelForName", "true") or setNonStandardProperty("columnLabelForName=true");

It seems to be related to Hibernate issues:
https://hibernate.onjira.com/browse/HHH-2094 (closed)
https://hibernate.onjira.com/browse/HHH-4875
https://hibernate.onjira.com/browse/HHH-4956

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

A quick look at the code of Hibernate 4.1.9 Final (without actually testing it) suggests it is fixed in that version.

@firebird-automations
Copy link
Author

Modified by: @mrotteveel

Link: This issue is related to JDBC260 [ JDBC260 ]

@firebird-automations
Copy link
Author

Modified by: @mrotteveel

Link: This issue is related to JDBC162 [ JDBC162 ]

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

I am closing the issue as 'Won't fix', but don't hesitate to add a comment (or post on the Firebird-Java mailinglist) if you run into more problems with this.

@firebird-automations
Copy link
Author

Modified by: @mrotteveel

status: Open [ 1 ] => Resolved [ 5 ]

resolution: Won't Fix [ 2 ]

@firebird-automations
Copy link
Author

Modified by: @mrotteveel

status: Resolved [ 5 ] => Closed [ 6 ]

@firebird-automations
Copy link
Author

Commented by: Edilmar Alves (edilmar)

Doubt: how could I set up the persistence.xml for this property?
I tried this without sucess...
<property name="hibernate.connection.columnLabelForName" value="true"/>

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

columnLabelForName is a Jaybird connection property, not a Hibernate property. So you need to specify it either in the connection URL or as a datasource property (but only if you are using a Firebird datasource); the datasourceproperty would then be "nonStandardProperty" with value "columnLabelForName=true"

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

Also it could be that using <property name="hibernate.connection.columnLabelForName" value="true"/> will work, but I am simply not sure. Let me know if that works too.

@firebird-automations
Copy link
Author

Commented by: Edilmar Alves (edilmar)

Unfortunatelly the property setup in persistence.xml doesn't work.
Then, in my way, I have to use the URL property directly in Connection Pool from GlassFish.
But now if I have to test this query without GlassFish, just running a main() method to check up the DAO class, it is not possible for these kind of SQLs with casts.

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

If you work without glassfish, how do you configure and get your connection? Just add the property to the connection URL there.

@firebird-automations
Copy link
Author

Commented by: Edilmar Alves (edilmar)

In the tests out of GF (with direct main()), I program this way and now it worked fine with hibernate.connection.url:

  EntityManagerFactory emf = Persistence\.createEntityManagerFactory\("sat"\);
  EntityManager emAux = emf\.createEntityManager\(\);
  ConhecimentoDAO dao = new ConhecimentoJpaDAO\(\);
  dao\.setEntityManager\(emAux\);
  List<ConhecimentoImp\> list = dao\.getConhecimentoImp\(idConhecimento\); // the method with SQL Native Query using cast\(\)

Then, Persistence uses persistence.xml like this:

<persistence-unit name="sat" transaction-type="RESOURCE_LOCAL">
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.FirebirdDialect"/>
<property name="hibernate.connection.driver_class" value="org.firebirdsql.jdbc.FBDriver"/>
<property name="hibernate.connection.url" value="jdbc:firebirdsql:localhost/3050:/sistemas/satbd/SATIflecha.GDB?lc_ctype=ISO8859_1&columnLabelForName=true"/>
<property name="hibernate.connection.username" value="SYSDBA" />
<property name="hibernate.connection.password" value="masterkey" />
</properties>
</persistence-unit>

@firebird-automations
Copy link
Author

Commented by: @mrotteveel

Good to hear!

@firebird-automations
Copy link
Author

Modified by: @mrotteveel

Link: This issue is duplicated by JDBC303 [ JDBC303 ]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants