NOTE : this is stupid way of writing a blog :)
I have entities as following , The Aml object has many aliases and documents.
[1] AbstractEntity.java
import java.io.Serializable;
import java.util.Date;
import javax.persistence.Basic;
import javax.persistence.Column;
import javax.persistence.MappedSuperclass;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.Version;
import org.springframework.data.jpa.domain.AbstractPersistable;
@MappedSuperclass
public abstract class AbstractEntity<PK extends Serializable> extends AbstractPersistable<PK> {
private static final long serialVersionUID = 8453654076725018243L;
@Basic
@Temporal(TemporalType.TIMESTAMP)
private Date created = new Date();
@Basic
@Temporal(TemporalType.TIMESTAMP)
private Date lastModified;
@Version
@Column
private int version;
// getters and setters
}
[2] The parent entity => Aml.java
import java.util.Date;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.OneToMany;
import com.f.c.shared.models.AmlGroupType;
import com.f.c.shared.models.AmlType;
import com.f.c.shared.models.DOBType;
/**
* main object that holds the main information for EU Consolidated Aml info
*
* @author Prayag Upd
* @date Sep 21, 2012
*/
@Entity
public class Aml extends AbstractEntity<Long> {
/* a specific INDIVIDUAL or ENTITY */
private String groupId;
private AmlType amlType;
private AmlGroupType groupType;
private String referenceNumber;
private Address address;
private Date listedOn;
private String nameOriginalScript;
private String designation;
private String title;
private String nationality;
private DOBType dobType;
/* in dd/mm/yyyy format */
private Date dob;
private String country;
private String sortKey;
private String remarks;
private String firstName;
private String middleName;
private String lastName;
private String dobPlace;
private String program;
@OneToMany(fetch = FetchType.EAGER)
private AmlAlias amlAlias;
@OneToMany(fetch = FetchType.EAGER)
private AmlDocument amlDocument;
/*getters and setters*/
}
[3] Child entity => AmlAlias.java
import javax.persistence.Entity;
import com.f.c.shared.models.AmlAliasType;
@Entity
public class AmlAlias extends AbstractEntity<Long> {
private AmlAliasType aliasType;
private String aliasName;
private String remarks;
/*getters and setters*/
}
configuration /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="c">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<!-- Aml module -->
<class>com.f.c.server.entities.Aml</class>
<class>com.f.c.server.entities.AmlAlias</class>
<class>com.f.c.server.entities.AmlDocument</class>
<class>com.f.c.server.entities.Address</class>
<properties>
<property name="hibernate.hbm2ddl.auto" value="update" />
<property name="hibernate.transaction.flush_before_completion"
value="true" />
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.cache.provider_class" value="org.hibernate.cache.HashtableCacheProvider" />
</properties>
<exclude-unlisted-classes>true</exclude-unlisted-classes>
</persistence-unit>
<persistence-unit name="test">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>com.f.c.server.entities.Aml</class>
<class>com.f.c.server.entities.AmlAlias</class>
<class>com.f.c.server.entities.AmlDocument</class>
<class>com.f.c.server.entities.Address</class>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
<property name="driverClassName" value="org.hsqldb.jdbcDriver" />
<property name="username" value="sa" />
<property name="password" value="" />
</properties>
<exclude-unlisted-classes>true</exclude-unlisted-classes>
</persistence-unit>
</persistence>
/WEB-INF/jpa-context.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"
default-autowire="byName">
<!-- Scans within the base package of the application for @Components to
configure as beans -->
<bean id="placeholderConfig"
class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="location" value="classpath:WEB-INF/db.properties" />
<property name="ignoreResourceNotFound" value="true"></property>
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="showSql" value="true" />
<property name="generateDdl" value="true" />
<property name="databasePlatform" value="${db.dialect}" />
</bean>
</property>
<property name="persistenceXmlLocation" value="${db.persistenceXml}"/>
<property name="persistenceUnitName" value="${db.persistenceUnit}"/>
</bean>
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
destroy-method="close">
<property name="driverClassName" value="${db.driver}" />
<property name="url" value="${db.url}" />
<property name="username" value="${db.username}" />
<property name="password" value="${db.password}" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"></property>
</bean>
<tx:annotation-driven />
<bean
class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" />
</beans>
Problem
The error I get is :
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor#0': Initialization of bean failed; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'entityManagerFactory' defined in class path resource [WEB-INF/jpa-context.xml]: Invocation of init method failed; nested exception is org.hibernate.AnnotationException: Illegal attempt to map a non collection as a @OneToMany, @ManyToMany or @CollectionOfElements: com.f.c.server.entities.Aml.amlAlias
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:527) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:291) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:288) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.registerBeanPostProcessors(AbstractApplicationContext.java:710) ~[spring-context-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:410) ~[spring-context-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.web.context.ContextLoader.createWebApplicationContext(ContextLoader.java:276) ~[spring-web-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:197) ~[spring-web-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:47) [spring-web-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4701) [catalina.jar:7.0.12]
at org.apache.catalina.core.StandardContext$1.call(StandardContext.java:5204) [catalina.jar:7.0.12]
at org.apache.catalina.core.StandardContext$1.call(StandardContext.java:5199) [catalina.jar:7.0.12]
at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303) [na:1.6.0_23]
at java.util.concurrent.FutureTask.run(FutureTask.java:138) [na:1.6.0_23]
at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) [na:1.6.0_23]
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) [na:1.6.0_23]
at java.lang.Thread.run(Thread.java:662) [na:1.6.0_23]
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'entityManagerFactory' defined in class path resource [WEB-INF/jpa-context.xml]: Invocation of init method failed; nested exception is org.hibernate.AnnotationException: Illegal attempt to map a non collection as a @OneToMany, @ManyToMany or @CollectionOfElements: com.f1soft.ctbs.server.entities.Aml.amlAlias
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1420) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:519) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:291) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:288) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeansOfType(DefaultListableBeanFactory.java:398) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.BeanFactoryUtils.beansOfTypeIncludingAncestors(BeanFactoryUtils.java:275) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.detectPersistenceExceptionTranslators(PersistenceExceptionTranslationInterceptor.java:139) ~[spring-tx-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.<init>(PersistenceExceptionTranslationInterceptor.java:79) ~[spring-tx-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.dao.annotation.PersistenceExceptionTranslationAdvisor.<init>(PersistenceExceptionTranslationAdvisor.java:70) ~[spring-tx-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor.setBeanFactory(PersistenceExceptionTranslationPostProcessor.java:99) ~[spring-tx-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeAwareMethods(AbstractAutowireCapableBeanFactory.java:1439) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1408) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:519) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
... 18 common frames omitted
Caused by: org.hibernate.AnnotationException: Illegal attempt to map a non collection as a @OneToMany, @ManyToMany or @CollectionOfElements: com.f1soft.ctbs.server.entities.Aml.amlAlias
at org.hibernate.cfg.annotations.CollectionBinder.getCollectionBinder(CollectionBinder.java:324) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.AnnotationBinder.processElementAnnotations(AnnotationBinder.java:1723) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.AnnotationBinder.processIdPropertiesIfNotAlready(AnnotationBinder.java:796) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.AnnotationBinder.bindClass(AnnotationBinder.java:707) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.Configuration$MetadataSourceQueue.processAnnotatedClassesQueue(Configuration.java:4035) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.Configuration$MetadataSourceQueue.processMetadata(Configuration.java:3989) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.Configuration.secondPassCompile(Configuration.java:1398) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.cfg.Configuration.buildMappings(Configuration.java:1375) ~[hibernate-core-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.ejb.Ejb3Configuration.buildMappings(Ejb3Configuration.java:1519) ~[hibernate-entitymanager-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.ejb.EventListenerConfigurator.configure(EventListenerConfigurator.java:193) ~[hibernate-entitymanager-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.ejb.Ejb3Configuration.configure(Ejb3Configuration.java:1100) ~[hibernate-entitymanager-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.ejb.Ejb3Configuration.configure(Ejb3Configuration.java:689) ~[hibernate-entitymanager-3.6.6.Final.jar:3.6.6.Final]
at org.hibernate.ejb.HibernatePersistence.createContainerEntityManagerFactory(HibernatePersistence.java:73) ~[hibernate-entitymanager-3.6.6.Final.jar:3.6.6.Final]
at org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean.createNativeEntityManagerFactory(LocalContainerEntityManagerFactoryBean.java:225) ~[spring-orm-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.afterPropertiesSet(AbstractEntityManagerFactoryBean.java:308) ~[spring-orm-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1477) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1417) ~[spring-beans-3.0.5.RELEASE.jar:3.0.5.RELEASE]
... 33 common frames omitted
In a short it's Illegal attempt to map a non collection as a @OneToMany, @ManyToMany or @CollectionOfElements: com.f.c.server.entities.Aml.amlAlias
Solution
[1] - First change parent entity to have a list of child entities
@OneToMany(mappedBy = "aml")
private List<AmlAlias> amlAlias;
@OneToMany(mappedBy = "aml")
private List<AmlDocument> amlDocument;
[2] - Change child entity adding the following line
@ManyToOne
private Aml aml;
References
1 - Illegal attempt to map a non collection, available at
https://groups.google.com/forum/?fromgroups=#!topic/play-framework/NmMvTGg50a4
2 - Hibernate cannot simultaneously fetch multiple bags, available at
http://stackoverflow.com/questions/4334970/hibernate-cannot-simultaneously-fetch-multiple-bags