6

I'm working on switching my JPA persistence provider from EclipseLink 2.3 to Hibernate 3.6.5.Final. The problem is with a native query. Note: this wasn't a problem with EclipseLink. I'm trying to obtain a scalar value, a String from a table that I don't have an Entity declared for. Here is the code:

Query q = em.createNativeQuery("select description from foo where foo_id = ?");
q.setParameter(1, fooId);
String description = (String)q.getSingleResult();

With Hibernate I get a ClassCastException because the object returned is actually a proxy object. I don't know what type it is, but I know it isn't an array (object.getClass().isArray() is false) and I know it isn't a List (object instanceof List is false).

What am I missing?

Tomasz Nurkiewicz
  • 334,321
  • 69
  • 703
  • 674
Ryan
  • 7,499
  • 9
  • 52
  • 61
  • What interfaces does `q.getSingleResult().getClass().getInterfaces()` return? – Tomasz Nurkiewicz Jan 12 '12 at 21:05
  • Ahhh... that was what I needed. It is of type java.sql.Clob, org.hibernate.engine.jdbc.WrappedClob, and java.io.Serializable. If you make that an answer I'll accept it. I didn't even realize the column was a clob and I'm surprised EclipseLink was doing the conversion to String for me. – Ryan Jan 12 '12 at 21:15
  • 1
    Just FYI two other issues came up with the conversion to Hibernate. (1) calling a getEntityXList() method on an EntityY to force the EntityManager to query the database and load the lazy loaded list worked in EclipseLink, but I had to make it getEntityXList().size() for it to work in Hibernate. (2) an untyped criteria query worked in EclipseLink, but in Hibernate I get an exception about no selection. I just added the type: CriteriaQuery cq = builder.createQuery(EntityX.class); – Ryan Jan 13 '12 at 17:24
  • Worked for me! https://stackoverflow.com/questions/28993398/hibernate-createnativequery-returning-proxy-object-for-clob – elciospy May 09 '19 at 17:05

2 Answers2

6

Summarizing comments below the question:

What interfaces does q.getSingleResult().getClass().getInterfaces() return?


It is of type java.sql.Clob, org.hibernate.engine.jdbc.WrappedClob, and java.io.Serializable. [...] I didn't even realize the column was a clob and I'm surprised EclipseLink was doing the conversion to String for me


Looks like EclipseLink is smart enough to convert CLOB (which is actually a very long sequence of characters, just like String) to String if required. With Hibernate this must be done explicitly. I guess this complies to the JPA specification.

Tomasz Nurkiewicz
  • 334,321
  • 69
  • 703
  • 674
0

Have you configured the right database dialect for hibernate? The dialect is used to map the type of scalar values.

Mirko
  • 11
  • 1
  • I'm using an Oracle database and I've got it configured in a DataSource in my application server. When Hibernate initializes it reports in the logs - Using dialect: org.hibernate.dialect.Oracle10gDialect so I guess it figured it out. – Ryan Jan 12 '12 at 21:23