Can't access EntityManager with JPA 2.1 and Hibernate5 - java

I have an application with Hibernate 5, and added JPA 2.1 to perform bulk Updates with CriteriaBuilder.createCriteriaUpdate().
But I need to assign CriteriaBuilder from EntityManager.getCriteriaBuilder(), and I can't get the EntityManager.
I don't have a persistence.xml file, and I thought Hibernate would provide an EntityManager for me.
I tried the following annotations in the DAO class:
#Autowired
EntityManager entityManager
and
#PersistenceContext
EntityManager entityManager;
Both fail to inject the dependency.
I also tried to instace an EntityManagerFactory, but it failed as I don't have a persistence.xml file. All the entities are annotated like this:
#Entity
#Table(name = "My_Entity")
public class MyEntity extends BaseEntity {
private static final long serialVersionUID = -8442071276091708080L;
#Column(name = "VALUE", nullable = false)
private BigDecimal value;
...
}
Here is part of my pom.xml:
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>5.1.3.Final</version>
<type>jar</type>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.1.3.Final</version>
<type>jar</type>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.1-api</artifactId>
<version>1.0.0.Final</version>
</dependency>
applicationContext.xml
<bean class="org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor"/>
<bean id="transactionManager"
class="org.springframework.orm.hibernate5.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory"/>
<property name="nestedTransactionAllowed" value="true"/>
</bean>
Hibernate instances the SessionFactory, is there a way to get the EM from it?

If you use spring it would be much easier to use the spring boot starters modules. For JPA it would be "spring-boot-starter-data-jpa" you can find the definition of the maven dependency here.
Additionally, could you add more information about your configuration? You say you don't use a persistence.xml so what do you use to set your datasources?

Related

While using OneToMany tags .. No Persistence provider for EntityManager - Hibernate JPA

