I have an enumeration with a list of states (for example)
enum State { UP, DOWN, RETRY };
The column in my database is of type enum. When I try to execute a Hibernate request by setting a parameter in the request using setParameter("keyword", State.RETRY); , I get an error
The value of the [RETRY] โโparameter does not match the expected type [package.name.State (n / a)]
In my Glassfish 4.1 server.log for my domain. I am using Hibernate 4.3.6.
When viewing the source code for Hibernate, I see that the error is due to lines 958-960 in org.hibernate.jpa.spi.BaseQueryImpl :
private static boolean isValidBindValue(Class expectedType, Object value, TemporalType temporalType) { if ( expectedType.isInstance( value ) ) { return true; } ... return false; }
isValidBindValue returns false, and so I get the message.
It returns the String equivalent of enum because of this string:
String.format("Parameter value [%s] did not match expected type [%s (%s)]", bind, parameterType.getName(), extractName( temporalType ) )
The bind object is implicitly converted to a String value by calling the toString method on the Object , which represents enum State.RETRY .
So, how can I convince Hibernate that State.RETRY is an instance of State ?
Hibernate seems to have been updated to the JPA 2.1 specification, which has been stricter in this commit since April 2013:
https://github.com/hibernate/hibernate-orm/commit/84520cd6e36e9207c41528cf9311cae905a86425
An object is annotated as follows:
@Basic(optional = false) @Column(name = "state") @Enumerated(EnumType.String) private State state;
Edit:
My RetryState enum is loaded by EarLibClassLoader . While Query loads URLClassLoader, and EntityManager loads with another class loader.