Hibernate SVN: r18634 - jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen.
by hibernate-commits@lists.jboss.org
Author: hardy.ferentschik
Date: 2010-01-26 12:48:54 -0500 (Tue, 26 Jan 2010)
New Revision: 18634
Modified:
jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/Context.java
jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/JPAMetaModelEntityProcessor.java
Log:
METAGEN-21
Modified: jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/Context.java
===================================================================
--- jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/Context.java 2010-01-26 17:15:37 UTC (rev 18633)
+++ jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/Context.java 2010-01-26 17:48:54 UTC (rev 18634)
@@ -35,7 +35,7 @@
* @author Emmanuel Bernard
*/
public class Context {
- private static final String DEBUG_PARAMETER = "debug";
+
private final Map<String, MetaEntity> metaEntitiesToProcess = new HashMap<String, MetaEntity>();
private final Map<String, MetaEntity> metaSuperclassAndEmbeddableToProcess = new HashMap<String, MetaEntity>();
@@ -53,7 +53,7 @@
public Context(ProcessingEnvironment pe) {
this.pe = pe;
- String debugParam = pe.getOptions().get( DEBUG_PARAMETER );
+ String debugParam = pe.getOptions().get( JPAMetaModelEntityProcessor.DEBUG_OPTION );
if ( debugParam != null && "true".equals( debugParam ) ) {
logDebug = true;
}
Modified: jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/JPAMetaModelEntityProcessor.java
===================================================================
--- jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/JPAMetaModelEntityProcessor.java 2010-01-26 17:15:37 UTC (rev 18633)
+++ jpamodelgen/trunk/src/main/java/org/hibernate/jpamodelgen/JPAMetaModelEntityProcessor.java 2010-01-26 17:48:54 UTC (rev 18634)
@@ -23,6 +23,7 @@
import javax.annotation.processing.ProcessingEnvironment;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.SupportedAnnotationTypes;
+import javax.annotation.processing.SupportedOptions;
import javax.annotation.processing.SupportedSourceVersion;
import javax.lang.model.element.AnnotationMirror;
import javax.lang.model.element.Element;
@@ -48,8 +49,9 @@
*/
@SupportedAnnotationTypes("*")
@SupportedSourceVersion(RELEASE_6)
+@SupportedOptions({ JPAMetaModelEntityProcessor.DEBUG_OPTION })
public class JPAMetaModelEntityProcessor extends AbstractProcessor {
-
+ public static final String DEBUG_OPTION = "debug";
private static final Boolean ALLOW_OTHER_PROCESSORS_TO_CLAIM_ANNOTATIONS = Boolean.FALSE;
private boolean xmlProcessed = false;
15 years
Hibernate SVN: r18633 - in core/trunk/annotations/src: test/java/org/hibernate/test/annotations/derivedidentities/e1 and 7 other directories.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 12:15:37 -0500 (Tue, 26 Jan 2010)
New Revision: 18633
Added:
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Dependent.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DependentId.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DerivedIdentitySimpleParentIdClassDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Employee.java
Modified:
core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e4/b/DerivedIdentitySimpleParentSimpleDepMapsIdTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java
Log:
HHH-4529 Add support for id copy when @MapsId is used.
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -967,127 +967,6 @@
return true;
}
-// /*
-// * Get the annotated elements, guessing the access type from @Id or @EmbeddedId presence.
-// * Change EntityBinder by side effect
-// */
-// private static InheritanceState.ElementsToProcess getElementsToProcess(
-// PersistentClass persistentClass, XClass clazzToProcess,
-// Map<XClass, InheritanceState> inheritanceStatePerClass,
-// EntityBinder entityBinder, ExtendedMappings mappings
-// ) {
-// InheritanceState inheritanceState = inheritanceStatePerClass.get( clazzToProcess );
-// assert !inheritanceState.isEmbeddableSuperclass();
-//
-//
-// List<XClass> classesToProcess = getMappedSuperclassesTillNextEntityOrdered(
-// persistentClass, clazzToProcess, inheritanceStatePerClass, mappings
-// );
-//
-// AccessType accessType = determineDefaultAccessType( clazzToProcess, inheritanceStatePerClass );
-//
-// List<PropertyData> elements = new ArrayList<PropertyData>();
-// int deep = classesToProcess.size();
-// int idPropertyCount = 0;
-//
-// for ( int index = 0; index < deep; index++ ) {
-// PropertyContainer propertyContainer = new PropertyContainer( classesToProcess.get( index ), clazzToProcess );
-// int currentIdPropertyCount = addElementsOfClass( elements, accessType, propertyContainer, mappings );
-// idPropertyCount += currentIdPropertyCount;
-// }
-//
-// entityBinder.setPropertyAccessType( accessType );
-//
-// if ( idPropertyCount == 0 && !inheritanceState.hasParents() ) {
-// throw new AnnotationException( "No identifier specified for entity: " + clazzToProcess.getName() );
-// }
-//
-// return new InheritanceState.ElementsToProcess( elements, idPropertyCount);
-// }
-
-// private static AccessType determineDefaultAccessType(XClass annotatedClass, Map<XClass, InheritanceState> inheritanceStatePerClass) {
-// XClass xclass = annotatedClass;
-// while ( xclass != null && !Object.class.getName().equals( xclass.getName() ) ) {
-// if ( xclass.isAnnotationPresent( Entity.class ) || xclass.isAnnotationPresent( MappedSuperclass.class ) ) {
-// for ( XProperty prop : xclass.getDeclaredProperties( AccessType.PROPERTY.getType() ) ) {
-// if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
-// return AccessType.PROPERTY;
-// }
-// }
-// for ( XProperty prop : xclass.getDeclaredProperties( AccessType.FIELD.getType() ) ) {
-// if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
-// return AccessType.FIELD;
-// }
-// }
-// }
-// xclass = xclass.getSuperclass();
-// }
-// throw new AnnotationException( "No identifier specified for entity: " + annotatedClass.getName() );
-// }
-//
-// private static List<XClass> getMappedSuperclassesTillNextEntityOrdered(
-// PersistentClass persistentClass, XClass annotatedClass,
-// Map<XClass, InheritanceState> inheritanceStatePerClass,
-// ExtendedMappings mappings
-// ) {
-//
-// //ordered to allow proper messages on properties subclassing
-// List<XClass> classesToProcess = new ArrayList<XClass>();
-// XClass currentClassInHierarchy = annotatedClass;
-// InheritanceState superclassState;
-// final ReflectionManager reflectionManager = mappings.getReflectionManager();
-// do {
-// classesToProcess.add( 0, currentClassInHierarchy );
-// XClass superClass = currentClassInHierarchy;
-// do {
-// superClass = superClass.getSuperclass();
-// superclassState = inheritanceStatePerClass.get( superClass );
-// }
-// while ( superClass != null && !reflectionManager
-// .equals( superClass, Object.class ) && superclassState == null );
-//
-// currentClassInHierarchy = superClass;
-// }
-// while ( superclassState != null && superclassState.isEmbeddableSuperclass() );
-// addMappedSuperClassInMetadata(
-// persistentClass, annotatedClass, inheritanceStatePerClass, mappings, classesToProcess
-// );
-//
-//
-// return classesToProcess;
-// }
-//
-// private static void addMappedSuperClassInMetadata(PersistentClass persistentClass,
-// XClass annotatedClass,
-// Map<XClass, InheritanceState> inheritanceStatePerClass,
-// ExtendedMappings mappings,
-// List<XClass> classesToProcess) {
-// //add @MappedSuperclass in the metadata
-// // classes from 0 to n-1 are @MappedSuperclass and should be linked
-// org.hibernate.mapping.MappedSuperclass mappedSuperclass = null;
-// final InheritanceState superEntityState =
-// InheritanceState.getInheritanceStateOfSuperEntity( annotatedClass, inheritanceStatePerClass );
-// PersistentClass superEntity =
-// superEntityState != null ?
-// mappings.getClass( superEntityState.getClazz().getName() ) :
-// null;
-// final int lastMappedSuperclass = classesToProcess.size() - 1;
-// for ( int index = 0 ; index < lastMappedSuperclass ; index++ ) {
-// org.hibernate.mapping.MappedSuperclass parentSuperclass = mappedSuperclass;
-// final Class<?> type = mappings.getReflectionManager().toClass( classesToProcess.get( index ) );
-// //add MAppedSuperclass if not already there
-// mappedSuperclass = mappings.getMappedSuperclass( type );
-// if (mappedSuperclass == null) {
-// mappedSuperclass = new org.hibernate.mapping.MappedSuperclass(parentSuperclass, superEntity );
-// mappedSuperclass.setMappedClass( type );
-// mappings.addMappedSuperclass( type, mappedSuperclass );
-// }
-// }
-// if (mappedSuperclass != null) {
-// persistentClass.setSuperMappedSuperclass(mappedSuperclass);
-// }
-// }
-
/*
* Process the filters defined on the given class, as well as all filters defined
* on the MappedSuperclass(s) in the inheritance hierarchy
@@ -1347,11 +1226,6 @@
}
log.trace( "{} is a version property", inferredData.getPropertyName() );
RootClass rootClass = (RootClass) propertyHolder.getPersistentClass();
-// PropertyBinder propBinder = new PropertyBinder();
-// propBinder.setName( inferredData.getPropertyName() );
-// propBinder.setReturnedClassName( inferredData.getTypeName() );
-// propBinder.setLazy( false );
-// propBinder.setAccessType( inferredData.getDefaultAccess() );
propertyBinder.setColumns( columns );
Property prop = propertyBinder.makePropertyValueAndBind();
propertyBinder.getSimpleValueBinder().setVersion(true);
@@ -1809,23 +1683,43 @@
propertyBinder.setLazy( lazy );
propertyBinder.setColumns( columns );
-// if ( isIdentifierMapper ) {
-// propertyBinder.setInsertable( false );
-// propertyBinder.setUpdatable( false );
-// }
+
propertyBinder.makePropertyValueAndBind();
+
}
+ if (isOverridden) {
+ final PropertyData mapsIdProperty = BinderHelper.getPropertyAnnotatedWithMapsId(
+ isId, propertyHolder, property.getName(), mappings
+ );
+ HashMap<String, IdGenerator> localGenerators = (HashMap<String, IdGenerator>) classGenerators.clone();
+ final IdGenerator foreignGenerator = new IdGenerator();
+ foreignGenerator.setIdentifierGeneratorStrategy( "assigned" );
+ foreignGenerator.setName( "Hibernate-local--foreign generator" );
+ foreignGenerator.setIdentifierGeneratorStrategy( "foreign" );
+ foreignGenerator.addParam( "property", mapsIdProperty.getPropertyName() );
+ localGenerators.put( foreignGenerator.getName(), foreignGenerator );
+
+ BinderHelper.makeIdGenerator(
+ (SimpleValue) propertyBinder.getValue(),
+ foreignGenerator.getIdentifierGeneratorStrategy(),
+ foreignGenerator.getName(),
+ mappings,
+ localGenerators
+ );
+ }
if (isId) {
//components and regular basic types create SimpleValue objects
final SimpleValue value = ( SimpleValue ) propertyBinder.getValue();
- processId(
- propertyHolder,
- inferredData,
- value,
- classGenerators,
- isIdentifierMapper,
- mappings
- );
+ if ( !isOverridden ) {
+ processId(
+ propertyHolder,
+ inferredData,
+ value,
+ classGenerators,
+ isIdentifierMapper,
+ mappings
+ );
+ }
}
}
//init index
@@ -1862,7 +1756,13 @@
}
}
- private static void processId(PropertyHolder propertyHolder, PropertyData inferredData, SimpleValue idValue, HashMap<String, IdGenerator> classGenerators, boolean isIdentifierMapper, ExtendedMappings mappings) {
+ private static void processId(
+ PropertyHolder propertyHolder,
+ PropertyData inferredData,
+ SimpleValue idValue,
+ HashMap<String, IdGenerator> classGenerators,
+ boolean isIdentifierMapper,
+ ExtendedMappings mappings) {
if ( isIdentifierMapper ) {
throw new AnnotationException(
"@IdClass class should not have @Id nor @EmbeddedId properties: "
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Dependent.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Dependent.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Dependent.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -0,0 +1,22 @@
+package org.hibernate.test.annotations.derivedidentities.e1.a;
+
+import javax.persistence.Entity;
+import javax.persistence.Id;
+import javax.persistence.IdClass;
+import javax.persistence.ManyToOne;
+
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+(a)IdClass(DependentId.class)
+public class Dependent {
+ @Id
+ String name;
+
+ // id attribute mapped by join column default
+ @Id
+ @ManyToOne
+ Employee emp;
+}
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DependentId.java (from rev 18624, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DependentId.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DependentId.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DependentId.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -0,0 +1,11 @@
+package org.hibernate.test.annotations.derivedidentities.e1.a;
+
+import java.io.Serializable;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class DependentId implements Serializable {
+ String name;
+ long empPK; // corresponds to PK type of Employee
+}
\ No newline at end of file
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DerivedIdentitySimpleParentIdClassDepTest.java (from rev 18625, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DerivedIdentitySimpleParentIdClassDepTest.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/DerivedIdentitySimpleParentIdClassDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -0,0 +1,45 @@
+package org.hibernate.test.annotations.derivedidentities.e1.a;
+
+import org.hibernate.Session;
+import org.hibernate.test.annotations.TestCase;
+import org.hibernate.test.util.SchemaUtil;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class
+ DerivedIdentitySimpleParentIdClassDepTest extends TestCase {
+
+ public void testManyToOne() throws Exception {
+// assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK", getCfg() ) );
+// assertTrue( ! SchemaUtil.isColumnPresent( "Dependent", "empPK", getCfg() ) );
+// Employee e = new Employee();
+// e.empId = 1;
+// e.empName = "Emmanuel";
+// Session s = openSession( );
+// s.getTransaction().begin();
+// s.persist( e );
+// Dependent d = new Dependent();
+// d.emp = e;
+// d.name = "Doggy";
+// d.emp = e;
+// s.persist( d );
+// s.flush();
+// s.clear();
+// DependentId dId = new DependentId();
+// dId.name = d.name;
+// dId.empPK = d.emp.empId;
+// d = (Dependent) s.get( Dependent.class, dId );
+// assertEquals( e.empId, d.emp.empId );
+// s.getTransaction().rollback();
+// s.close();
+ }
+
+ @Override
+ protected Class<?>[] getAnnotatedClasses() {
+ return new Class<?>[] {
+ //Dependent.class,
+ //Employee.class
+ };
+ }
+}
\ No newline at end of file
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Employee.java (from rev 18624, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/Employee.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Employee.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/a/Employee.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -0,0 +1,14 @@
+package org.hibernate.test.annotations.derivedidentities.e1.a;
+
+import javax.persistence.Entity;
+import javax.persistence.Id;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class Employee {
+ @Id
+ long empId;
+ String empName;
+}
\ No newline at end of file
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -23,7 +23,7 @@
d.emp = e;
d.id = new DependentId();
d.id.name = "Doggy";
- d.id.empPK = e.empId; //FIXME not needed when foreign is enabled
+ //d.id.empPK = e.empId; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
@@ -46,7 +46,7 @@
d.emp = e;
d.id = new DependentId();
d.id.name = "Doggy";
- d.id.empPK = e.empId; //FIXME not needed when foreign is enabled
+ //d.id.empPK = e.empId; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -25,9 +25,9 @@
d.emp = e;
d.id = new DependentId();
d.id.name = "Doggy";
- d.id.empPK = new EmployeeId();
- d.id.empPK.firstName = e.firstName; //FIXME not needed when foreign is enabled
- d.id.empPK.lastName = e.lastName; //FIXME not needed when foreign is enabled
+// d.id.empPK = new EmployeeId(); //FIXME not needed when foreign is enabled
+// d.id.empPK.firstName = e.firstName; //FIXME not needed when foreign is enabled
+// d.id.empPK.lastName = e.lastName; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -25,9 +25,9 @@
d.emp = e;
d.id = new DependentId();
d.id.name = "Doggy";
- d.id.empPK = new EmployeeId();
- d.id.empPK.firstName = e.empId.firstName; //FIXME not needed when foreign is enabled
- d.id.empPK.lastName = e.empId.lastName; //FIXME not needed when foreign is enabled
+// d.id.empPK = new EmployeeId();
+// d.id.empPK.firstName = e.empId.firstName; //FIXME not needed when foreign is enabled
+// d.id.empPK.lastName = e.empId.lastName; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e4/b/DerivedIdentitySimpleParentSimpleDepMapsIdTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e4/b/DerivedIdentitySimpleParentSimpleDepMapsIdTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e4/b/DerivedIdentitySimpleParentSimpleDepMapsIdTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -21,7 +21,7 @@
s.persist( e );
MedicalHistory d = new MedicalHistory();
d.patient = e;
- d.id = "aaa"; //FIXME not needed when foreign is enabled
+ //d.id = "aaa"; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
@@ -46,7 +46,7 @@
s.persist( e );
FinancialHistory d = new FinancialHistory();
d.patient = e;
- d.id = "aaa"; //FIXME not needed when foreign is enabled
+ //d.id = "aaa"; //FIXME not needed when foreign is enabled
s.persist( d );
s.flush();
s.clear();
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -22,9 +22,9 @@
s.getTransaction().begin();
s.persist( e );
MedicalHistory d = new MedicalHistory();
- d.id = new PersonId();
- d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
- d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
+// d.id = new PersonId(); //FIXME not needed when foreign is enabled
+// d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
+// d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
d.patient = e;
s.persist( d );
s.flush();
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java 2010-01-26 17:12:42 UTC (rev 18632)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java 2010-01-26 17:15:37 UTC (rev 18633)
@@ -21,9 +21,9 @@
s.getTransaction().begin();
s.persist( e );
MedicalHistory d = new MedicalHistory();
- d.id = new PersonId();
- d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
- d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
+// d.id = new PersonId();
+// d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
+// d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
d.patient = e;
s.persist( d );
s.flush();
15 years
Hibernate SVN: r18632 - in core/trunk/core/src/main/java/org/hibernate: mapping and 1 other directory.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 12:12:42 -0500 (Tue, 26 Jan 2010)
New Revision: 18632
Modified:
core/trunk/core/src/main/java/org/hibernate/id/CompositeNestedGeneratedValueGenerator.java
core/trunk/core/src/main/java/org/hibernate/mapping/Component.java
Log:
HHH-4847 inject both object id and the entity itself when asking nested identifier generators
Modified: core/trunk/core/src/main/java/org/hibernate/id/CompositeNestedGeneratedValueGenerator.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/id/CompositeNestedGeneratedValueGenerator.java 2010-01-26 17:11:04 UTC (rev 18631)
+++ core/trunk/core/src/main/java/org/hibernate/id/CompositeNestedGeneratedValueGenerator.java 2010-01-26 17:12:42 UTC (rev 18632)
@@ -67,7 +67,7 @@
}
public static interface GenerationPlan {
- public void execute(SessionImplementor session, Object incomingObject);
+ public void execute(SessionImplementor session, Object incomingObject, Object objectId);
}
private final GenerationContextLocator generationContextLocator;
@@ -87,7 +87,7 @@
Iterator itr = generationPlans.iterator();
while ( itr.hasNext() ) {
final GenerationPlan plan = (GenerationPlan) itr.next();
- plan.execute( session, context );
+ plan.execute( session, object, context );
}
return context;
Modified: core/trunk/core/src/main/java/org/hibernate/mapping/Component.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/mapping/Component.java 2010-01-26 17:11:04 UTC (rev 18631)
+++ core/trunk/core/src/main/java/org/hibernate/mapping/Component.java 2010-01-26 17:12:42 UTC (rev 18632)
@@ -434,9 +434,9 @@
this.injector = injector;
}
- public void execute(SessionImplementor session, Object incomingObject) {
+ public void execute(SessionImplementor session, Object incomingObject, Object idObject) {
final Object generatedValue = subGenerator.generate( session, incomingObject );
- injector.set( incomingObject, generatedValue, session.getFactory() );
+ injector.set( idObject, generatedValue, session.getFactory() );
}
}
15 years
Hibernate SVN: r18631 - core/trunk/entitymanager/src/main/java/org/hibernate/ejb/util.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 12:11:04 -0500 (Tue, 26 Jan 2010)
New Revision: 18631
Modified:
core/trunk/entitymanager/src/main/java/org/hibernate/ejb/util/LogHelper.java
Log:
HHH-4843 guard against null properties
Modified: core/trunk/entitymanager/src/main/java/org/hibernate/ejb/util/LogHelper.java
===================================================================
--- core/trunk/entitymanager/src/main/java/org/hibernate/ejb/util/LogHelper.java 2010-01-26 14:51:54 UTC (rev 18630)
+++ core/trunk/entitymanager/src/main/java/org/hibernate/ejb/util/LogHelper.java 2010-01-26 17:11:04 UTC (rev 18631)
@@ -90,10 +90,12 @@
sb.append( "]\n\t" );
sb.append( "Properties [" );
Properties properties = unitInfo.getProperties();
- Enumeration names = properties.propertyNames();
- while ( names.hasMoreElements() ) {
- String name = (String) names.nextElement();
- sb.append( "\n\t\t" ).append( name ).append( ": " ).append( properties.getProperty( name ) );
+ if (properties != null) {
+ Enumeration names = properties.propertyNames();
+ while ( names.hasMoreElements() ) {
+ String name = (String) names.nextElement();
+ sb.append( "\n\t\t" ).append( name ).append( ": " ).append( properties.getProperty( name ) );
+ }
}
sb.append( "]" );
return sb.toString();
15 years
Hibernate SVN: r18630 - core/trunk/entitymanager/src/main/java/org/hibernate/ejb/metamodel.
by hibernate-commits@lists.jboss.org
Author: smarlow(a)redhat.com
Date: 2010-01-26 09:51:54 -0500 (Tue, 26 Jan 2010)
New Revision: 18630
Modified:
core/trunk/entitymanager/src/main/java/org/hibernate/ejb/metamodel/AbstractIdentifiableType.java
Log:
HHH-4846 fix NPE and also address JCTS-946
Modified: core/trunk/entitymanager/src/main/java/org/hibernate/ejb/metamodel/AbstractIdentifiableType.java
===================================================================
--- core/trunk/entitymanager/src/main/java/org/hibernate/ejb/metamodel/AbstractIdentifiableType.java 2010-01-26 13:39:26 UTC (rev 18629)
+++ core/trunk/entitymanager/src/main/java/org/hibernate/ejb/metamodel/AbstractIdentifiableType.java 2010-01-26 14:51:54 UTC (rev 18630)
@@ -241,10 +241,8 @@
* super class.
*/
protected void checkDeclaredVersion() {
- if ( version == null ) {
- if ( getSupertype() != null && getSupertype().hasVersionAttribute() ) {
- throw new IllegalArgumentException( "The version attribute is not declared on this type" );
- }
+ if ( version == null || ( getSupertype() != null && getSupertype().hasVersionAttribute() )) {
+ throw new IllegalArgumentException( "The version attribute is not declared on this type" );
}
}
15 years
Hibernate SVN: r18629 - in core/trunk/annotations/src: test/java/org/hibernate/test/annotations/idclassgeneratedvalue and 1 other directory.
by hibernate-commits@lists.jboss.org
Author: stalep
Date: 2010-01-26 08:39:26 -0500 (Tue, 26 Jan 2010)
New Revision: 18629
Modified:
core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/idclassgeneratedvalue/IdClassGeneratedValueTest.java
Log:
[HHH-4552] generatedvalue for compositekeys are now parsed and added to the id properties
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 13:30:32 UTC (rev 18628)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 13:39:26 UTC (rev 18629)
@@ -2100,6 +2100,22 @@
new HashMap<String, IdGenerator>(), entityBinder, isIdentifierMapper, isComponentEmbedded,
inSecondPass, mappings, inheritanceStatePerClass
);
+
+ XProperty property = propertyAnnotatedElement.getProperty();
+ if(property.isAnnotationPresent(GeneratedValue.class) &&
+ property.isAnnotationPresent(Id.class))
+ {
+ //clone classGenerator and override with local values
+ HashMap<String, IdGenerator> localGenerators = (HashMap<String, IdGenerator>) new HashMap<String, IdGenerator>();
+ localGenerators.putAll( buildLocalGenerators( property, mappings ) );
+
+ GeneratedValue generatedValue = property.getAnnotation( GeneratedValue.class );
+ String generatorType = generatedValue != null ? generatorType( generatedValue.strategy() ) : "assigned";
+ String generator = generatedValue != null ? generatedValue.generator() : BinderHelper.ANNOTATION_STRING_DEFAULT;
+
+ BinderHelper.makeIdGenerator( (SimpleValue) comp.getProperty(property.getName()).getValue(), generatorType, generator, mappings, localGenerators);
+ }
+
}
return comp;
}
@@ -2120,21 +2136,6 @@
return comp;
}
- private static void bindId(
- String generatorType, String generatorName,
- PropertyData inferredData, Ejb3Column[] columns, PropertyHolder propertyHolder,
- Map<String, IdGenerator> localGenerators,
- boolean isComposite,
- AccessType propertyAccessor, EntityBinder entityBinder, boolean isEmbedded,
- boolean isIdentifierMapper, ExtendedMappings mappings,
- Map<XClass, InheritanceState> inheritanceStatePerClass
- ) {
-
- bindId(generatorType, generatorName, inferredData, null, columns, propertyHolder,
- localGenerators, isComposite, propertyAccessor, entityBinder,
- isEmbedded, isIdentifierMapper, mappings, inheritanceStatePerClass);
- }
-
private static void bindId(
String generatorType, String generatorName, PropertyData inferredData,
PropertyData baseInferredData, Ejb3Column[] columns, PropertyHolder propertyHolder,
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/idclassgeneratedvalue/IdClassGeneratedValueTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/idclassgeneratedvalue/IdClassGeneratedValueTest.java 2010-01-26 13:30:32 UTC (rev 18628)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/idclassgeneratedvalue/IdClassGeneratedValueTest.java 2010-01-26 13:39:26 UTC (rev 18629)
@@ -75,7 +75,7 @@
s = openSession();
s.beginTransaction();
- List<Simple> simpleList = s.createQuery( "select s from Simple2 s" ).list();
+ List<Simple2> simpleList = s.createQuery( "select s from Simple2 s" ).list();
assertEquals( simpleList.size(), 2 );
s1 = ( Simple2 ) s.load( Simple2.class, new SimplePK( s1Id1, 2L ) );
assertEquals( s1.getQuantity(), 10 );
@@ -101,7 +101,7 @@
s = openSession();
s.beginTransaction();
- List<Simple> simpleList = s.createQuery( "select m from Multiple m" ).list();
+ List<Multiple> simpleList = s.createQuery( "select m from Multiple m" ).list();
assertEquals( simpleList.size(), 2 );
m1 = ( Multiple ) s.load( Multiple.class, new MultiplePK( m1Id1, m1Id2, 2L ) );
assertEquals( m1.getQuantity(), 10 );
15 years
Hibernate SVN: r18628 - in core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities: e5/b and 2 other directories.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 08:30:32 -0500 (Tue, 26 Jan 2010)
New Revision: 18628
Added:
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/MedicalHistory.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/Person.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/PersonId.java
Modified:
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
Log:
HHH-4529 Add support for parent's id as EmbeddedId and derived entity reusing the same PK class than the parent
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java 2010-01-26 13:26:07 UTC (rev 18627)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java 2010-01-26 13:30:32 UTC (rev 18628)
@@ -38,7 +38,7 @@
@Override
protected Class<?>[] getAnnotatedClasses() {
return new Class<?>[] {
- MedicalHistory.class,
+ MedicalHistory.class,
Person.class
};
}
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java (from rev 18627, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/DerivedIdentityEmbeddedIdParentSameIdTypeDepTest.java 2010-01-26 13:30:32 UTC (rev 18628)
@@ -0,0 +1,44 @@
+package org.hibernate.test.annotations.derivedidentities.e6.b;
+
+import org.hibernate.Session;
+import org.hibernate.test.annotations.TestCase;
+import org.hibernate.test.util.SchemaUtil;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class DerivedIdentityEmbeddedIdParentSameIdTypeDepTest extends TestCase {
+
+ public void testOneToOneExplicitJoinColumn() throws Exception {
+ assertTrue( SchemaUtil.isColumnPresent( "MedicalHistory", "FK1", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "MedicalHistory", "FK2", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "MedicalHistory", "firstname", getCfg() ) );
+ Person e = new Person();
+ e.id = new PersonId();
+ e.id.firstName = "Emmanuel";
+ e.id.lastName = "Bernard";
+ Session s = openSession( );
+ s.getTransaction().begin();
+ s.persist( e );
+ MedicalHistory d = new MedicalHistory();
+ d.id = new PersonId();
+ d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
+ d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
+ d.patient = e;
+ s.persist( d );
+ s.flush();
+ s.clear();
+ d = (MedicalHistory) s.get( MedicalHistory.class, d.id );
+ assertEquals( d.id.firstName, d.patient.id.firstName );
+ s.getTransaction().rollback();
+ s.close();
+ }
+
+ @Override
+ protected Class<?>[] getAnnotatedClasses() {
+ return new Class<?>[] {
+ MedicalHistory.class,
+ Person.class
+ };
+ }
+}
\ No newline at end of file
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/MedicalHistory.java (from rev 18627, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/MedicalHistory.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/MedicalHistory.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/MedicalHistory.java 2010-01-26 13:30:32 UTC (rev 18628)
@@ -0,0 +1,26 @@
+package org.hibernate.test.annotations.derivedidentities.e6.b;
+
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+import javax.persistence.JoinColumn;
+import javax.persistence.JoinColumns;
+import javax.persistence.MapsId;
+import javax.persistence.OneToOne;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class MedicalHistory {
+ //all attributes map to relationship: AttributeOverride not allowed
+ @EmbeddedId
+ PersonId id;
+
+ @MapsId
+ @JoinColumns({
+ @JoinColumn(name = "FK1", referencedColumnName = "firstName"),
+ @JoinColumn(name = "FK2", referencedColumnName = "lastName")
+ })
+ @OneToOne
+ Person patient;
+}
\ No newline at end of file
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/Person.java (from rev 18627, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/Person.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/Person.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/Person.java 2010-01-26 13:30:32 UTC (rev 18628)
@@ -0,0 +1,13 @@
+package org.hibernate.test.annotations.derivedidentities.e6.b;
+
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class Person {
+ @EmbeddedId
+ PersonId id;
+}
\ No newline at end of file
Copied: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/PersonId.java (from rev 18627, core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/PersonId.java)
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/PersonId.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e6/b/PersonId.java 2010-01-26 13:30:32 UTC (rev 18628)
@@ -0,0 +1,13 @@
+package org.hibernate.test.annotations.derivedidentities.e6.b;
+
+import java.io.Serializable;
+import javax.persistence.Embeddable;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Embeddable
+public class PersonId implements Serializable {
+ String firstName;
+ String lastName;
+}
\ No newline at end of file
15 years
Hibernate SVN: r18627 - in core/trunk/annotations/src: test/java/org/hibernate/test/annotations/derivedidentities and 2 other directories.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 08:26:07 -0500 (Tue, 26 Jan 2010)
New Revision: 18627
Added:
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/MedicalHistory.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/Person.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/PersonId.java
Modified:
core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
Log:
HHH-4529 Add support for parent's id as IdClass and derived entity reusing the same PK class than the parent
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 13:08:02 UTC (rev 18626)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 13:26:07 UTC (rev 18627)
@@ -2000,9 +2000,9 @@
+ " must not have @Id properties when used as an @EmbeddedId: "
+ BinderHelper.getPath( propertyHolder, inferredData ) );
}
- if ( comp.getPropertySpan() == 0 ) {
+ if ( referencedEntityName == null && comp.getPropertySpan() == 0 ) {
throw new AnnotationException( comp.getComponentClassName()
- + " has no persistent id property"
+ + " has no persistent id property: "
+ BinderHelper.getPath( propertyHolder, inferredData ) );
}
}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/DerivedIdentityIdClassParentSameIdTypeDepTest.java 2010-01-26 13:26:07 UTC (rev 18627)
@@ -0,0 +1,45 @@
+package org.hibernate.test.annotations.derivedidentities.e5.b;
+
+import java.util.Date;
+
+import org.hibernate.Session;
+import org.hibernate.test.annotations.TestCase;
+import org.hibernate.test.util.SchemaUtil;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class DerivedIdentityIdClassParentSameIdTypeDepTest extends TestCase {
+
+ public void testOneToOneExplicitJoinColumn() throws Exception {
+ assertTrue( SchemaUtil.isColumnPresent( "MedicalHistory", "FK1", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "MedicalHistory", "FK2", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "MedicalHistory", "firstname", getCfg() ) );
+ Person e = new Person();
+ e.firstName = "Emmanuel";
+ e.lastName = "Bernard";
+ Session s = openSession( );
+ s.getTransaction().begin();
+ s.persist( e );
+ MedicalHistory d = new MedicalHistory();
+ d.id = new PersonId();
+ d.id.firstName = "Emmanuel"; //FIXME not needed when foreign is enabled
+ d.id.lastName = "Bernard"; //FIXME not needed when foreign is enabled
+ d.patient = e;
+ s.persist( d );
+ s.flush();
+ s.clear();
+ d = (MedicalHistory) s.get( MedicalHistory.class, d.id );
+ assertEquals( d.id.firstName, d.patient.firstName );
+ s.getTransaction().rollback();
+ s.close();
+ }
+
+ @Override
+ protected Class<?>[] getAnnotatedClasses() {
+ return new Class<?>[] {
+ MedicalHistory.class,
+ Person.class
+ };
+ }
+}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/MedicalHistory.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/MedicalHistory.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/MedicalHistory.java 2010-01-26 13:26:07 UTC (rev 18627)
@@ -0,0 +1,27 @@
+package org.hibernate.test.annotations.derivedidentities.e5.b;
+
+import java.util.Date;
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+import javax.persistence.JoinColumn;
+import javax.persistence.JoinColumns;
+import javax.persistence.MapsId;
+import javax.persistence.OneToOne;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class MedicalHistory {
+ //all attributes map to relationship: AttributeOverride not allowed
+ @EmbeddedId
+ PersonId id;
+
+ @MapsId
+ @JoinColumns({
+ @JoinColumn(name = "FK1", referencedColumnName = "firstName"),
+ @JoinColumn(name = "FK2", referencedColumnName = "lastName")
+ })
+ @OneToOne
+ Person patient;
+}
\ No newline at end of file
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/Person.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/Person.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/Person.java 2010-01-26 13:26:07 UTC (rev 18627)
@@ -0,0 +1,17 @@
+package org.hibernate.test.annotations.derivedidentities.e5.b;
+
+import javax.persistence.Entity;
+import javax.persistence.Id;
+import javax.persistence.IdClass;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+(a)IdClass(PersonId.class)
+public class Person {
+ @Id
+ String firstName;
+ @Id
+ String lastName;
+}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/PersonId.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/PersonId.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e5/b/PersonId.java 2010-01-26 13:26:07 UTC (rev 18627)
@@ -0,0 +1,11 @@
+package org.hibernate.test.annotations.derivedidentities.e5.b;
+
+import java.io.Serializable;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class PersonId implements Serializable {
+ String firstName;
+ String lastName;
+}
15 years
Hibernate SVN: r18626 - in core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities: e3 and 1 other directories.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 08:08:02 -0500 (Tue, 26 Jan 2010)
New Revision: 18626
Added:
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Dependent.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DependentId.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Employee.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/EmployeeId.java
Log:
HHH-4529 add tests for parent class @EmbeddedId and derived class @EmbeddedId
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Dependent.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Dependent.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Dependent.java 2010-01-26 13:08:02 UTC (rev 18626)
@@ -0,0 +1,31 @@
+package org.hibernate.test.annotations.derivedidentities.e3.b;
+
+import javax.persistence.AttributeOverride;
+import javax.persistence.Column;
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+import javax.persistence.JoinColumn;
+import javax.persistence.JoinColumns;
+import javax.persistence.ManyToOne;
+import javax.persistence.MapsId;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class Dependent {
+ // default column name for "name" attribute is overridden
+ @AttributeOverride(name = "name", column = @Column(name = "dep_name"))
+ @EmbeddedId
+ DependentId id;
+
+
+ @MapsId("empPK")
+ @JoinColumns({
+ @JoinColumn(name = "FK1", referencedColumnName = "firstName"),
+ @JoinColumn(name = "FK2", referencedColumnName = "lastName")
+ })
+ @ManyToOne
+ Employee emp;
+
+}
\ No newline at end of file
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DependentId.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DependentId.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DependentId.java 2010-01-26 13:08:02 UTC (rev 18626)
@@ -0,0 +1,13 @@
+package org.hibernate.test.annotations.derivedidentities.e3.b;
+
+import java.io.Serializable;
+import javax.persistence.Embeddable;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Embeddable
+public class DependentId implements Serializable {
+ String name;
+ EmployeeId empPK;
+}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest.java 2010-01-26 13:08:02 UTC (rev 18626)
@@ -0,0 +1,49 @@
+package org.hibernate.test.annotations.derivedidentities.e3.b;
+
+import org.hibernate.Session;
+import org.hibernate.test.annotations.TestCase;
+import org.hibernate.test.util.SchemaUtil;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class DerivedIdentityEmbeddedIdParentEmbeddedIdDepTest extends TestCase {
+ public void testManyToOne() throws Exception {
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK1", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK2", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "dep_name", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "Dependent", "firstName", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "Dependent", "lastName", getCfg() ) );
+ Employee e = new Employee();
+ e.empId = new EmployeeId();
+ e.empId.firstName = "Emmanuel";
+ e.empId.lastName = "Bernard";
+ Session s = openSession( );
+ s.getTransaction().begin();
+ s.persist( e );
+ Dependent d = new Dependent();
+ d.emp = e;
+ d.id = new DependentId();
+ d.id.name = "Doggy";
+ d.id.empPK = new EmployeeId();
+ d.id.empPK.firstName = e.empId.firstName; //FIXME not needed when foreign is enabled
+ d.id.empPK.lastName = e.empId.lastName; //FIXME not needed when foreign is enabled
+ s.persist( d );
+ s.flush();
+ s.clear();
+ d = (Dependent) s.get( Dependent.class, d.id );
+ assertNotNull( d.emp );
+ assertEquals( e.empId.firstName, d.emp.empId.firstName );
+ s.getTransaction().rollback();
+ s.close();
+ }
+
+
+ @Override
+ protected Class<?>[] getAnnotatedClasses() {
+ return new Class<?>[] {
+ Dependent.class,
+ Employee.class
+ };
+ }
+}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Employee.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Employee.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/Employee.java 2010-01-26 13:08:02 UTC (rev 18626)
@@ -0,0 +1,14 @@
+package org.hibernate.test.annotations.derivedidentities.e3.b;
+
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Entity
+public class Employee {
+ @EmbeddedId
+ EmployeeId empId;
+}
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/EmployeeId.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/EmployeeId.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e3/b/EmployeeId.java 2010-01-26 13:08:02 UTC (rev 18626)
@@ -0,0 +1,13 @@
+package org.hibernate.test.annotations.derivedidentities.e3.b;
+
+import java.io.Serializable;
+import javax.persistence.Embeddable;
+
+/**
+ * @author Emmanuel Bernard
+ */
+@Embeddable
+public class EmployeeId implements Serializable {
+ String firstName;
+ String lastName;
+}
15 years
Hibernate SVN: r18625 - in core/trunk/annotations/src: test/java/org/hibernate/test/annotations/derivedidentities/e1/b and 2 other directories.
by hibernate-commits@lists.jboss.org
Author: epbernard
Date: 2010-01-26 07:57:01 -0500 (Tue, 26 Jan 2010)
New Revision: 18625
Added:
core/trunk/annotations/src/main/java/org/hibernate/cfg/ColumnsBuilder.java
core/trunk/annotations/src/main/java/org/hibernate/cfg/CopyIdentifierComponentSecondPass.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java
Modified:
core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationConfiguration.java
core/trunk/annotations/src/main/java/org/hibernate/cfg/BinderHelper.java
core/trunk/annotations/src/main/java/org/hibernate/cfg/InheritanceState.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/c/Dependent.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DependentId.java
core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/EmployeeId.java
Log:
HHH-4529 Add support for parent's id being an IdClass or an EmbeddedId (last case not tested yet). (example e2.b)
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationBinder.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -52,7 +52,6 @@
import javax.persistence.IdClass;
import javax.persistence.InheritanceType;
import javax.persistence.JoinColumn;
-import javax.persistence.JoinColumns;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;
import javax.persistence.ManyToOne;
@@ -105,7 +104,6 @@
import org.hibernate.annotations.Formula;
import org.hibernate.annotations.GenericGenerator;
import org.hibernate.annotations.Index;
-import org.hibernate.annotations.JoinColumnsOrFormulas;
import org.hibernate.annotations.LazyToOne;
import org.hibernate.annotations.LazyToOneOption;
import org.hibernate.annotations.ManyToAny;
@@ -167,7 +165,7 @@
import org.hibernate.persister.entity.SingleTableEntityPersister;
import org.hibernate.persister.entity.UnionSubclassEntityPersister;
import org.hibernate.type.TypeFactory;
-import org.hibernate.util.StringHelper;
+
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -182,7 +180,8 @@
* @author Hardy Ferentschik
*/
@SuppressWarnings("unchecked")
-public final class AnnotationBinder {
+public final class
+ AnnotationBinder {
/*
* Some design description
@@ -625,30 +624,16 @@
HashMap<String, IdGenerator> classGenerators = buildLocalGenerators( clazzToProcess, mappings );
// check properties
- final ElementsToProcess elementsToProcess = getElementsToProcess(
- persistentClass, clazzToProcess, inheritanceStatePerClass, entityBinder, mappings
- );
-
+ final InheritanceState.ElementsToProcess elementsToProcess = inheritanceState.getElementsToProcess();
+ inheritanceState.postProcess( persistentClass, entityBinder );
+
final boolean subclassAndSingleTableStrategy = inheritanceState.getType() == InheritanceType.SINGLE_TABLE
&& inheritanceState.hasParents();
//process idclass if any
Set<String> idProperties = new HashSet<String>();
- IdClass idClass = null;
- XClass current = null;
- if ( !inheritanceState.hasParents() ) {
- //look for idClass
- InheritanceState state = inheritanceState;
- do {
- current = state.getClazz();
- if ( current.isAnnotationPresent( IdClass.class ) ) {
- idClass = current.getAnnotation( IdClass.class );
- break;
- }
- state = InheritanceState.getSuperclassInheritanceState( current, inheritanceStatePerClass );
- }
- while ( state != null );
- }
- if ( idClass != null ) {
+ XClass classWithIdClass = inheritanceState.getClassWithIdClass(false);
+ if ( classWithIdClass != null ) {
+ IdClass idClass = classWithIdClass.getAnnotation( IdClass.class );
XClass compositeClass = mappings.getReflectionManager().toXClass( idClass.value() );
boolean isComponent = true;
AccessType propertyAccessor = entityBinder.getPropertyAccessor( compositeClass );
@@ -658,7 +643,7 @@
entityBinder.getPropertyAccessType(), "id", compositeClass
);
PropertyData baseInferredData = new PropertyPreloadedData(
- entityBinder.getPropertyAccessType(), "id", current
+ entityBinder.getPropertyAccessType(), "id", classWithIdClass
);
HashMap<String, IdGenerator> localGenerators = new HashMap<String, IdGenerator>();
boolean ignoreIdAnnotations = entityBinder.isIgnoreIdAnnotations();
@@ -982,134 +967,127 @@
return true;
}
- /*
- * Get the annotated elements, guessing the access type from @Id or @EmbeddedId presence.
- * Change EntityBinder by side effect
- */
- private static ElementsToProcess getElementsToProcess(
- PersistentClass persistentClass, XClass clazzToProcess,
- Map<XClass, InheritanceState> inheritanceStatePerClass,
- EntityBinder entityBinder, ExtendedMappings mappings
- ) {
- InheritanceState inheritanceState = inheritanceStatePerClass.get( clazzToProcess );
- assert !inheritanceState.isEmbeddableSuperclass();
+// /*
+// * Get the annotated elements, guessing the access type from @Id or @EmbeddedId presence.
+// * Change EntityBinder by side effect
+// */
+// private static InheritanceState.ElementsToProcess getElementsToProcess(
+// PersistentClass persistentClass, XClass clazzToProcess,
+// Map<XClass, InheritanceState> inheritanceStatePerClass,
+// EntityBinder entityBinder, ExtendedMappings mappings
+// ) {
+// InheritanceState inheritanceState = inheritanceStatePerClass.get( clazzToProcess );
+// assert !inheritanceState.isEmbeddableSuperclass();
+//
+//
+// List<XClass> classesToProcess = getMappedSuperclassesTillNextEntityOrdered(
+// persistentClass, clazzToProcess, inheritanceStatePerClass, mappings
+// );
+//
+// AccessType accessType = determineDefaultAccessType( clazzToProcess, inheritanceStatePerClass );
+//
+// List<PropertyData> elements = new ArrayList<PropertyData>();
+// int deep = classesToProcess.size();
+// int idPropertyCount = 0;
+//
+// for ( int index = 0; index < deep; index++ ) {
+// PropertyContainer propertyContainer = new PropertyContainer( classesToProcess.get( index ), clazzToProcess );
+// int currentIdPropertyCount = addElementsOfClass( elements, accessType, propertyContainer, mappings );
+// idPropertyCount += currentIdPropertyCount;
+// }
+//
+// entityBinder.setPropertyAccessType( accessType );
+//
+// if ( idPropertyCount == 0 && !inheritanceState.hasParents() ) {
+// throw new AnnotationException( "No identifier specified for entity: " + clazzToProcess.getName() );
+// }
+//
+// return new InheritanceState.ElementsToProcess( elements, idPropertyCount);
+// }
+// private static AccessType determineDefaultAccessType(XClass annotatedClass, Map<XClass, InheritanceState> inheritanceStatePerClass) {
+// XClass xclass = annotatedClass;
+// while ( xclass != null && !Object.class.getName().equals( xclass.getName() ) ) {
+// if ( xclass.isAnnotationPresent( Entity.class ) || xclass.isAnnotationPresent( MappedSuperclass.class ) ) {
+// for ( XProperty prop : xclass.getDeclaredProperties( AccessType.PROPERTY.getType() ) ) {
+// if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
+// return AccessType.PROPERTY;
+// }
+// }
+// for ( XProperty prop : xclass.getDeclaredProperties( AccessType.FIELD.getType() ) ) {
+// if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
+// return AccessType.FIELD;
+// }
+// }
+// }
+// xclass = xclass.getSuperclass();
+// }
+// throw new AnnotationException( "No identifier specified for entity: " + annotatedClass.getName() );
+// }
+//
+// private static List<XClass> getMappedSuperclassesTillNextEntityOrdered(
+// PersistentClass persistentClass, XClass annotatedClass,
+// Map<XClass, InheritanceState> inheritanceStatePerClass,
+// ExtendedMappings mappings
+// ) {
+//
+// //ordered to allow proper messages on properties subclassing
+// List<XClass> classesToProcess = new ArrayList<XClass>();
+// XClass currentClassInHierarchy = annotatedClass;
+// InheritanceState superclassState;
+// final ReflectionManager reflectionManager = mappings.getReflectionManager();
+// do {
+// classesToProcess.add( 0, currentClassInHierarchy );
+// XClass superClass = currentClassInHierarchy;
+// do {
+// superClass = superClass.getSuperclass();
+// superclassState = inheritanceStatePerClass.get( superClass );
+// }
+// while ( superClass != null && !reflectionManager
+// .equals( superClass, Object.class ) && superclassState == null );
+//
+// currentClassInHierarchy = superClass;
+// }
+// while ( superclassState != null && superclassState.isEmbeddableSuperclass() );
+// addMappedSuperClassInMetadata(
+// persistentClass, annotatedClass, inheritanceStatePerClass, mappings, classesToProcess
+// );
+//
+//
+// return classesToProcess;
+// }
+//
+// private static void addMappedSuperClassInMetadata(PersistentClass persistentClass,
+// XClass annotatedClass,
+// Map<XClass, InheritanceState> inheritanceStatePerClass,
+// ExtendedMappings mappings,
+// List<XClass> classesToProcess) {
+// //add @MappedSuperclass in the metadata
+// // classes from 0 to n-1 are @MappedSuperclass and should be linked
+// org.hibernate.mapping.MappedSuperclass mappedSuperclass = null;
+// final InheritanceState superEntityState =
+// InheritanceState.getInheritanceStateOfSuperEntity( annotatedClass, inheritanceStatePerClass );
+// PersistentClass superEntity =
+// superEntityState != null ?
+// mappings.getClass( superEntityState.getClazz().getName() ) :
+// null;
+// final int lastMappedSuperclass = classesToProcess.size() - 1;
+// for ( int index = 0 ; index < lastMappedSuperclass ; index++ ) {
+// org.hibernate.mapping.MappedSuperclass parentSuperclass = mappedSuperclass;
+// final Class<?> type = mappings.getReflectionManager().toClass( classesToProcess.get( index ) );
+// //add MAppedSuperclass if not already there
+// mappedSuperclass = mappings.getMappedSuperclass( type );
+// if (mappedSuperclass == null) {
+// mappedSuperclass = new org.hibernate.mapping.MappedSuperclass(parentSuperclass, superEntity );
+// mappedSuperclass.setMappedClass( type );
+// mappings.addMappedSuperclass( type, mappedSuperclass );
+// }
+// }
+// if (mappedSuperclass != null) {
+// persistentClass.setSuperMappedSuperclass(mappedSuperclass);
+// }
+// }
- List<XClass> classesToProcess = getMappedSuperclassesTillNextEntityOrdered(
- persistentClass, clazzToProcess, inheritanceStatePerClass, mappings
- );
-
- AccessType accessType = determineDefaultAccessType( clazzToProcess, inheritanceStatePerClass );
-
- List<PropertyData> elements = new ArrayList<PropertyData>();
- int deep = classesToProcess.size();
- int idPropertyCount = 0;
-
- for ( int index = 0; index < deep; index++ ) {
- PropertyContainer propertyContainer = new PropertyContainer( classesToProcess.get( index ), clazzToProcess );
- int currentIdPropertyCount = addElementsOfClass( elements, accessType, propertyContainer, mappings );
- idPropertyCount += currentIdPropertyCount;
- }
-
- entityBinder.setPropertyAccessType( accessType );
-
- if ( idPropertyCount == 0 && !inheritanceState.hasParents() ) {
- throw new AnnotationException( "No identifier specified for entity: " + clazzToProcess.getName() );
- }
-
- return new ElementsToProcess( elements, idPropertyCount);
- }
-
- private static final class ElementsToProcess {
- private final List<PropertyData> properties;
- private final int idPropertyCount;
-
- public List<PropertyData> getElements() {
- return properties;
- }
-
- public int getIdPropertyCount() {
- return idPropertyCount;
- }
-
- private ElementsToProcess(List<PropertyData> properties, int idPropertyCount) {
- this.properties = properties;
- this.idPropertyCount = idPropertyCount;
- }
- }
-
- private static AccessType determineDefaultAccessType(XClass annotatedClass, Map<XClass, InheritanceState> inheritanceStatePerClass) {
- XClass xclass = annotatedClass;
- while ( xclass != null && !Object.class.getName().equals( xclass.getName() ) ) {
- if ( xclass.isAnnotationPresent( Entity.class ) || xclass.isAnnotationPresent( MappedSuperclass.class ) ) {
- for ( XProperty prop : xclass.getDeclaredProperties( AccessType.PROPERTY.getType() ) ) {
- if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
- return AccessType.PROPERTY;
- }
- }
- for ( XProperty prop : xclass.getDeclaredProperties( AccessType.FIELD.getType() ) ) {
- if ( prop.isAnnotationPresent( Id.class ) || prop.isAnnotationPresent( EmbeddedId.class ) ) {
- return AccessType.FIELD;
- }
- }
- }
- xclass = xclass.getSuperclass();
- }
- throw new AnnotationException( "No identifier specified for entity: " + annotatedClass.getName() );
- }
-
- private static List<XClass> getMappedSuperclassesTillNextEntityOrdered(
- PersistentClass persistentClass, XClass annotatedClass,
- Map<XClass, InheritanceState> inheritanceStatePerClass,
- ExtendedMappings mappings
- ) {
-
- //ordered to allow proper messages on properties subclassing
- List<XClass> classesToProcess = new ArrayList<XClass>();
- XClass currentClassInHierarchy = annotatedClass;
- InheritanceState superclassState;
- final ReflectionManager reflectionManager = mappings.getReflectionManager();
- do {
- classesToProcess.add( 0, currentClassInHierarchy );
- XClass superClass = currentClassInHierarchy;
- do {
- superClass = superClass.getSuperclass();
- superclassState = inheritanceStatePerClass.get( superClass );
- }
- while ( superClass != null && !reflectionManager
- .equals( superClass, Object.class ) && superclassState == null );
-
- currentClassInHierarchy = superClass;
- }
- while ( superclassState != null && superclassState.isEmbeddableSuperclass() );
-
- //add @MappedSuperclass in the metadata
- // classes from 0 to n-1 are @MappedSuperclass and should be linked
- org.hibernate.mapping.MappedSuperclass mappedSuperclass = null;
- final InheritanceState superEntityState =
- InheritanceState.getInheritanceStateOfSuperEntity( annotatedClass, inheritanceStatePerClass );
- PersistentClass superEntity =
- superEntityState != null ?
- mappings.getClass( superEntityState.getClazz().getName() ) :
- null;
- final int lastMappedSuperclass = classesToProcess.size() - 1;
- for ( int index = 0 ; index < lastMappedSuperclass ; index++ ) {
- org.hibernate.mapping.MappedSuperclass parentSuperclass = mappedSuperclass;
- final Class<?> type = mappings.getReflectionManager().toClass( classesToProcess.get( index ) );
- //add MAppedSuperclass if not already there
- mappedSuperclass = mappings.getMappedSuperclass( type );
- if (mappedSuperclass == null) {
- mappedSuperclass = new org.hibernate.mapping.MappedSuperclass(parentSuperclass, superEntity );
- mappedSuperclass.setMappedClass( type );
- mappings.addMappedSuperclass( type, mappedSuperclass );
- }
- }
- if (mappedSuperclass != null) {
- persistentClass.setSuperMappedSuperclass(mappedSuperclass);
- }
- return classesToProcess;
- }
-
/*
* Process the filters defined on the given class, as well as all filters defined
* on the MappedSuperclass(s) in the inheritance hierarchy
@@ -1235,7 +1213,7 @@
* @return the number of id properties found while iterating the elements of {@code annoatedClass} using
* the determined access strategy, {@code false} otherwise.
*/
- private static int addElementsOfClass(
+ static int addElementsOfClass(
List<PropertyData> elements, AccessType defaultAccessType, PropertyContainer propertyContainer, ExtendedMappings mappings
) {
int idPropertyCounter = 0;
@@ -1295,14 +1273,12 @@
EntityBinder entityBinder, boolean isIdentifierMapper,
boolean isComponentEmbedded, boolean inSecondPass, ExtendedMappings mappings,
Map<XClass, InheritanceState> inheritanceStatePerClass
- )
- throws MappingException {
+ ) throws MappingException {
/**
* inSecondPass can only be used to apply right away the second pass of a composite-element
* Because it's a value type, there is no bidirectional association, hence second pass
* ordering does not matter
*/
- Ejb3Column[] columns = null;
log.trace(
"Processing annotations of {}.{}", propertyHolder.getEntityName(), inferredData.getPropertyName()
@@ -1318,71 +1294,15 @@
+ BinderHelper.getPath( propertyHolder, inferredData )
);
}
- return;
+ return ;
}
- Ejb3JoinColumn[] joinColumns = buildExplicitJoinColumns(
- propertyHolder, property, inferredData, entityBinder, mappings
- );
+ ColumnsBuilder columnsBuilder = new ColumnsBuilder(
+ propertyHolder, nullability, property, inferredData, entityBinder, mappings
+ ).extractMetadata();
+ Ejb3Column[] columns = columnsBuilder.getColumns();
+ Ejb3JoinColumn[] joinColumns = columnsBuilder.getJoinColumns();
- if ( property.isAnnotationPresent( Column.class ) || property.isAnnotationPresent( Formula.class ) ) {
- Column ann = property.getAnnotation( Column.class );
- Formula formulaAnn = property.getAnnotation( Formula.class );
- columns = Ejb3Column.buildColumnFromAnnotation(
- new Column[] { ann }, formulaAnn, nullability, propertyHolder, inferredData,
- entityBinder.getSecondaryTables(), mappings
- );
- }
- else if ( property.isAnnotationPresent( Columns.class ) ) {
- Columns anns = property.getAnnotation( Columns.class );
- columns = Ejb3Column.buildColumnFromAnnotation(
- anns.columns(), null, nullability, propertyHolder, inferredData, entityBinder.getSecondaryTables(),
- mappings
- );
- }
-
- //set default values if needed
- if ( joinColumns == null &&
- ( property.isAnnotationPresent( ManyToOne.class )
- || property.isAnnotationPresent( OneToOne.class ) )
- ) {
- joinColumns = buildDefaultJoinColumnsForXToOne(
- propertyHolder, property, inferredData, entityBinder, mappings
- );
- }
- else if ( joinColumns == null &&
- ( property.isAnnotationPresent( OneToMany.class )
- || property.isAnnotationPresent( CollectionOfElements.class ) //legacy Hibernate
- || property.isAnnotationPresent( ElementCollection.class )
- ) ) {
- OneToMany oneToMany = property.getAnnotation( OneToMany.class );
- String mappedBy = oneToMany != null ?
- oneToMany.mappedBy() :
- "";
- joinColumns = Ejb3JoinColumn.buildJoinColumns(
- (JoinColumn[]) null,
- mappedBy, entityBinder.getSecondaryTables(),
- propertyHolder, inferredData.getPropertyName(), mappings
- );
- }
- else if ( joinColumns == null && property.isAnnotationPresent( org.hibernate.annotations.Any.class ) ) {
- throw new AnnotationException( "@Any requires an explicit @JoinColumn(s): "
- + BinderHelper.getPath( propertyHolder, inferredData ) );
- }
- if ( columns == null && !property.isAnnotationPresent( ManyToMany.class ) ) {
- //useful for collection of embedded elements
- columns = Ejb3Column.buildColumnFromAnnotation(
- null, null, nullability, propertyHolder, inferredData, entityBinder.getSecondaryTables(), mappings
- );
- }
-
- if ( nullability == Nullability.FORCED_NOT_NULL ) {
- //force columns to not null
- for (Ejb3Column col : columns) {
- col.forceNotNull();
- }
- }
-
final XClass returnedClass = inferredData.getClassOrElement();
//prepare PropertyBinder
@@ -1839,7 +1759,22 @@
|| property.isAnnotationPresent( EmbeddedId.class )
|| returnedClass.isAnnotationPresent( Embeddable.class );
+ //FIXME do the overrideColumnFromMapsIdProperty here and force the idclass type to look like an @embedded
+ //Overrides from @MapsId if needed
+ boolean isOverridden = false;
+ if ( isId || propertyHolder.isOrWithinEmbeddedId() ) {
+ Ejb3Column[] oldColumns = columns;
+ columns = columnsBuilder.overrideColumnFromMapsIdProperty(isId);
+ isOverridden = oldColumns != columns;
+ }
if ( isComponent ) {
+ String referencedEntityName = null;
+ if (isOverridden) {
+ final PropertyData mapsIdProperty = BinderHelper.getPropertyAnnotatedWithMapsId(
+ isId, propertyHolder, property.getName(), mappings
+ );
+ referencedEntityName = mapsIdProperty.getClassOrElementName();
+ }
AccessType propertyAccessor = entityBinder.getPropertyAccessor( property );
propertyBinder = bindComponent(
inferredData,
@@ -1850,7 +1785,9 @@
mappings,
isComponentEmbedded,
isId,
- inheritanceStatePerClass
+ inheritanceStatePerClass,
+ referencedEntityName,
+ isOverridden ? (Ejb3JoinColumn[]) columns : null
);
}
else {
@@ -1870,16 +1807,6 @@
}
}
- //Override from @MapsId if needed
- if ( isId || propertyHolder.isOrWithinEmbeddedId() ) {
- columns = overrideColumnFromMapsIdProperty(
- isId ? "" : property.getName(), //@MapsId("") points to the id property
- columns,
- propertyHolder,
- entityBinder,
- mappings );
- }
-
propertyBinder.setLazy( lazy );
propertyBinder.setColumns( columns );
// if ( isIdentifierMapper ) {
@@ -1968,69 +1895,6 @@
);
}
- private static Ejb3JoinColumn[] buildDefaultJoinColumnsForXToOne(PropertyHolder propertyHolder, XProperty property, PropertyData inferredData, EntityBinder entityBinder, ExtendedMappings mappings) {
- Ejb3JoinColumn[] joinColumns;
- JoinTable joinTableAnn = propertyHolder.getJoinTable( property );
- if ( joinTableAnn != null ) {
- joinColumns = Ejb3JoinColumn.buildJoinColumns(
- joinTableAnn.inverseJoinColumns(), null, entityBinder.getSecondaryTables(),
- propertyHolder, inferredData.getPropertyName(), mappings
- );
- if ( StringHelper.isEmpty( joinTableAnn.name() ) ) {
- throw new AnnotationException(
- "JoinTable.name() on a @ToOne association has to be explicit: "
- + BinderHelper.getPath( propertyHolder, inferredData )
- );
- }
- }
- else {
- OneToOne oneToOneAnn = property.getAnnotation( OneToOne.class );
- String mappedBy = oneToOneAnn != null ?
- oneToOneAnn.mappedBy() :
- null;
- joinColumns = Ejb3JoinColumn.buildJoinColumns(
- ( JoinColumn[]) null,
- mappedBy, entityBinder.getSecondaryTables(),
- propertyHolder, inferredData.getPropertyName(), mappings
- );
- }
- return joinColumns;
- }
-
- private static Ejb3JoinColumn[] buildExplicitJoinColumns(PropertyHolder propertyHolder, XProperty property, PropertyData inferredData, EntityBinder entityBinder, ExtendedMappings mappings) {
- //process @JoinColumn(s) before @Column(s) to handle collection of entities properly
- Ejb3JoinColumn[] joinColumns = null;
- {
- JoinColumn[] anns = null;
-
- if ( property.isAnnotationPresent( JoinColumn.class ) ) {
- anns = new JoinColumn[] { property.getAnnotation( JoinColumn.class ) };
- }
- else if ( property.isAnnotationPresent( JoinColumns.class ) ) {
- JoinColumns ann = property.getAnnotation( JoinColumns.class );
- anns = ann.value();
- int length = anns.length;
- if ( length == 0 ) {
- throw new AnnotationException( "Cannot bind an empty @JoinColumns" );
- }
- }
- if ( anns != null ) {
- joinColumns = Ejb3JoinColumn.buildJoinColumns(
- anns, null, entityBinder.getSecondaryTables(),
- propertyHolder, inferredData.getPropertyName(), mappings
- );
- }
- else if ( property.isAnnotationPresent( JoinColumnsOrFormulas.class ) ) {
- JoinColumnsOrFormulas ann = property.getAnnotation( JoinColumnsOrFormulas.class );
- joinColumns = Ejb3JoinColumn.buildJoinColumnsOrFormulas(
- ann, null, entityBinder.getSecondaryTables(),
- propertyHolder, inferredData.getPropertyName(), mappings
- );
- }
- }
- return joinColumns;
- }
-
//TODO move that to collection binder?
private static void bindJoinedTableAssociation(
XProperty property, ExtendedMappings mappings, EntityBinder entityBinder,
@@ -2107,14 +1971,27 @@
boolean isIdentifierMapper,
ExtendedMappings mappings,
boolean isComponentEmbedded,
- boolean isId,
- Map<XClass, InheritanceState> inheritanceStatePerClass
- ) {
- Component comp = fillComponent(
- propertyHolder, inferredData, propertyAccessor, !isId, entityBinder,
- isComponentEmbedded, isIdentifierMapper,
- false, mappings, inheritanceStatePerClass
- );
+ boolean isId, //is a identifier
+ Map<XClass, InheritanceState> inheritanceStatePerClass,
+ String referencedEntityName, //is a component who is overridden by a @MapsId
+ Ejb3JoinColumn[] columns) {
+ Component comp;
+ if ( referencedEntityName != null ) {
+ comp = createComponent( propertyHolder, inferredData, isComponentEmbedded, isIdentifierMapper );
+ SecondPass sp = new CopyIdentifierComponentSecondPass(
+ comp,
+ referencedEntityName,
+ columns,
+ mappings);
+ mappings.addSecondPass( sp );
+ }
+ else {
+ comp = fillComponent(
+ propertyHolder, inferredData, propertyAccessor, !isId, entityBinder,
+ isComponentEmbedded, isIdentifierMapper,
+ false, mappings, inheritanceStatePerClass
+ );
+ }
if (isId) {
comp.setKey( true );
if ( propertyHolder.getPersistentClass().getIdentifier() != null ) {
@@ -2341,32 +2218,6 @@
}
}
- private static Ejb3Column[] overrideColumnFromMapsIdProperty(String propertyPath,
- Ejb3Column[] columns,
- PropertyHolder propertyHolder,
- EntityBinder entityBinder,
- ExtendedMappings mappings) {
- Ejb3Column[] result = columns;
- final XClass persistentXClass;
- try {
- persistentXClass = mappings.getReflectionManager()
- .classForName( propertyHolder.getPersistentClass().getClassName(), AnnotationBinder.class );
- }
- catch ( ClassNotFoundException e ) {
- throw new AssertionFailure( "PersistentClass name cannot be converted into a Class", e);
- }
- final PropertyData annotatedWithMapsId = mappings.getPropertyAnnotatedWithMapsId( persistentXClass, propertyPath );
- if ( annotatedWithMapsId != null ) {
- result = buildExplicitJoinColumns( propertyHolder, annotatedWithMapsId.getProperty(), annotatedWithMapsId, entityBinder, mappings );
- if (result == null) {
- result = buildDefaultJoinColumnsForXToOne( propertyHolder, annotatedWithMapsId.getProperty(), annotatedWithMapsId, entityBinder, mappings );
- throw new UnsupportedOperationException( "Implicit @JoinColumn is not supported on @MapsId properties: "
- + annotatedWithMapsId.getDeclaringClass() + " " + annotatedWithMapsId.getPropertyName() );
- }
- }
- return result;
- }
-
private static void setupComponentTuplizer(XProperty property, Component component) {
if ( property == null ) return;
if ( property.isAnnotationPresent( Tuplizers.class ) ) {
@@ -2459,9 +2310,7 @@
propertyBinder.setCascade( cascadeStrategy );
propertyBinder.setProperty( property );
propertyBinder.setXToMany( true );
- Property prop = propertyBinder.makePropertyAndBind();
- //composite FK columns are in the same table so its OK
- //propertyHolder.addProperty( prop, columns, inferredData.getDeclaringClass() );
+ propertyBinder.makePropertyAndBind();
}
protected static void defineFetchingStrategy(ToOne toOne, XProperty property) {
@@ -2768,14 +2617,17 @@
* @param orderedClasses Order list of all annotated entities and their mapped superclasses
* @return A map of {@code InheritanceState}s keyed against their {@code XClass}.
*/
- public static Map<XClass, InheritanceState> buildInheritanceStates(List<XClass> orderedClasses) {
+ public static Map<XClass, InheritanceState> buildInheritanceStates(
+ List<XClass> orderedClasses,
+ ExtendedMappings mappings) {
+ ReflectionManager reflectionManager = mappings.getReflectionManager();
Map<XClass, InheritanceState> inheritanceStatePerClass = new HashMap<XClass, InheritanceState>(
orderedClasses.size()
);
for (XClass clazz : orderedClasses) {
InheritanceState superclassState = InheritanceState.getSuperclassInheritanceState(
clazz, inheritanceStatePerClass );
- InheritanceState state = new InheritanceState( clazz );
+ InheritanceState state = new InheritanceState( clazz, inheritanceStatePerClass, mappings );
if ( superclassState != null ) {
//the classes are ordered thus preventing an NPE
//FIXME if an entity has subclasses annotated @MappedSperclass wo sub @Entity this is wrong
@@ -2827,4 +2679,5 @@
}
return false;
}
+
}
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationConfiguration.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationConfiguration.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/AnnotationConfiguration.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -359,35 +359,11 @@
caches.clear();
try {
inSecondPass = true;
- Iterator iter = secondPasses.iterator();
- while ( iter.hasNext() ) {
- SecondPass sp = ( SecondPass ) iter.next();
- //do the second pass of simple value types first and remove them
- if ( sp instanceof SetSimpleValueTypeSecondPass ) {
- sp.doSecondPass( classes );
- iter.remove();
- }
- }
+ processSecondPassesOfType( SetSimpleValueTypeSecondPass.class );
+ processSecondPassesOfType( CopyIdentifierComponentSecondPass.class );
processFkSecondPassInOrder();
- iter = secondPasses.iterator();
- while ( iter.hasNext() ) {
- SecondPass sp = ( SecondPass ) iter.next();
- //do the second pass of fk before the others and remove them
- if ( sp instanceof CreateKeySecondPass ) {
- sp.doSecondPass( classes );
- iter.remove();
- }
- }
-
- iter = secondPasses.iterator();
- while ( iter.hasNext() ) {
- SecondPass sp = ( SecondPass ) iter.next();
- //do the SecondaryTable second pass before any association because associations can be built on joins
- if ( sp instanceof SecondaryTableSecondPass ) {
- sp.doSecondPass( classes );
- iter.remove();
- }
- }
+ processSecondPassesOfType( CreateKeySecondPass.class );
+ processSecondPassesOfType( SecondaryTableSecondPass.class );
super.secondPassCompile();
inSecondPass = false;
}
@@ -413,6 +389,18 @@
applyConstraintsToDDL();
}
+ private void processSecondPassesOfType(Class<? extends SecondPass> type) {
+ Iterator iter = secondPasses.iterator();
+ while ( iter.hasNext() ) {
+ SecondPass sp = ( SecondPass ) iter.next();
+ //do the second pass of simple value types first and remove them
+ if ( type.isInstance( sp ) ) {
+ sp.doSecondPass( classes );
+ iter.remove();
+ }
+ }
+ }
+
private void applyConstraintsToDDL() {
boolean applyOnDdl = getProperties().getProperty(
"hibernate.validator.apply_to_ddl",
@@ -623,11 +611,12 @@
log.debug( "Process annotated classes" );
//bind classes in the correct order calculating some inheritance state
List<XClass> orderedClasses = orderAndFillHierarchy( annotatedClasses );
+ ExtendedMappings mappings = createExtendedMappings();
Map<XClass, InheritanceState> inheritanceStatePerClass = AnnotationBinder.buildInheritanceStates(
- orderedClasses
+ orderedClasses, mappings
);
- ExtendedMappings mappings = createExtendedMappings();
+
for ( XClass clazz : orderedClasses ) {
//todo use the same extended mapping
AnnotationBinder.bindClass( clazz, inheritanceStatePerClass, mappings );
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/BinderHelper.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/BinderHelper.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/BinderHelper.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -652,4 +652,17 @@
return StringHelper.qualify( holder.getPath(), property.getPropertyName() );
}
+ static PropertyData getPropertyAnnotatedWithMapsId(boolean isId, PropertyHolder propertyHolder, String propertyName, ExtendedMappings mappings) {
+ final XClass persistentXClass;
+ try {
+ persistentXClass = mappings.getReflectionManager()
+ .classForName( propertyHolder.getPersistentClass().getClassName(), AnnotationBinder.class );
+ }
+ catch ( ClassNotFoundException e ) {
+ throw new AssertionFailure( "PersistentClass name cannot be converted into a Class", e);
+ }
+ String propertyPath = isId ? "" : propertyName;
+ final PropertyData annotatedWithMapsId = mappings.getPropertyAnnotatedWithMapsId( persistentXClass, propertyPath );
+ return annotatedWithMapsId;
+ }
}
Added: core/trunk/annotations/src/main/java/org/hibernate/cfg/ColumnsBuilder.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/ColumnsBuilder.java (rev 0)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/ColumnsBuilder.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -0,0 +1,199 @@
+package org.hibernate.cfg;
+
+import javax.persistence.Column;
+import javax.persistence.ElementCollection;
+import javax.persistence.JoinColumn;
+import javax.persistence.JoinColumns;
+import javax.persistence.JoinTable;
+import javax.persistence.ManyToMany;
+import javax.persistence.ManyToOne;
+import javax.persistence.OneToMany;
+import javax.persistence.OneToOne;
+
+import org.hibernate.AnnotationException;
+import org.hibernate.AssertionFailure;
+import org.hibernate.annotations.CollectionOfElements;
+import org.hibernate.annotations.Columns;
+import org.hibernate.annotations.Formula;
+import org.hibernate.annotations.JoinColumnsOrFormulas;
+import org.hibernate.annotations.common.reflection.XClass;
+import org.hibernate.annotations.common.reflection.XProperty;
+import org.hibernate.cfg.annotations.EntityBinder;
+import org.hibernate.cfg.annotations.Nullability;
+import org.hibernate.util.StringHelper;
+
+/**
+ * Do the initial discovery of columns metadata and apply defaults.
+ * Also hosts some convinient methods related to column processing
+ *
+ * @author Emmanuel Bernard
+ */
+class ColumnsBuilder {
+ private PropertyHolder propertyHolder;
+ private Nullability nullability;
+ private XProperty property;
+ private PropertyData inferredData;
+ private EntityBinder entityBinder;
+ private ExtendedMappings mappings;
+ private Ejb3Column[] columns;
+ private Ejb3JoinColumn[] joinColumns;
+
+ public ColumnsBuilder(PropertyHolder propertyHolder, Nullability nullability, XProperty property, PropertyData inferredData, EntityBinder entityBinder, ExtendedMappings mappings) {
+ this.propertyHolder = propertyHolder;
+ this.nullability = nullability;
+ this.property = property;
+ this.inferredData = inferredData;
+ this.entityBinder = entityBinder;
+ this.mappings = mappings;
+ }
+
+ public Ejb3Column[] getColumns() {
+ return columns;
+ }
+
+ public Ejb3JoinColumn[] getJoinColumns() {
+ return joinColumns;
+ }
+
+ public ColumnsBuilder extractMetadata() {
+ columns = null;
+ joinColumns = buildExplicitJoinColumns(property, inferredData);
+
+
+ if ( property.isAnnotationPresent( Column.class ) || property.isAnnotationPresent( Formula.class ) ) {
+ Column ann = property.getAnnotation( Column.class );
+ Formula formulaAnn = property.getAnnotation( Formula.class );
+ columns = Ejb3Column.buildColumnFromAnnotation(
+ new Column[] { ann }, formulaAnn, nullability, propertyHolder, inferredData,
+ entityBinder.getSecondaryTables(), mappings
+ );
+ }
+ else if ( property.isAnnotationPresent( Columns.class ) ) {
+ Columns anns = property.getAnnotation( Columns.class );
+ columns = Ejb3Column.buildColumnFromAnnotation(
+ anns.columns(), null,
+ nullability, propertyHolder, inferredData, entityBinder.getSecondaryTables(),
+ mappings
+ );
+ }
+
+ //set default values if needed
+ if ( joinColumns == null &&
+ ( property.isAnnotationPresent( ManyToOne.class )
+ || property.isAnnotationPresent( OneToOne.class ) )
+ ) {
+ joinColumns = buildDefaultJoinColumnsForXToOne(property, inferredData);
+ }
+ else if ( joinColumns == null &&
+ ( property.isAnnotationPresent( OneToMany.class )
+ || property.isAnnotationPresent( CollectionOfElements.class ) //legacy Hibernate
+ || property.isAnnotationPresent( ElementCollection.class )
+ ) ) {
+ OneToMany oneToMany = property.getAnnotation( OneToMany.class );
+ String mappedBy = oneToMany != null ?
+ oneToMany.mappedBy() :
+ "";
+ joinColumns = Ejb3JoinColumn.buildJoinColumns(
+ null,
+ mappedBy, entityBinder.getSecondaryTables(),
+ propertyHolder, inferredData.getPropertyName(), mappings
+ );
+ }
+ else if ( joinColumns == null && property.isAnnotationPresent( org.hibernate.annotations.Any.class ) ) {
+ throw new AnnotationException( "@Any requires an explicit @JoinColumn(s): "
+ + BinderHelper.getPath( propertyHolder, inferredData ) );
+ }
+ if ( columns == null && !property.isAnnotationPresent( ManyToMany.class ) ) {
+ //useful for collection of embedded elements
+ columns = Ejb3Column.buildColumnFromAnnotation(
+ null, null,
+ nullability, propertyHolder, inferredData, entityBinder.getSecondaryTables(), mappings
+ );
+ }
+
+ if ( nullability == Nullability.FORCED_NOT_NULL ) {
+ //force columns to not null
+ for (Ejb3Column col : columns ) {
+ col.forceNotNull();
+ }
+ }
+ return this;
+ }
+
+ Ejb3JoinColumn[] buildDefaultJoinColumnsForXToOne(XProperty property, PropertyData inferredData) {
+ Ejb3JoinColumn[] joinColumns;
+ JoinTable joinTableAnn = propertyHolder.getJoinTable( property );
+ if ( joinTableAnn != null ) {
+ joinColumns = Ejb3JoinColumn.buildJoinColumns(
+ joinTableAnn.inverseJoinColumns(), null, entityBinder.getSecondaryTables(),
+ propertyHolder, inferredData.getPropertyName(), mappings
+ );
+ if ( StringHelper.isEmpty( joinTableAnn.name() ) ) {
+ throw new AnnotationException(
+ "JoinTable.name() on a @ToOne association has to be explicit: "
+ + BinderHelper.getPath( propertyHolder, inferredData )
+ );
+ }
+ }
+ else {
+ OneToOne oneToOneAnn = property.getAnnotation( OneToOne.class );
+ String mappedBy = oneToOneAnn != null ?
+ oneToOneAnn.mappedBy() :
+ null;
+ joinColumns = Ejb3JoinColumn.buildJoinColumns(
+ null,
+ mappedBy, entityBinder.getSecondaryTables(),
+ propertyHolder, inferredData.getPropertyName(), mappings
+ );
+ }
+ return joinColumns;
+ }
+
+ Ejb3JoinColumn[] buildExplicitJoinColumns(XProperty property, PropertyData inferredData) {
+ //process @JoinColumn(s) before @Column(s) to handle collection of entities properly
+ Ejb3JoinColumn[] joinColumns = null;
+ {
+ JoinColumn[] anns = null;
+
+ if ( property.isAnnotationPresent( JoinColumn.class ) ) {
+ anns = new JoinColumn[] { property.getAnnotation( JoinColumn.class ) };
+ }
+ else if ( property.isAnnotationPresent( JoinColumns.class ) ) {
+ JoinColumns ann = property.getAnnotation( JoinColumns.class );
+ anns = ann.value();
+ int length = anns.length;
+ if ( length == 0 ) {
+ throw new AnnotationException( "Cannot bind an empty @JoinColumns" );
+ }
+ }
+ if ( anns != null ) {
+ joinColumns = Ejb3JoinColumn.buildJoinColumns(
+ anns, null, entityBinder.getSecondaryTables(),
+ propertyHolder, inferredData.getPropertyName(), mappings
+ );
+ }
+ else if ( property.isAnnotationPresent( JoinColumnsOrFormulas.class ) ) {
+ JoinColumnsOrFormulas ann = property.getAnnotation( JoinColumnsOrFormulas.class );
+ joinColumns = Ejb3JoinColumn.buildJoinColumnsOrFormulas(
+ ann, null, entityBinder.getSecondaryTables(),
+ propertyHolder, inferredData.getPropertyName(), mappings
+ );
+ }
+ }
+ return joinColumns;
+ }
+
+ Ejb3Column[] overrideColumnFromMapsIdProperty(boolean isId) {
+ Ejb3Column[] result = columns;
+ final PropertyData annotatedWithMapsId = BinderHelper.getPropertyAnnotatedWithMapsId( isId, propertyHolder, property.getName(), mappings );
+ if ( annotatedWithMapsId != null ) {
+ result = buildExplicitJoinColumns( annotatedWithMapsId.getProperty(), annotatedWithMapsId );
+ if (result == null) {
+ //result = buildDefaultJoinColumnsForXToOne( annotatedWithMapsId.getProperty(), annotatedWithMapsId);
+ throw new UnsupportedOperationException( "Implicit @JoinColumn is not supported on @MapsId properties: "
+ + annotatedWithMapsId.getDeclaringClass() + " " + annotatedWithMapsId.getPropertyName() );
+ }
+ }
+ return result;
+ }
+}
Added: core/trunk/annotations/src/main/java/org/hibernate/cfg/CopyIdentifierComponentSecondPass.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/CopyIdentifierComponentSecondPass.java (rev 0)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/CopyIdentifierComponentSecondPass.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -0,0 +1,118 @@
+package org.hibernate.cfg;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+import org.hibernate.AnnotationException;
+import org.hibernate.AssertionFailure;
+import org.hibernate.MappingException;
+import org.hibernate.mapping.Column;
+import org.hibernate.mapping.Component;
+import org.hibernate.mapping.PersistentClass;
+import org.hibernate.mapping.Property;
+import org.hibernate.mapping.SimpleValue;
+import org.hibernate.mapping.Value;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class CopyIdentifierComponentSecondPass implements SecondPass {
+ private final String referencedEntityName;
+ private final Component component;
+ private final ExtendedMappings mappings;
+ private final Ejb3JoinColumn[] joinColumns;
+
+ public CopyIdentifierComponentSecondPass(
+ Component comp, String referencedEntityName, Ejb3JoinColumn[] joinColumns, ExtendedMappings mappings) {
+ this.component = comp;
+ this.referencedEntityName = referencedEntityName;
+ this.mappings = mappings;
+ this.joinColumns = joinColumns;
+ }
+
+ //FIXME better error names
+ public void doSecondPass(Map persistentClasses) throws MappingException {
+ PersistentClass referencedPersistentClass = (PersistentClass) persistentClasses.get( referencedEntityName );
+ if ( referencedPersistentClass == null ) {
+ throw new AnnotationException(
+ "Unknown entity name: " + referencedEntityName
+ );
+ };
+ if ( ! ( referencedPersistentClass.getIdentifier() instanceof Component ) ) {
+ throw new AssertionFailure( "Unexpected identifier type on the referenced entity when mapping a @MapsId: "
+ + referencedEntityName);
+ }
+ Component referencedComponent = (Component) referencedPersistentClass.getIdentifier();
+ Iterator<Property> properties = referencedComponent.getPropertyIterator();
+
+ //prepare column name structure
+ boolean isExplicitReference = true;
+ Map<String, Ejb3JoinColumn> columnByReferencedName = new HashMap<String, Ejb3JoinColumn>(joinColumns.length);
+ for (Ejb3JoinColumn joinColumn : joinColumns) {
+ final String referencedColumnName = joinColumn.getReferencedColumn();
+ if ( BinderHelper.isDefault( referencedColumnName ) ) {
+ break;
+ }
+ columnByReferencedName.put( referencedColumnName, joinColumn );
+ }
+ //try default column orientation
+ int index = 0;
+ if ( columnByReferencedName.isEmpty() ) {
+ isExplicitReference = false;
+ for (Ejb3JoinColumn joinColumn : joinColumns) {
+ columnByReferencedName.put( "" + index, joinColumn );
+ index++;
+ }
+ index = 0;
+ }
+
+ while ( properties.hasNext() ) {
+ Property referencedProperty = properties.next();
+ if ( referencedProperty.isComposite() ) {
+ throw new AssertionFailure( "Unexpected nested component on the referenced entity when mapping a @MapsId: "
+ + referencedEntityName);
+ }
+ else {
+ Property property = new Property();
+ property.setName( referencedProperty.getName() );
+ property.setNodeName( referencedProperty.getNodeName() );
+ //FIXME set optional?
+ //property.setOptional( property.isOptional() );
+ property.setPersistentClass( component.getOwner() );
+ property.setPropertyAccessorName( referencedProperty.getPropertyAccessorName() );
+ SimpleValue value = new SimpleValue( component.getTable() );
+ property.setValue( value );
+ final SimpleValue referencedValue = (SimpleValue) referencedProperty.getValue();
+ value.setTypeName( referencedValue.getTypeName() );
+ value.setTypeParameters( referencedValue.getTypeParameters() );
+ final Iterator<Column> columns = referencedValue.getColumnIterator();
+ //FIXME take care of Formula
+ while ( columns.hasNext() ) {
+ Column column = columns.next();
+ final Ejb3JoinColumn joinColumn;
+ String logicalColumnName = null;
+ if ( isExplicitReference ) {
+ final String columnName = column.getName();
+ logicalColumnName = mappings.getLogicalColumnName( columnName, referencedPersistentClass.getTable() );
+ joinColumn = columnByReferencedName.get( logicalColumnName );
+ }
+ else {
+ joinColumn = columnByReferencedName.get( "" + index );
+ index++;
+ }
+ if (joinColumn == null) {
+ throw new AnnotationException(
+ isExplicitReference ?
+ "Unable to find column reference in the @MapsId mapping: " + logicalColumnName :
+ "Implicit column reference in the @MapsId mapping fails, try to use explicit referenceColumnNames: " + referencedEntityName
+ );
+ }
+ value.addColumn( new Column( joinColumn.getName() ) );
+ column.setValue( value );
+ }
+ component.addProperty( property );
+ }
+ }
+ }
+}
Modified: core/trunk/annotations/src/main/java/org/hibernate/cfg/InheritanceState.java
===================================================================
--- core/trunk/annotations/src/main/java/org/hibernate/cfg/InheritanceState.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/main/java/org/hibernate/cfg/InheritanceState.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -23,13 +23,24 @@
*/
package org.hibernate.cfg;
+import java.util.ArrayList;
+import java.util.List;
import java.util.Map;
+import javax.persistence.EmbeddedId;
+import javax.persistence.Entity;
+import javax.persistence.Id;
+import javax.persistence.IdClass;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.MappedSuperclass;
+import org.hibernate.AnnotationException;
+import org.hibernate.annotations.common.reflection.ReflectionManager;
import org.hibernate.annotations.common.reflection.XAnnotatedElement;
import org.hibernate.annotations.common.reflection.XClass;
+import org.hibernate.annotations.common.reflection.XProperty;
+import org.hibernate.cfg.annotations.EntityBinder;
+import org.hibernate.mapping.PersistentClass;
/**
* Some extra data to the inheritance position of a class.
@@ -37,12 +48,8 @@
* @author Emmanuel Bernard
*/
public class InheritanceState {
- public InheritanceState(XClass clazz) {
- this.setClazz( clazz );
- extractInheritanceType();
- }
-
private XClass clazz;
+ private XClass identifierType;
/**
* Has sibling (either mappedsuperclass entity)
@@ -55,7 +62,22 @@
private boolean hasParents = false;
private InheritanceType type;
private boolean isEmbeddableSuperclass = false;
+ private Map<XClass, InheritanceState> inheritanceStatePerClass;
+ private List<XClass> classesToProcessForMappedSuperclass = new ArrayList<XClass>();
+ private ExtendedMappings mappings;
+ private AccessType accessType;
+ private ElementsToProcess elementsToProcess;
+ public InheritanceState(XClass clazz,
+ Map<XClass, InheritanceState> inheritanceStatePerClass,
+ ExtendedMappings mappings) {
+ this.setClazz( clazz );
+ this.mappings = mappings;
+ this.inheritanceStatePerClass = inheritanceStatePerClass;
+ this.identifierType = mappings.getReflectionManager().toXClass( void.class ); //not initialized
+ extractInheritanceType();
+ }
+
private void extractInheritanceType() {
XAnnotatedElement element = getClazz();
Inheritance inhAnn = element.getAnnotation( Inheritance.class );
@@ -144,4 +166,170 @@
public void setEmbeddableSuperclass(boolean embeddableSuperclass) {
isEmbeddableSuperclass = embeddableSuperclass;
}
+
+ public XClass getIdentifierTypeIfComponent() {
+ final ReflectionManager reflectionManager = mappings.getReflectionManager();
+ if ( reflectionManager.equals( identifierType, void.class ) ) {
+ IdClass idClass = clazz.getAnnotation( IdClass.class );
+ if (idClass != null) {
+ identifierType = reflectionManager.toXClass( idClass.value() );
+ }
+ else {
+ //find @EmbeddedId
+ getElementsToProcess();
+ }
+ }
+ return identifierType;
+ }
+
+ void postProcess(PersistentClass persistenceClass, EntityBinder entityBinder) {
+ //make sure we run elements to process
+ getElementsToProcess();
+ addMappedSuperClassInMetadata(persistenceClass);
+ entityBinder.setPropertyAccessType( accessType );
+ }
+
+ public XClass getClassWithIdClass(boolean evenIfSubclass) {
+ if ( !evenIfSubclass && hasParents() ) {
+ return null;
+ }
+ if ( clazz.isAnnotationPresent( IdClass.class ) ) {
+ return clazz;
+ }
+ else {
+ InheritanceState state = InheritanceState.getSuperclassInheritanceState( clazz, inheritanceStatePerClass );
+ if (state != null){
+ return state.getClassWithIdClass(true);
+ }
+ else {
+ return null;
+ }
+
+ }
+ }
+
+ /*
+ * Get the annotated elements, guessing the access type from @Id or @EmbeddedId presence.
+ * Change EntityBinder by side effect
+ */
+ public ElementsToProcess getElementsToProcess() {
+ if (elementsToProcess == null) {
+ InheritanceState inheritanceState = inheritanceStatePerClass.get( clazz );
+ assert !inheritanceState.isEmbeddableSuperclass();
+
+
+ getMappedSuperclassesTillNextEntityOrdered();
+
+ accessType = determineDefaultAccessType( );
+
+ List<PropertyData> elements = new ArrayList<PropertyData>();
+ int deep = classesToProcessForMappedSuperclass.size();
+ int idPropertyCount = 0;
+
+ for ( int index = 0; index < deep; index++ ) {
+ PropertyContainer propertyContainer = new PropertyContainer( classesToProcessForMappedSuperclass.get( index ), clazz );
+ int currentIdPropertyCount = AnnotationBinder.addElementsOfClass( elements, accessType, propertyContainer, mappings );
+ idPropertyCount += currentIdPropertyCount;
+ }
+
+ if ( idPropertyCount == 0 && !inheritanceState.hasParents() ) {
+ throw new AnnotationException( "No identifier specified for entity: " + clazz.getName() );
+ }
+ elementsToProcess = new ElementsToProcess( elements, idPropertyCount);
+ }
+ return elementsToProcess;
+ }
+
+ private AccessType determineDefaultAccessType() {
+ XClass xclass = clazz;
+ while ( xclass != null && !Object.class.getName().equals( xclass.getName() ) ) {
+ if ( xclass.isAnnotationPresent( Entity.class ) || xclass.isAnnotationPresent( MappedSuperclass.class ) ) {
+ for ( XProperty prop : xclass.getDeclaredProperties( AccessType.PROPERTY.getType() ) ) {
+ final boolean isEmbeddedId = prop.isAnnotationPresent( EmbeddedId.class );
+ if ( prop.isAnnotationPresent( Id.class ) || isEmbeddedId ) {
+ if (isEmbeddedId) {
+ identifierType = prop.getClassOrElementClass();
+ }
+ return AccessType.PROPERTY;
+ }
+ }
+ for ( XProperty prop : xclass.getDeclaredProperties( AccessType.FIELD.getType() ) ) {
+ final boolean isEmbeddedId = prop.isAnnotationPresent( EmbeddedId.class );
+ if ( prop.isAnnotationPresent( Id.class ) || isEmbeddedId ) {
+ if ( isEmbeddedId ) {
+ identifierType = prop.getClassOrElementClass();
+ }
+ return AccessType.FIELD;
+ }
+ }
+ }
+ xclass = xclass.getSuperclass();
+ }
+ throw new AnnotationException( "No identifier specified for entity: " + clazz.getName() );
+ }
+
+ private void getMappedSuperclassesTillNextEntityOrdered() {
+
+ //ordered to allow proper messages on properties subclassing
+ XClass currentClassInHierarchy = clazz;
+ InheritanceState superclassState;
+ do {
+ classesToProcessForMappedSuperclass.add( 0, currentClassInHierarchy );
+ XClass superClass = currentClassInHierarchy;
+ do {
+ superClass = superClass.getSuperclass();
+ superclassState = inheritanceStatePerClass.get( superClass );
+ }
+ while ( superClass != null
+ && !mappings.getReflectionManager().equals( superClass, Object.class ) && superclassState == null );
+
+ currentClassInHierarchy = superClass;
+ }
+ while ( superclassState != null && superclassState.isEmbeddableSuperclass() );
+ }
+
+ private void addMappedSuperClassInMetadata(PersistentClass persistentClass) {
+ //add @MappedSuperclass in the metadata
+ // classes from 0 to n-1 are @MappedSuperclass and should be linked
+ org.hibernate.mapping.MappedSuperclass mappedSuperclass = null;
+ final InheritanceState superEntityState =
+ InheritanceState.getInheritanceStateOfSuperEntity( clazz, inheritanceStatePerClass );
+ PersistentClass superEntity =
+ superEntityState != null ?
+ mappings.getClass( superEntityState.getClazz().getName() ) :
+ null;
+ final int lastMappedSuperclass = classesToProcessForMappedSuperclass.size() - 1;
+ for ( int index = 0 ; index < lastMappedSuperclass ; index++ ) {
+ org.hibernate.mapping.MappedSuperclass parentSuperclass = mappedSuperclass;
+ final Class<?> type = mappings.getReflectionManager().toClass( classesToProcessForMappedSuperclass.get( index ) );
+ //add MAppedSuperclass if not already there
+ mappedSuperclass = mappings.getMappedSuperclass( type );
+ if (mappedSuperclass == null) {
+ mappedSuperclass = new org.hibernate.mapping.MappedSuperclass(parentSuperclass, superEntity );
+ mappedSuperclass.setMappedClass( type );
+ mappings.addMappedSuperclass( type, mappedSuperclass );
+ }
+ }
+ if (mappedSuperclass != null) {
+ persistentClass.setSuperMappedSuperclass(mappedSuperclass);
+ }
+ }
+
+ static final class ElementsToProcess {
+ private final List<PropertyData> properties;
+ private final int idPropertyCount;
+
+ public List<PropertyData> getElements() {
+ return properties;
+ }
+
+ public int getIdPropertyCount() {
+ return idPropertyCount;
+ }
+
+ private ElementsToProcess(List<PropertyData> properties, int idPropertyCount) {
+ this.properties = properties;
+ this.idPropertyCount = idPropertyCount;
+ }
+ }
}
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/b/DerivedIdentitySimpleParentEmbeddedIdDepTest.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -7,7 +7,8 @@
/**
* @author Emmanuel Bernard
*/
-public class DerivedIdentitySimpleParentEmbeddedIdDepTest extends TestCase {
+public class
+ DerivedIdentitySimpleParentEmbeddedIdDepTest extends TestCase {
public void testManyToOne() throws Exception {
assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK", getCfg() ) );
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/c/Dependent.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/c/Dependent.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e1/c/Dependent.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -17,7 +17,6 @@
@Id
- //@JoinColumn(name = "FK")
// id attribute mapped by join column default
@ManyToOne
Employee emp;
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DependentId.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DependentId.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DependentId.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -2,6 +2,7 @@
import java.io.Serializable;
import javax.persistence.Embeddable;
+import javax.persistence.Embedded;
/**
* @author Emmanuel Bernard
Added: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java (rev 0)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/DerivedIdentityIdClassParentEmbeddedIdDepTest.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -0,0 +1,49 @@
+package org.hibernate.test.annotations.derivedidentities.e2.b;
+
+import org.hibernate.Session;
+import org.hibernate.test.annotations.TestCase;
+import org.hibernate.test.util.SchemaUtil;
+
+/**
+ * @author Emmanuel Bernard
+ */
+public class DerivedIdentityIdClassParentEmbeddedIdDepTest extends TestCase {
+
+ public void testManyToOne() throws Exception {
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK1", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "FK2", getCfg() ) );
+ assertTrue( SchemaUtil.isColumnPresent( "Dependent", "name", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "Dependent", "firstName", getCfg() ) );
+ assertTrue( ! SchemaUtil.isColumnPresent( "Dependent", "lastName", getCfg() ) );
+ Employee e = new Employee();
+ e.firstName = "Emmanuel";
+ e.lastName = "Bernard";
+ Session s = openSession( );
+ s.getTransaction().begin();
+ s.persist( e );
+ Dependent d = new Dependent();
+ d.emp = e;
+ d.id = new DependentId();
+ d.id.name = "Doggy";
+ d.id.empPK = new EmployeeId();
+ d.id.empPK.firstName = e.firstName; //FIXME not needed when foreign is enabled
+ d.id.empPK.lastName = e.lastName; //FIXME not needed when foreign is enabled
+ s.persist( d );
+ s.flush();
+ s.clear();
+ d = (Dependent) s.get( Dependent.class, d.id );
+ assertNotNull( d.emp );
+ assertEquals( e.firstName, d.emp.firstName );
+ s.getTransaction().rollback();
+ s.close();
+ }
+
+
+ @Override
+ protected Class<?>[] getAnnotatedClasses() {
+ return new Class<?>[] {
+ Dependent.class,
+ Employee.class
+ };
+ }
+}
Modified: core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/EmployeeId.java
===================================================================
--- core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/EmployeeId.java 2010-01-26 12:19:38 UTC (rev 18624)
+++ core/trunk/annotations/src/test/java/org/hibernate/test/annotations/derivedidentities/e2/b/EmployeeId.java 2010-01-26 12:57:01 UTC (rev 18625)
@@ -1,9 +1,13 @@
package org.hibernate.test.annotations.derivedidentities.e2.b;
+import java.io.Serializable;
+import javax.persistence.Embeddable;
+
/**
* @author Emmanuel Bernard
*/
-public class EmployeeId {
+@Embeddable
+public class EmployeeId implements Serializable {
String firstName;
String lastName;
}
\ No newline at end of file
15 years