Well i've benn looking for this problem wasting so much time, so i'm here.
import javax.persistence.*;
#Entity
#Table(name = "secretario")
public class Secretario {
#Id
#GeneratedValue
private long codigoS;
#Column
private String nombre;
#ManyToOne
#JoinColumn(name = "codigoE")
private Empleado e;
import javax.persistence.*;
import java.io.Serializable;
import java.util.ArrayList;
#Entity
#Table
public class Empleado implements Serializable {
private static final long serialVersionUID = 1l;
#Id
#Column
#GeneratedValue
private long codigoE;
#Column
private String apellido;
#Column
private String nombre;
#OneToMany(mappedBy = "e")
private ArrayList<Secretario> secretario;
When i use te OneToMany and ManyToOne tags i got this exception and i dont why... or how ...
INFO: HHH000400: Using dialect: org.hibernate.dialect.MySQL8Dialect
Exception in thread "main" javax.persistence.PersistenceException: No Persistence provider for EntityManager named Persistencia
at javax.persistence.Persistence.createEntityManagerFactory(Persistence.java:85)
at javax.persistence.Persistence.createEntityManagerFactory(Persistence.java:54)
at tests.TestEmpleados.main(TestEmpleados.java:22)
here is my persistence config
<?xml version="1.0" encoding="UTF-8" ?>
<persistence xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence
http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
version="2.0" xmlns="http://java.sun.com/xml/ns/persistence">
<persistence-unit name="Persistencia">
<!-- <description>
Persistence unit for the JPA tutorial of the Hibernate Getting Started Guide
</description>-->
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<!-- Representar clases -->
<class>model.Empleado</class>
<class>model.Secretario</class>
<properties>
<property name="javax.persistence.jdbc.driver" value="com.mysql.jdbc.Driver"/>
<property name="javax.persistence.jdbc.url" value="jdbc:mysql://localhost:3306/hibernate"/>
<property name="javax.persistence.jdbc.user" value="root"/>
<property name="javax.persistence.jdbc.password" value=""/>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL8Dialect"/>
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
</properties>
</persistence-unit>
</persistence>
And my maven config
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.example</groupId>
<artifactId>Hibernate</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<!-- https://mvnrepository.com/artifact/org.hibernate/hibernate-core -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.3.1.Final</version>
</dependency>
<!--<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>5.3.1.Final</version>
</dependency>-->
<!-- https://mvnrepository.com/artifact/javax.persistence/javax.persistence-api -->
<dependency>
<groupId>javax.persistence</groupId>
<artifactId>javax.persistence-api</artifactId>
<version>2.2</version>
</dependency>
<!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.21</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>
</build>
</project>
Some way i fixed using the #Transient tag and my entities were correctly persisted, but when i tried to query them i got a null in the OneToMany relation bcz it tells hibernate not to do something with that attribute...
emf = Persistence.createEntityManagerFactory("Persistencia");
manager = emf.createEntityManager();
This is where the exception shows
#UPDATE
Somehow i figured out that #OneToMany only accepts Collection Type as List,set, Map, etc but not "ArrayList" and i just changed the data type and it work fine..
#Transient - tells hibernate not persist such fields, that's why you have null at this fields. Also that's why you don't get problem again.
#ManyToOne are Lazy by default, so you should get them inside transaction.
You can achive this to annotate method where you use this property with #Transactional if you use JPA. Or you can use methods beginTransaction(), endTransaction() from EntityManager.
As long as your entity will go from transactional scope error will occure again. So convert your entity to dto before gone from transactional scope.
Another solution you can annotate your fields as Eager, so they will be downloaded from database with parent entity.
But Eager - bad solution, don't use it if don't know what is it.
I will try to answer the question but certain things depends on your setup i.e using as Java SE or J2EE application.
For Java SE, make sure you have your persistence file inside META-INF/persistence.xml under resources folder, Please check this article or in docs
For J2EE application, you generally configure the JNDI name in your server's configuration and then use that JNDI name inside your persistence.xml.
Also, please check all your database credentials and check access to it manually and follow the stack trace, it will tell you complete story what is going wrong.

Inject EntityManagerFactory using #PersistenceUnit on Jersey with Wildfly

I'm trying to inject EntityManagerFactory using #PersistenceUnit, but it's always null.
I think my persistence.xml is OK, since I can get the EntityManager with this code:
EntityManager em = Persistence.createEntityManagerFactory("myPersistenceUnit").createEntityManager();
So, I would like to know if I'm doing something wrong, or if this is not possible when using Jersey (2.23) and Wildfly 10 (JBoss EAP 7).
Here is what I've done so far:
Created a jersey-quickstart-webapp maven project on eclipse;
Added the following dependencies to my pom.xml:
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-api</artifactId>
<version>7.0</version>
</dependency>
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.1-api</artifactId>
<version>1.0.0.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>5.2.2.Final</version>
</dependency>
<dependency>
<groupId>com.hynnet</groupId>
<artifactId>oracle-driver-ojdbc6</artifactId>
<version>12.1.0.1</version>
</dependency>
Created the persistence.xml:
<persistence-unit name="myPersistenceUnit"
transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<!-- All persistence classes must be listed -->
<class>com.mps.classes.TermosPesquisados</class>
<properties>
<!-- Provider-specific connection properties -->
<property name="javax.persistence.jdbc.driver" value="oracle.jdbc.OracleDriver" />
<property name="javax.persistence.jdbc.url" value="JDBC_URL" />
<property name="javax.persistence.jdbc.user" value="USER" />
<property name="javax.persistence.jdbc.password" value="PASSWORD" />
<property name="hibernate.dialect" value="org.hibernate.dialect.Oracle10gDialect" />
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.connection.release_mode" value="after_transaction" />
<property name="hibernate.connection.isolation" value="2" />
</properties>
</persistence-unit>
Modified the MyResource.java:
#ManagedBean
#Path("myresource")
public class MyResource {
#PersistenceUnit(unitName= "myPersistenceUnit")
private EntityManagerFactory emf;
#GET
#Produces(MediaType.TEXT_PLAIN)
public String getIt() {
if(emf == null)
return "emf is null";
return "emf is not null";
}
}
Added an empty beans.xml (not sure if it's necessary);
It seems that Jersey conflicts with Resteasy. This way, I had 2 options:
Turn-off Resteasy on JBoss/Wildfly (I know that's possible, but I don't know how);
Remove Jersey and use Resteasy instead;
I ended up choosing the 2nd option because it was easier and I have no reasons to use specifically Jersey.
This way, I had to change my web.xml, replacing this:
<servlet-name>Jersey Web Application</servlet-name>
<servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
...
<servlet-mapping>
<servlet-name>Jersey Web Application</servlet-name>
<url-pattern>/webapi/*</url-pattern>
</servlet-mapping>
For this:
<servlet-name>javax.ws.rs.core.Application</servlet-name>
...
<servlet-mapping>
<servlet-name>javax.ws.rs.core.Application</servlet-name>
<url-pattern>/webapi/*</url-pattern>
</servlet-mapping>
*Another option was to create a class extending Application class.
*beans.xml was not necessary.
Then, I annotated my resource class with #Stateless and I was able to inject EntityManager properly:
#Path("myresource")
#Stateless
public class MyResource {
#PersistenceContext(unitName="myPersistenceUnit")
private EntityManager em;
...
At this point, EntityManager was OK, but somehow it was using JBoss h2 in-memmory database (ExampleDS).
So, I configured an oracle datasource on JBoss (OracleDS) and updated my persistence.xml to use OracleDS and JTA instead of "RESOURCE_LOCAL":
<persistence-unit name="myPersistenceUnit" transaction-type="JTA">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<jta-data-source>java:jboss/datasources/OracleDS</jta-data-source>
...
With those steps I was able to inject EntityManager and make my CRUD operations successfully.
There is no point for a #ManagedBean annotation here, this is a JSF annotation and I according to your code you're trying to expose a REST layer.
Just remove it and all will be fine (also ensure that you have a beans.xml in your classpath to enable CDI, otherwise annotate your class with #Stateless)
I think Entity manager should be enough :
#PersistenceUnit(unitName= "myPersistenceUnit")
private EntityManager em;

No persistence provider for EntityManager for Hibernate in Maven

I am getting this error:
Exception in thread "main" javax.persistence.PersistenceException: No Persistence provider for EntityManager named tarefas at
javax.persistence.Persistence.createEntityManagerFactory(Persistence.java:61)
My jars is okay, as you seem in the pom.xml
My main class:
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
public class GeraTabelas {
public static void main(String[] args)
{
EntityManagerFactory factory = Persistence.createEntityManagerFactory("tarefas");
factory.close();
}
}
pom.xml
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.2.2.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>4.3.9.Final</version>
</dependency>
persistence.xml
<persistence-unit name="tarefas">
<!-- provedor/implementacao do JPA -->
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<!-- entidade mapeada -->
<class>br.com.abc.models.Usuario</class>
<properties>
<property name="hibernate.connection.url" value= .... //The rest of properties...
</properties>
</persistence-unit>
It may be the position of the pom.xml file in the wrong location? I did this way because of others posts that said it was this way but this interrogation point appears in the folders and I am beginner in Maven to know what it is.
Thanks.

How to use TomEE with Hibernate

I have created very simple app with persistence context (hibernate as provider) to read some value from database. I use Eclipse with Maven.
First, I get
Caused by: org.apache.openejb.OpenEJBException: java.lang.ClassCastException: org.hibernate.ejb.HibernatePersistence cannot be cast to javax.persistence.spi.PersistenceProvider:
and according to this topic
http://openejb.979440.n4.nabble.com/problem-with-hibernate-persistence-provider-td980429.html
I excluded hibernate-jpa-2.0-api. Now, my dependencies look
<dependency>
<groupId>postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>9.1-901.jdbc4</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>4.1.3.Final</version>
<exclusions>
<exclusion>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.0-api</artifactId>
</exclusion>
</exclusions>
</dependency>
Now, I don't know why...
Caused by: java.lang.ClassNotFoundException: org.hibernate.transaction.TransactionManagerLookup
But TransactionManagerLookup is in hibernate-core.
Please, can anybody tell me, how should look pom.xml to use hibernate in TomEE?
1. Copy the required Hibernate .jars to <tomee-home>/lib
According to the documentation ( http://tomee.apache.org/tomee-and-hibernate.html ), the following ones are sufficient and in fact they worked for me:
<tomee-home>/lib/antlr-2.7.7.jar
<tomee-home>/lib/dom4j-1.6.1.jar
<tomee-home>/lib/hibernate-commons-annotations-4.0.2.Final.jar
<tomee-home>/lib/hibernate-core-4.2.21.Final.jar
<tomee-home>/lib/hibernate-entitymanager-4.2.21.Final.jar
<tomee-home>/lib/hibernate-validator-4.3.2.Final.jar
<tomee-home>/lib/javassist-3.18.1-GA.jar
<tomee-home>/lib/jboss-logging-3.1.0.GA.jar
All these .jars are contained in the Hibernate ORM 4.2.x download ( http://hibernate.org/orm/ ), except for the Hibernate Validator, which is a separate download ( http://hibernate.org/validator/ ).
2. Edit your pom.xml
Using the javaee-api maven artifact with a scope of provided you can now use the JPA specification in your project. However, if you have been using some Hibernate specific features, classes or annotations before, you can still refer to Hibernate in your pom.xml to match those dependencies:
<!-- JPA spec (required) -->
<dependencies>
<dependency>
<groupId>org.apache.openejb</groupId>
<artifactId>javaee-api</artifactId>
<version>6.0-4</version>
<scope>provided</scope>
</dependency>
<!-- Hibernate specific features (only if needed) -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>4.2.21.Final</version>
<scope>provided</scope>
</dependency>
3. Define your database connection
Edit <tomee-home>/conf/tomee.xml:
<Resource id="myJtaDatabase" type="DataSource">
JdbcDriver com.mysql.jdbc.Driver
JdbcUrl jdbc:mysql://localhost:3306/my_dbname?autoReconnect=true
UserName foo
Password bar
validationQuery = SELECT 1
JtaManaged true
</Resource>
You can also put the above <Resource>...</Resource> definition into WEB-INF/resources.xml and ship it with your application instead:
<?xml version="1.0" encoding="UTF-8"?>
<resources>
<!-- Put <Resource> elements here -->
<resources>
4. JTA Datasource
Now that you told TomEE how to establish a connection, define a JTA datasource in /src/main/java/META-INF/persistence.xml:
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0"
xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence
http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd">
<persistence-unit name="my_persistence_unit">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<jta-data-source>java:openejb/Resource/myJtaDatabase</jta-data-source>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect" />
<!-- As many hibernate properties as you need, some examples: -->
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.format_sql" value="true" />
<!-- Drop and then re-create the database schema (don't do this in production) -->
<property name="hibernate.hbm2ddl.auto" value="update" />
</properties>
</persistence-unit>
</persistence>
5. Start using JPA
Obtain an EntityManager in a CDI bean or EJB like this:
#PersistenceContext(unitName = "my_persistence_unit")
private EntityManager em;
Final Notes
Hibernate versions 4.3+
I am using Hibernate 4.2.21 (JPA 2.0, Java EE 6) along with TomEE 1.7.2. Any TomEE 1.7.x, 1.6.x and 1.5.x will work. However, you cannot use Hibernate 4.3+ (JPA 2.1 / Java EE 7), as TomEE 1.7.x and below only support Java EE 6. If you really want to use Java EE 7 features along with TomEE, this blog post might be helpful: http://rmannibucau.wordpress.com/2013/07/19/little-tip-to-help-you-to-test-javaee-7-in-tomee-with-tomee-maven-plugin/
TomEE 1.5.x
TomEE 1.5.x already includes a javassist-<version>.jar, so you don't have to copy one.
Try this:
Add:
<tomee-home>/lib/antlr-2.7.7.jar
<tomee-home>/lib/dom4j-1.6.1.jar
<tomee-home>/lib/ehcache-core-2.5.1.jar
<tomee-home>/lib/ehcache-terracotta-2.5.1.jar
<tomee-home>/lib/hibernate-commons-annotations-4.0.1.Final.jar
<tomee-home>/lib/hibernate-core-4.1.4.Final.jar
<tomee-home>/lib/hibernate-ehcache-4.1.4.Final.jar
<tomee-home>/lib/hibernate-entitymanager-4.1.4.Final.jar
<tomee-home>/lib/hibernate-validator-4.3.0.Final.jar
<tomee-home>/lib/jboss-logging-3.1.0.GA.jar
<tomee-home>/lib/terracotta-toolkit-1.4-runtime-4.1.0.jar
The ehcache jars might be optional, but haven't tried without them.
Remove (optional):
<tomee-home>/lib/asm-3.2.jar
<tomee-home>/lib/bval-core-0.4.jar
<tomee-home>/lib/bval-jsr303-0.4.jar
<tomee-home>/lib/commons-lang-2.6.jar
<tomee-home>/lib/openjpa-2.2.0.jar
<tomee-home>/lib/serp-1.13.1.jar
yes just dropping the hibernate-jpa-2.1-api-1.0.0.Final.jar into the TomEE lib folder worked for me.

problem using Hibernate annotation with JodaTime

i am coming back because i still have problem using JodaTime. After the previous comments, i modified my pom and the #Type annotation is fixed. Here is my new pom :
<properties>
<org.springframework.version>3.0.3.RELEASE</org.springframework.version>
<hibernate.version>3.6.0.Beta1</hibernate.version>
</properties>
<dependencies>
...
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>${hibernate.version}</version>
<type>jar</type>
<scope>compile</scope>
</dependency>
<!-- Spring Dependencies -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>3.0.2.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${org.springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${org.springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${org.springframework.version}</version>
</dependency>
<dependency>
<groupId>commons-dbcp</groupId>
<artifactId>commons-dbcp</artifactId>
<version>20030825.184428</version>
</dependency>
<dependency>
<groupId>commons-pool</groupId>
<artifactId>commons-pool</artifactId>
<version>20030825.183949</version>
</dependency>
<dependency>
<groupId>commons-validator</groupId>
<artifactId>commons-validator</artifactId>
<version>1.3.1</version>
<classifier>sources</classifier>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.5</version>
</dependency>
<!-- Joda Time dependencies -->
<dependency>
<artifactId>joda-time</artifactId>
<groupId>joda-time</groupId>
<version>1.6</version>
</dependency>
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time-jsptags</artifactId>
<version>1.0.2</version>
</dependency>
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time-hibernate</artifactId>
<version>1.2</version>
<type>jar</type>
<scope>compile</scope>
</dependency>
</dependencies>
I am actually developping a personnal project where i use Spring and Hibernate. I also use JodaTime to persist the date fields. When i am doing unit testing with Junit4, i caught this exception :
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'sessionFactory' defined in class path resource [spring/spring-dao.xml]: Invocation of init method failed; nested exception is java.lang.IncompatibleClassChangeError: Implementing class
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1412)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:519)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456)
....
fr.cc2i.intervention.dao.test.WebInterventionTest.oneTimedSetUp(WebInterventionTest.java:33)
.....
Caused by: java.lang.IncompatibleClassChangeError: Implementing class
at java.lang.ClassLoader.defineClass1(Native Method)
at java.lang.ClassLoader.defineClassCond(ClassLoader.java:632)
at java.lang.ClassLoader.defineClass(ClassLoader.java:616)
at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:141)
at java.net.URLClassLoader.defineClass(URLClassLoader.java:283)
at java.net.URLClassLoader.access$000(URLClassLoader.java:58)
at java.net.URLClassLoader$1.run(URLClassLoader.java:197)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
at java.lang.ClassLoader.loadClass(ClassLoader.java:307)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301)
at java.lang.ClassLoader.loadClass(ClassLoader.java:248)
at java.lang.Class.getDeclaredConstructors0(Native Method)
at java.lang.Class.privateGetDeclaredConstructors(Class.java:2389)
at java.lang.Class.getConstructor0(Class.java:2699)
at java.lang.Class.getDeclaredConstructor(Class.java:1985)
at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:104)
at
.....
According to that website : http://www.mail-archive.com/joda-interest#lists.sourceforge.net/msg00609.html, jodatime might cause the error.
Can someone explain me what is : java.lang.incompatibleChangeError : Implementing Class ?
and how to solve that problem?
My spring configuration :
<bean id="sessionFactory"
class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource"> <ref local="dataSource" /></property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
<prop key="hibernate.show_sql">false</prop>
<prop key="hibernate.current_session_context_class">thread</prop>
<prop key="hibernate.transaction.factory_class">org.hibernate.transaction.JDBCTransactionFactory</prop>
<!-- Pour les requetes SQL -->
<prop key="hibernate.query.substitutions">true 1, false 0, yes 'Y', no 'N'</prop>
<!-- manipuler avec attention -->
<prop key="hibernate.hbm2ddl.auto">create</prop>
<prop key="hibernate.hbm2ddl.auto">update</prop>
</props>
</property>
<property name="annotatedClasses">
<list>
<value>fr.cc2i.intervention.dao.beans.Client</value>
<value>fr.cc2i.intervention.dao.beans.Intervention</value>
<value>fr.cc2i.intervention.dao.beans.Technicien</value>
<value>fr.cc2i.intervention.dao.beans.Contrat</value>
</list>
</property>
</bean>
My entity class :
package fr.cc2i.intervention.dao.beans;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import org.hibernate.annotations.Type;
import org.joda.time.Period;
/**
* Classe définissant un contrat
* My code is written in French ;)
* #author lindows
*
*/
#Entity
#Table(name="T_Contrat")
public class Contrat {
private long id;
private String reference;
private Period heures_totales;
private Period heures_restantes;
public Contrat(){}
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
public long getId() {
return id;
}
private void setId(long id) {
this.id = id;
}
public String getReference() {
return reference;
}
public void setReference(String reference) {
this.reference = reference;
}
#Column
#Type(type="org.joda.time.contrib.hibernate.PersistantPeriod")
public Period getHeures_totales() {
return heures_totales;
}
public void setHeures_totales(Period heuresTotales) {
heures_totales = heuresTotales;
}
#Column
#Type(type="org.joda.time.contrib.hibernate.PersistantPeriod")
public Period getHeures_restantes() {
return heures_restantes;
}
public void setHeures_restantes(Period heuresRestantes) {
heures_restantes = heuresRestantes;
}
public String toString(){
return this.reference + " - \n Heures totales :" + this.heures_totales.toString() +
" Heures Restantes : " + this.heures_restantes.toString();
}
}
Thanks for your help
As I wrote in a comment, your pom.xml is messy and this is somehow the root cause of the issue. Here comes the full explanation.
According to the announcement of the Simultaneous Hibernate 3.5.4 and 3.6.0.Beta1 Releases quoted below, the hibernate-annotations module has been merged into core in Hibernate 3.6.x (made possible since Hibernate 3.6.x is dropping JDK 1.4 support):
3.6.0.Beta1
3.6 introduces some new features as well as incorporating most of the
fixes from 3.5. Changes of particular
interest include
Dropping support for JDK 1.4
merging some modules into core; specifically hibernate-jmx and
hibernate-annotations
repackaging of classes in hibernate-testing
HHH-2277 : fixes a long known limitation in key-many-to-one support.
HHH-5138, HHH-5182, HHH-5262 : collectively address a
number of improvements to the
"Hibernate type system". See the newly
separated and expanded chapter on
Types in the reference manual for
details.
HHH-5268 : java.util.UUID support
For more details about 3.6.0.Beta1,
including the full list of changes,
see the release page.
And indeed, the latest versions of hibernate-annotations-3.6-SNAPSHOT.jar are actually empty jars (because of the merge) that were temporarily built until the total removal of the maven module itself. But because you're not using hibernate-core-3.6-SNAPSHOT.jar, you just don't have the #Type annotation at all.
Now, here is a summary of my recommendations/remarks:
Use Maven transitive dependency resolution mechanism, do not declare all dependencies but only the "top level" one i.e. hibernate-entitymanager if you want to use JPA.
Starting with version 3.5, Hibernate Core, Annotations, EntityManager are released together, their versions are in sync.
If you want to use Hibernate 3.6.x (Beta2 is there now), the #Type is in hibernate-core (that's not really important if you use transitive dependencies).
I don't recommend to rely on SNAPSHOT unless you know exactly what you're doing.
So your pom.xml should declare something like this for Hibernate:
<project>
...
<properties>
<!--hibernate.version>3.4.O.GA</hibernate.version--> <!-- for JPA 1.0 -->
<hibernate.version>3.5.4-Final</hibernate.version> <!-- for JPA 2.0 -->
<!--hibernate.version>3.6.0.Beta2</hibernate.version--> <!-- experimental -->
<properties>
...
<dependencies>
<!-- Hibernate dependencies -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>${hibernate.version}</version>
</dependency>
...
</dependencies>
...
</project>
And that's all you need.
The #Type annotation is present in hibernate-annotations, version 3.5.1-Final. I don't find the snapshot you are using 3.6.0-SNAPSHOT in the jboss repository, so I couldn't test that specifically, but my guess is that the annotation is missing/has been removed from the snapshot version for some reason.
Unless there is a specific reason you need a snapshot, I would stick to released versions. If you revert to 3.5.1-Final, that will fix the problem.
The Type API is changing in Hibernate 3.6.0. I would be surprised if the Joda Time Contrib classes work at all with Hibernate 3.6 although they should work with Hibernate 3.5. Can I suggest you take a look at my project which has implementations of Usertypes for Joda Time and JSR310: http://usertype.sourceforge.net/
Thanks and regards,
Chris

Categories

Resources