HHH-7048: Moved logic in resolvers to Binder and changed Binder.processMappings to receive all entity hierarchies at once to enable one-pass resolution of all entities and attributes.
This commit is contained in:
parent
50166f79bc
commit
3e96b29a3a
|
@ -24,12 +24,8 @@
|
|||
package org.hibernate.metamodel.internal;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
import org.hibernate.AssertionFailure;
|
||||
import org.hibernate.DuplicateMappingException;
|
||||
import org.hibernate.MappingException;
|
||||
|
@ -48,10 +44,7 @@ import org.hibernate.internal.util.Value;
|
|||
import org.hibernate.metamodel.MetadataSourceProcessingOrder;
|
||||
import org.hibernate.metamodel.MetadataSources;
|
||||
import org.hibernate.metamodel.SessionFactoryBuilder;
|
||||
import org.hibernate.metamodel.internal.source.AssociationResolver;
|
||||
import org.hibernate.metamodel.internal.source.Binder;
|
||||
import org.hibernate.metamodel.internal.source.HibernateTypeResolver;
|
||||
import org.hibernate.metamodel.internal.source.IdentifierGeneratorResolver;
|
||||
import org.hibernate.metamodel.internal.source.annotations.AnnotationMetadataSourceProcessorImpl;
|
||||
import org.hibernate.metamodel.internal.source.hbm.HbmMetadataSourceProcessorImpl;
|
||||
import org.hibernate.metamodel.spi.MetadataSourceProcessor;
|
||||
|
@ -64,7 +57,6 @@ import org.hibernate.metamodel.spi.binding.TypeDefinition;
|
|||
import org.hibernate.metamodel.spi.domain.BasicType;
|
||||
import org.hibernate.metamodel.spi.domain.Type;
|
||||
import org.hibernate.metamodel.spi.relational.Database;
|
||||
import org.hibernate.metamodel.spi.source.EntityHierarchy;
|
||||
import org.hibernate.metamodel.spi.source.FilterDefinitionSource;
|
||||
import org.hibernate.metamodel.spi.source.MappingDefaults;
|
||||
import org.hibernate.metamodel.spi.source.MetaAttributeContext;
|
||||
|
@ -74,6 +66,7 @@ import org.hibernate.persister.spi.PersisterClassResolver;
|
|||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.service.classloading.spi.ClassLoaderService;
|
||||
import org.hibernate.type.TypeResolver;
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
/**
|
||||
* Container for configuration data collected during binding the metamodel.
|
||||
|
@ -161,18 +154,9 @@ public class MetadataImpl implements MetadataImplementor, Serializable {
|
|||
|
||||
processTypeDefinitions( metadataSourceProcessors );
|
||||
processFilterDefinitions( metadataSourceProcessors );
|
||||
|
||||
processIdentifierGenerators( metadataSourceProcessors );
|
||||
|
||||
processMappings( metadataSourceProcessors );
|
||||
|
||||
bindMappingDependentMetadata( metadataSourceProcessors );
|
||||
|
||||
// todo : remove this by coordinated ordering of entity processing
|
||||
new AssociationResolver( this ).resolve();
|
||||
new HibernateTypeResolver( this ).resolve();
|
||||
// IdentifierGeneratorResolver.resolve() must execute after AttributeTypeResolver.resolve()
|
||||
new IdentifierGeneratorResolver( this ).resolve();
|
||||
}
|
||||
|
||||
|
||||
|
@ -254,20 +238,11 @@ public class MetadataImpl implements MetadataImplementor, Serializable {
|
|||
}
|
||||
|
||||
private void processMappings(MetadataSourceProcessor[] metadataSourceProcessors) {
|
||||
final ArrayList<String> processedEntityNames = new ArrayList<String>();
|
||||
final Binder binder = new Binder( this, processedEntityNames );
|
||||
for ( MetadataSourceProcessor processor : metadataSourceProcessors ) {
|
||||
for ( EntityHierarchy entityHierarchy : processor.extractEntityHierarchies() ) {
|
||||
binder.processEntityHierarchy( entityHierarchy );
|
||||
}
|
||||
}
|
||||
final Binder binder = new Binder( this );
|
||||
for ( MetadataSourceProcessor processor : metadataSourceProcessors )
|
||||
binder.processEntityHierarchies( processor.extractEntityHierarchies() );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
private void bindMappingDependentMetadata(MetadataSourceProcessor[] metadataSourceProcessors) {
|
||||
for ( MetadataSourceProcessor metadataSourceProcessor : metadataSourceProcessors ) {
|
||||
metadataSourceProcessor.processMappingDependentMetadata();
|
||||
|
|
|
@ -33,12 +33,16 @@ import java.util.HashMap;
|
|||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import java.util.Properties;
|
||||
import org.hibernate.AssertionFailure;
|
||||
import org.hibernate.EntityMode;
|
||||
import org.hibernate.TruthValue;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.NamingStrategy;
|
||||
import org.hibernate.cfg.NotYetImplementedException;
|
||||
import org.hibernate.cfg.ObjectNameNormalizer;
|
||||
import org.hibernate.id.IdentifierGenerator;
|
||||
import org.hibernate.id.PersistentIdentifierGenerator;
|
||||
import org.hibernate.internal.util.ReflectHelper;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
import org.hibernate.internal.util.beans.BeanInfoHelper;
|
||||
|
@ -48,7 +52,6 @@ import org.hibernate.metamodel.spi.binding.AttributeBinding;
|
|||
import org.hibernate.metamodel.spi.binding.AttributeBindingContainer;
|
||||
import org.hibernate.metamodel.spi.binding.BasicAttributeBinding;
|
||||
import org.hibernate.metamodel.spi.binding.BasicPluralAttributeElementBinding;
|
||||
import org.hibernate.metamodel.spi.binding.CollectionLaziness;
|
||||
import org.hibernate.metamodel.spi.binding.ComponentAttributeBinding;
|
||||
import org.hibernate.metamodel.spi.binding.EntityBinding;
|
||||
import org.hibernate.metamodel.spi.binding.EntityDiscriminator;
|
||||
|
@ -59,6 +62,7 @@ import org.hibernate.metamodel.spi.binding.ManyToOneAttributeBinding;
|
|||
import org.hibernate.metamodel.spi.binding.MetaAttribute;
|
||||
import org.hibernate.metamodel.spi.binding.PluralAttributeElementNature;
|
||||
import org.hibernate.metamodel.spi.binding.SimpleValueBinding;
|
||||
import org.hibernate.metamodel.spi.binding.SingularAssociationAttributeBinding;
|
||||
import org.hibernate.metamodel.spi.binding.SingularAttributeBinding;
|
||||
import org.hibernate.metamodel.spi.binding.TypeDefinition;
|
||||
import org.hibernate.metamodel.spi.domain.Attribute;
|
||||
|
@ -67,6 +71,7 @@ import org.hibernate.metamodel.spi.domain.Entity;
|
|||
import org.hibernate.metamodel.spi.domain.PluralAttribute;
|
||||
import org.hibernate.metamodel.spi.domain.SingularAttribute;
|
||||
import org.hibernate.metamodel.spi.relational.Column;
|
||||
import org.hibernate.metamodel.spi.relational.Datatype;
|
||||
import org.hibernate.metamodel.spi.relational.DerivedValue;
|
||||
import org.hibernate.metamodel.spi.relational.ForeignKey;
|
||||
import org.hibernate.metamodel.spi.relational.Identifier;
|
||||
|
@ -112,41 +117,77 @@ import org.hibernate.metamodel.spi.source.ToOneAttributeSource;
|
|||
import org.hibernate.metamodel.spi.source.UniqueConstraintSource;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.persister.entity.EntityPersister;
|
||||
import org.hibernate.service.config.spi.ConfigurationService;
|
||||
import org.hibernate.tuple.entity.EntityTuplizer;
|
||||
import org.hibernate.type.Type;
|
||||
|
||||
/**
|
||||
* The common binder shared between annotations and {@code hbm.xml} processing.
|
||||
* <p/>
|
||||
* The API consists of {@link #Binder(MetadataImplementor, List)} and {@link #processEntityHierarchy(EntityHierarchy)}
|
||||
* The API consists of {@link #Binder( MetadataImplementor )} and {@link #processEntityHierarchies(Iterable)}
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
* @author Hardy Ferentschik
|
||||
*/
|
||||
public class Binder {
|
||||
private final MetadataImplementor metadata;
|
||||
private final List<String> processedEntityNames;
|
||||
private final ArrayList<String> processedEntityNames = new ArrayList<String>();
|
||||
|
||||
private InheritanceType currentInheritanceType;
|
||||
private EntityMode currentHierarchyEntityMode;
|
||||
private LocalBindingContext currentBindingContext;
|
||||
private HashMap<String, EntitySource> sourcesByName = new HashMap<String, EntitySource>();
|
||||
|
||||
public Binder(MetadataImplementor metadata, List<String> processedEntityNames) {
|
||||
public Binder( MetadataImplementor metadata ) {
|
||||
this.metadata = metadata;
|
||||
this.processedEntityNames = processedEntityNames;
|
||||
}
|
||||
|
||||
/**
|
||||
* Process an entity hierarchy.
|
||||
*
|
||||
* @param entityHierarchy THe hierarchy to process.
|
||||
* @param entityHierarchies THe hierarchies to process.
|
||||
*/
|
||||
public void processEntityHierarchy(EntityHierarchy entityHierarchy) {
|
||||
currentInheritanceType = entityHierarchy.getHierarchyInheritanceType();
|
||||
EntityBinding rootEntityBinding = createEntityBinding( entityHierarchy.getRootEntitySource(), null );
|
||||
if ( currentInheritanceType != InheritanceType.NO_INHERITANCE ) {
|
||||
processHierarchySubEntities( entityHierarchy.getRootEntitySource(), rootEntityBinding );
|
||||
}
|
||||
currentHierarchyEntityMode = null;
|
||||
public void processEntityHierarchies( Iterable<? extends EntityHierarchy> entityHierarchies ) {
|
||||
// Index sources by name so we can find and resolve entities on the fly as references to them are encountered (e.g., within associations)
|
||||
for ( EntityHierarchy hierarchy : entityHierarchies )
|
||||
mapSourcesByName( hierarchy.getRootEntitySource() );
|
||||
|
||||
for ( EntityHierarchy hierarchy : entityHierarchies ) {
|
||||
currentInheritanceType = hierarchy.getHierarchyInheritanceType();
|
||||
RootEntitySource rootEntitySource = hierarchy.getRootEntitySource();
|
||||
EntityBinding rootEntityBinding = createEntityBinding( rootEntitySource, null );
|
||||
// Create identifier generator for root entity
|
||||
Properties properties = new Properties();
|
||||
properties.putAll( metadata.getServiceRegistry().getService( ConfigurationService.class ).getSettings() );
|
||||
// TODO: where should these be added???
|
||||
if ( !properties.contains( AvailableSettings.PREFER_POOLED_VALUES_LO ) )
|
||||
properties.put( AvailableSettings.PREFER_POOLED_VALUES_LO, "false" );
|
||||
if ( !properties.contains( PersistentIdentifierGenerator.IDENTIFIER_NORMALIZER ) )
|
||||
properties.put( PersistentIdentifierGenerator.IDENTIFIER_NORMALIZER, new ObjectNameNormalizer() {
|
||||
|
||||
@Override
|
||||
protected boolean isUseQuotedIdentifiersGlobally() {
|
||||
return metadata.isGloballyQuotedIdentifiers();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected NamingStrategy getNamingStrategy() {
|
||||
return metadata.getNamingStrategy();
|
||||
}
|
||||
} );
|
||||
rootEntityBinding.getHierarchyDetails().getEntityIdentifier().
|
||||
createIdentifierGenerator( metadata.getIdentifierGeneratorFactory(), properties );
|
||||
|
||||
if ( currentInheritanceType != InheritanceType.NO_INHERITANCE )
|
||||
processHierarchySubEntities( rootEntitySource, rootEntityBinding );
|
||||
currentHierarchyEntityMode = null;
|
||||
}
|
||||
}
|
||||
|
||||
private void mapSourcesByName( EntitySource source ) {
|
||||
sourcesByName.put( source.getEntityName(), source );
|
||||
for ( SubclassEntitySource subsource : source.subclassEntitySources() )
|
||||
mapSourcesByName( subsource );
|
||||
}
|
||||
|
||||
private void processHierarchySubEntities(SubclassEntityContainer subclassEntitySource, EntityBinding superEntityBinding) {
|
||||
|
@ -455,6 +496,7 @@ public class Binder {
|
|||
|
||||
entityBinding.getHierarchyDetails().setEntityDiscriminator( discriminator );
|
||||
entityBinding.setDiscriminatorMatchValue( entitySource.getDiscriminatorMatchValue() );
|
||||
resolveTypeInformation(discriminator.getExplicitHibernateTypeDescriptor(), relationalValue);
|
||||
}
|
||||
|
||||
private void bindDiscriminatorValue(SubclassEntitySource entitySource, EntityBinding entityBinding) {
|
||||
|
@ -466,7 +508,7 @@ public class Binder {
|
|||
}
|
||||
|
||||
private void bindAttributes(
|
||||
AttributeSourceContainer attributeSourceContainer,
|
||||
AttributeSourceContainer attributeSourceContainer,
|
||||
AttributeBindingContainer attributeBindingContainer,
|
||||
Deque<TableSpecification> tableStack) {
|
||||
// todo : we really need the notion of a Stack here for the table from which the columns come for binding these attributes.
|
||||
|
@ -603,26 +645,26 @@ public class Binder {
|
|||
doBasicAttributeBinding( source, binding );
|
||||
}
|
||||
|
||||
private CollectionLaziness interpretLaziness(String laziness) {
|
||||
if ( laziness == null ) {
|
||||
laziness = Boolean.toString( metadata.getMappingDefaults().areAssociationsLazy() );
|
||||
}
|
||||
|
||||
if ( "extra".equals( laziness ) ) {
|
||||
return CollectionLaziness.EXTRA;
|
||||
}
|
||||
else if ( "false".equals( laziness ) ) {
|
||||
return CollectionLaziness.NOT;
|
||||
}
|
||||
else if ( "true".equals( laziness ) ) {
|
||||
return CollectionLaziness.LAZY;
|
||||
}
|
||||
|
||||
throw new MappingException(
|
||||
String.format( "Unexpected collection laziness value %s", laziness ),
|
||||
currentBindingContext.getOrigin()
|
||||
);
|
||||
}
|
||||
// private CollectionLaziness interpretLaziness(String laziness) {
|
||||
// if ( laziness == null ) {
|
||||
// laziness = Boolean.toString( metadata.getMappingDefaults().areAssociationsLazy() );
|
||||
// }
|
||||
//
|
||||
// if ( "extra".equals( laziness ) ) {
|
||||
// return CollectionLaziness.EXTRA;
|
||||
// }
|
||||
// else if ( "false".equals( laziness ) ) {
|
||||
// return CollectionLaziness.NOT;
|
||||
// }
|
||||
// else if ( "true".equals( laziness ) ) {
|
||||
// return CollectionLaziness.LAZY;
|
||||
// }
|
||||
//
|
||||
// throw new MappingException(
|
||||
// String.format( "Unexpected collection laziness value %s", laziness ),
|
||||
// currentBindingContext.getOrigin()
|
||||
// );
|
||||
// }
|
||||
|
||||
private void bindCollectionTable(
|
||||
PluralAttributeSource attributeSource,
|
||||
|
@ -688,7 +730,7 @@ public class Binder {
|
|||
AbstractPluralAttributeBinding pluralAttributeBinding,
|
||||
Deque<TableSpecification> tableStack) {
|
||||
|
||||
TableSpecification targetTable = tableStack.peekLast();
|
||||
// TableSpecification targetTable = tableStack.peekLast();
|
||||
pluralAttributeBinding.getPluralAttributeKeyBinding().prepareForeignKey(
|
||||
attributeSource.getKeySource().getExplicitForeignKeyName(),
|
||||
//tableStack.peekLast().getLogicalName()
|
||||
|
@ -885,21 +927,11 @@ public class Binder {
|
|||
}
|
||||
|
||||
final BasicAttributeBinding attributeBinding;
|
||||
if ( attributeSource.getNature() == SingularAttributeNature.BASIC ) {
|
||||
if ( attributeSource.getNature() == SingularAttributeNature.BASIC )
|
||||
attributeBinding = attributeBindingContainer.makeBasicAttributeBinding( attribute );
|
||||
resolveTypeInformation( attributeSource.getTypeInformation(), attributeBinding );
|
||||
}
|
||||
else if ( attributeSource.getNature() == SingularAttributeNature.MANY_TO_ONE ) {
|
||||
else if ( attributeSource.getNature() == SingularAttributeNature.MANY_TO_ONE )
|
||||
attributeBinding = attributeBindingContainer.makeManyToOneAttributeBinding( attribute );
|
||||
resolveTypeInformation( attributeSource.getTypeInformation(), attributeBinding );
|
||||
resolveToOneInformation(
|
||||
(ToOneAttributeSource) attributeSource,
|
||||
(ManyToOneAttributeBinding) attributeBinding
|
||||
);
|
||||
}
|
||||
else {
|
||||
throw new NotYetImplementedException();
|
||||
}
|
||||
else throw new NotYetImplementedException();
|
||||
|
||||
attributeBinding.setGeneration( attributeSource.getGeneration() );
|
||||
attributeBinding.setLazy( attributeSource.isLazy() );
|
||||
|
@ -915,6 +947,25 @@ public class Binder {
|
|||
|
||||
bindRelationalValues( attributeSource, attributeBinding );
|
||||
|
||||
resolveTypeInformation( attributeSource.getTypeInformation(), attributeBinding );
|
||||
if ( attributeSource.getNature() == SingularAttributeNature.MANY_TO_ONE )
|
||||
resolveToOneInformation( ( ToOneAttributeSource ) attributeSource, ( ManyToOneAttributeBinding ) attributeBinding );
|
||||
|
||||
if ( attributeBinding instanceof SingularAssociationAttributeBinding ) {
|
||||
SingularAssociationAttributeBinding assocAttrBinding = ( SingularAssociationAttributeBinding ) attributeBinding;
|
||||
String referencedEntityName = assocAttrBinding.getReferencedEntityName();
|
||||
EntityBinding referencedEntityBinding = getEntityBinding( referencedEntityName );
|
||||
if (referencedEntityBinding == null) {
|
||||
EntitySource source = sourcesByName.get(referencedEntityName);
|
||||
createEntityBinding(source, referencedEntityBinding);
|
||||
}
|
||||
AttributeBinding referencedAttrBinding = assocAttrBinding.isPropertyReference() ?
|
||||
referencedEntityBinding.locateAttributeBinding( assocAttrBinding.getReferencedAttributeName() ) :
|
||||
referencedEntityBinding.getHierarchyDetails().getEntityIdentifier().getValueBinding();
|
||||
assocAttrBinding.resolveReference( referencedAttrBinding );
|
||||
referencedAttrBinding.addEntityReferencingAttributeBinding( assocAttrBinding );
|
||||
}
|
||||
|
||||
attributeBinding.setMetaAttributeContext(
|
||||
buildMetaAttributeContext(
|
||||
attributeSource.metaAttributes(),
|
||||
|
@ -925,6 +976,24 @@ public class Binder {
|
|||
return attributeBinding;
|
||||
}
|
||||
|
||||
private EntityBinding getEntityBinding( String entityName ) {
|
||||
// Check if binding has already been created
|
||||
EntityBinding binding = metadata.getEntityBinding( entityName );
|
||||
if ( binding == null ) {
|
||||
// Find appropriate source to create binding
|
||||
EntitySource source = sourcesByName.get( entityName );
|
||||
// Get super entity binding (creating it if necessary using recursive call to this method)
|
||||
EntityBinding superBinding = source instanceof SubclassEntitySource
|
||||
? getEntityBinding( ( ( SubclassEntitySource ) source ).superclassEntitySource().getEntityName() )
|
||||
: null;
|
||||
// Create entity binding
|
||||
binding = createEntityBinding( source, superBinding );
|
||||
// Create entity binding's sub-entity bindings
|
||||
processHierarchySubEntities( source, binding );
|
||||
}
|
||||
return binding;
|
||||
}
|
||||
|
||||
private void resolveTypeInformation(ExplicitHibernateTypeSource typeSource, BasicAttributeBinding attributeBinding) {
|
||||
final Class<?> attributeJavaType = determineJavaType( attributeBinding.getAttribute() );
|
||||
if ( attributeJavaType != null ) {
|
||||
|
@ -933,6 +1002,7 @@ public class Binder {
|
|||
}
|
||||
|
||||
resolveTypeInformation( typeSource, attributeBinding.getHibernateTypeDescriptor(), attributeJavaType );
|
||||
resolveTypeInformation( attributeBinding.getHibernateTypeDescriptor(), (SimpleValue)attributeBinding.getValue() );
|
||||
}
|
||||
|
||||
private void resolveTypeInformation(
|
||||
|
@ -975,6 +1045,29 @@ public class Binder {
|
|||
}
|
||||
}
|
||||
|
||||
private void resolveTypeInformation( HibernateTypeDescriptor descriptor,
|
||||
SimpleValue value ) {
|
||||
Type resolvedType = descriptor.getResolvedTypeMapping();
|
||||
if ( resolvedType == null ) {
|
||||
final String name = descriptor.getExplicitTypeName() == null ? descriptor.getJavaTypeName() : descriptor.getExplicitTypeName();
|
||||
if (name != null) {
|
||||
resolvedType = metadata.getTypeResolver().heuristicType( name, convertTypeParametersToProperties( descriptor ) );
|
||||
descriptor.setResolvedTypeMapping( resolvedType );
|
||||
}
|
||||
if (resolvedType == null) return;
|
||||
}
|
||||
if ( descriptor.getJavaTypeName() == null ) descriptor.setJavaTypeName( resolvedType.getReturnedClass().getName() );
|
||||
if ( value.getDatatype() == null )
|
||||
value.setDatatype( new Datatype( resolvedType.sqlTypes( metadata )[0], resolvedType.getName(),
|
||||
resolvedType.getReturnedClass() ) );
|
||||
}
|
||||
|
||||
private Properties convertTypeParametersToProperties( HibernateTypeDescriptor descriptor ) {
|
||||
Properties props = new Properties( );
|
||||
if ( descriptor.getTypeParameters() != null ) props.putAll( descriptor.getTypeParameters() );
|
||||
return props;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param attribute the domain attribute
|
||||
*
|
||||
|
|
|
@ -64,11 +64,13 @@ public class HibernateTypeResolver {
|
|||
}
|
||||
for ( AttributeBinding attributeBinding : entityBinding.attributeBindings() ) {
|
||||
if ( SingularAttributeBinding.class.isInstance( attributeBinding ) ) {
|
||||
System.out.println("singlular binding: " + attributeBinding.getAttribute().getName());
|
||||
resolveSingularAttributeTypeInformation(
|
||||
SingularAttributeBinding.class.cast( attributeBinding )
|
||||
);
|
||||
}
|
||||
else if ( AbstractPluralAttributeBinding.class.isInstance( attributeBinding ) ) {
|
||||
System.out.println("plural binding: " + attributeBinding.getAttribute().getName());
|
||||
resolvePluralAttributeTypeInformation(
|
||||
AbstractPluralAttributeBinding.class.cast( attributeBinding )
|
||||
);
|
||||
|
@ -126,6 +128,7 @@ public class HibernateTypeResolver {
|
|||
// 2) we know the java type of the attribute
|
||||
Type resolvedType;
|
||||
resolvedType = determineSingularTypeFromDescriptor( attributeBinding.getHibernateTypeDescriptor() );
|
||||
System.out.println("resolvedType: " + resolvedType);
|
||||
if ( resolvedType == null ) {
|
||||
if ( ! attributeBinding.getAttribute().isSingular() ) {
|
||||
throw new AssertionFailure( "SingularAttributeBinding object has a plural attribute: " + attributeBinding.getAttribute().getName() );
|
||||
|
|
|
@ -144,7 +144,7 @@ public class EntityHierarchyBuilder {
|
|||
hierarchyInheritanceType,
|
||||
bindingContext
|
||||
);
|
||||
SubclassEntitySource subclassEntitySource = new SubclassEntitySourceImpl( subclassEntityClass );
|
||||
SubclassEntitySource subclassEntitySource = new SubclassEntitySourceImpl( subclassEntityClass, entitySource );
|
||||
entitySource.add( subclassEntitySource );
|
||||
addSubclassEntitySources(
|
||||
bindingContext,
|
||||
|
|
|
@ -23,15 +23,31 @@
|
|||
*/
|
||||
package org.hibernate.metamodel.internal.source.annotations.entity;
|
||||
|
||||
import org.hibernate.metamodel.spi.source.EntitySource;
|
||||
import org.hibernate.metamodel.spi.source.SubclassEntitySource;
|
||||
|
||||
/**
|
||||
* @author Hardy Ferentschik
|
||||
*/
|
||||
public class SubclassEntitySourceImpl extends EntitySourceImpl implements SubclassEntitySource {
|
||||
public SubclassEntitySourceImpl(EntityClass entityClass) {
|
||||
|
||||
private final EntitySource container;
|
||||
|
||||
public SubclassEntitySourceImpl( EntityClass entityClass,
|
||||
EntitySource container ) {
|
||||
super( entityClass );
|
||||
this.container = container;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*
|
||||
* @see org.hibernate.metamodel.spi.source.SubclassEntitySource#superclassEntitySource()
|
||||
*/
|
||||
@Override
|
||||
public EntitySource superclassEntitySource() {
|
||||
return container;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -36,6 +36,7 @@ import org.hibernate.internal.jaxb.mapping.hbm.JaxbJoinedSubclassElement;
|
|||
import org.hibernate.internal.jaxb.mapping.hbm.JaxbSubclassElement;
|
||||
import org.hibernate.internal.jaxb.mapping.hbm.JaxbUnionSubclassElement;
|
||||
import org.hibernate.internal.jaxb.mapping.hbm.SubEntityElement;
|
||||
import org.hibernate.metamodel.spi.source.EntitySource;
|
||||
import org.hibernate.metamodel.spi.source.SubclassEntityContainer;
|
||||
import org.hibernate.metamodel.spi.source.SubclassEntitySource;
|
||||
|
||||
|
@ -81,14 +82,14 @@ public class HierarchyBuilder {
|
|||
else {
|
||||
// we have to see if this things super-type has been found yet, and if not add it to the
|
||||
// extends queue
|
||||
final SubclassEntitySourceImpl subClassEntitySource = new SubclassEntitySourceImpl( currentMappingDocument, entityElement );
|
||||
final String entityItExtends =
|
||||
currentMappingDocument.getMappingLocalBindingContext().
|
||||
qualifyClassName( ( (SubEntityElement) entityElement ).getExtends() );
|
||||
final SubclassEntityContainer container = subEntityContainerMap.get( entityItExtends );
|
||||
final SubclassEntitySourceImpl subClassEntitySource = new SubclassEntitySourceImpl( currentMappingDocument, entityElement, ( EntitySource ) container );
|
||||
final String entityName = subClassEntitySource.getEntityName();
|
||||
subEntityContainerMap.put( entityName, subClassEntitySource );
|
||||
final String entityItExtends = currentMappingDocument.getMappingLocalBindingContext().qualifyClassName(
|
||||
((SubEntityElement) entityElement).getExtends()
|
||||
);
|
||||
processSubElements( entityElement, subClassEntitySource );
|
||||
final SubclassEntityContainer container = subEntityContainerMap.get( entityItExtends );
|
||||
if ( container != null ) {
|
||||
// we already have this entity's super, attach it and continue
|
||||
container.add( subClassEntitySource );
|
||||
|
@ -150,7 +151,7 @@ public class HierarchyBuilder {
|
|||
private void processElements(List subElements, SubclassEntityContainer container) {
|
||||
for ( Object subElementO : subElements ) {
|
||||
final SubEntityElement subElement = (SubEntityElement) subElementO;
|
||||
final SubclassEntitySourceImpl subclassEntitySource = new SubclassEntitySourceImpl( currentMappingDocument, subElement );
|
||||
final SubclassEntitySourceImpl subclassEntitySource = new SubclassEntitySourceImpl( currentMappingDocument, subElement, ( EntitySource ) container );
|
||||
container.add( subclassEntitySource );
|
||||
final String subEntityName = subclassEntitySource.getEntityName();
|
||||
subEntityContainerMap.put( subEntityName, subclassEntitySource );
|
||||
|
|
|
@ -27,6 +27,7 @@ import org.hibernate.internal.jaxb.mapping.hbm.EntityElement;
|
|||
import org.hibernate.internal.jaxb.mapping.hbm.JaxbJoinedSubclassElement;
|
||||
import org.hibernate.internal.jaxb.mapping.hbm.JaxbSubclassElement;
|
||||
import org.hibernate.internal.jaxb.mapping.hbm.JaxbUnionSubclassElement;
|
||||
import org.hibernate.metamodel.spi.source.EntitySource;
|
||||
import org.hibernate.metamodel.spi.source.SubclassEntitySource;
|
||||
import org.hibernate.metamodel.spi.source.TableSource;
|
||||
|
||||
|
@ -34,8 +35,14 @@ import org.hibernate.metamodel.spi.source.TableSource;
|
|||
* @author Steve Ebersole
|
||||
*/
|
||||
public class SubclassEntitySourceImpl extends AbstractEntitySourceImpl implements SubclassEntitySource {
|
||||
protected SubclassEntitySourceImpl(MappingDocument sourceMappingDocument, EntityElement entityElement) {
|
||||
|
||||
private final EntitySource container;
|
||||
|
||||
protected SubclassEntitySourceImpl( MappingDocument sourceMappingDocument,
|
||||
EntityElement entityElement,
|
||||
EntitySource container ) {
|
||||
super( sourceMappingDocument, entityElement );
|
||||
this.container = container;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -97,4 +104,14 @@ public class SubclassEntitySourceImpl extends AbstractEntitySourceImpl implement
|
|||
? ( (JaxbSubclassElement) entityElement() ).getDiscriminatorValue()
|
||||
: null;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*
|
||||
* @see SubclassEntitySource#superclassEntitySource()
|
||||
*/
|
||||
@Override
|
||||
public EntitySource superclassEntitySource() {
|
||||
return container;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -27,4 +27,9 @@ package org.hibernate.metamodel.spi.source;
|
|||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface SubclassEntitySource extends EntitySource {
|
||||
|
||||
/**
|
||||
* @return the entity source for the entity that is a superclass of the entity for which this is a source
|
||||
*/
|
||||
EntitySource superclassEntitySource();
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue