6 - SQM based on JPA type system
This commit is contained in:
parent
af2c32e32c
commit
f4126082da
|
@ -8,10 +8,18 @@ package org.hibernate;
|
|||
|
||||
import javax.persistence.metamodel.EntityType;
|
||||
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*
|
||||
* @deprecated (since 6.0) Access to JPA's type system and Hibernate's type
|
||||
* system has been separated into {@link JpaMetamodel}
|
||||
* and {@link org.hibernate.metamodel.spi.RuntimeModel} respectively.
|
||||
*/
|
||||
public interface Metamodel extends javax.persistence.metamodel.Metamodel {
|
||||
@Deprecated
|
||||
public interface Metamodel extends JpaMetamodel {
|
||||
/**
|
||||
* Access to the SessionFactory that this Metamodel instance is bound to.
|
||||
*
|
||||
|
@ -34,7 +42,7 @@ public interface Metamodel extends javax.persistence.metamodel.Metamodel {
|
|||
*
|
||||
* @return The entity descriptor
|
||||
*/
|
||||
<X> EntityType<X> entity(String entityName);
|
||||
<X> EntityDomainType<X> entity(String entityName);
|
||||
|
||||
String getImportedClassName(String className);
|
||||
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public abstract class AbstractBagSemantics<B extends Collection<?>> implements CollectionSemantics<B> {
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public B instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
if ( anticipatedSize < 1 ) {
|
||||
return (B) new ArrayList();
|
||||
}
|
||||
else {
|
||||
return (B) CollectionHelper.arrayList( anticipatedSize );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <E> Iterator<E> getElementIterator(B rawCollection) {
|
||||
if ( rawCollection == null ) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return (Iterator<E>) rawCollection.iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitElements(B rawCollection, Consumer action) {
|
||||
if ( rawCollection != null ) {
|
||||
rawCollection.forEach( action );
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,63 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
import java.util.function.BiConsumer;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.collection.spi.MapSemantics;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public abstract class AbstractMapSemantics<M extends Map<?,?>> implements MapSemantics<M> {
|
||||
@Override
|
||||
public Iterator getKeyIterator(M rawMap) {
|
||||
if ( rawMap == null ) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return rawMap.keySet().iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitKeys(M rawMap, Consumer action) {
|
||||
if ( rawMap != null ) {
|
||||
rawMap.keySet().forEach( action );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitEntries(M rawMap, BiConsumer action) {
|
||||
if ( rawMap != null ) {
|
||||
rawMap.forEach( action );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Iterator getElementIterator(Map rawMap) {
|
||||
if ( rawMap == null ) {
|
||||
return Collections.emptyIterator();
|
||||
}
|
||||
|
||||
return rawMap.values().iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitElements(M rawMap, Consumer action) {
|
||||
if ( rawMap != null ) {
|
||||
rawMap.values().forEach( action );
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public abstract class AbstractSetSemantics<S extends Set<?>> implements CollectionSemantics<S> {
|
||||
@Override
|
||||
public Iterator getElementIterator(Set rawCollection) {
|
||||
if ( rawCollection == null ) {
|
||||
return null;
|
||||
}
|
||||
return rawCollection.iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitElements(S rawCollection, Consumer action) {
|
||||
if ( rawCollection != null ) {
|
||||
rawCollection.forEach( action );
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,84 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Iterator;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* CollectionSemantics implementation for arrays
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardArraySemantics implements CollectionSemantics<Object[]> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardArraySemantics INSTANCE = new StandardArraySemantics();
|
||||
|
||||
private StandardArraySemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ARRAY;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object[] instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
// return (Object[]) Array.newInstance(
|
||||
// collectionDescriptor.getJavaTypeDescriptor().getJavaType().getComponentType(),
|
||||
// anticipatedSize
|
||||
// );
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentArrayHolder( key, session, collectionDescriptor );
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentArrayHolder( session, collectionDescriptor, rawCollection );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <E> Iterator<E> getElementIterator(Object[] rawCollection) {
|
||||
return (Iterator<E>) Arrays.stream( rawCollection ).iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitElements(Object[] array, Consumer action) {
|
||||
if ( array == null ) {
|
||||
return;
|
||||
}
|
||||
|
||||
for ( Object element : array ) {
|
||||
action.accept( element );
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* CollectionSemantics for bags
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardBagSemantics extends AbstractBagSemantics<Collection<?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardBagSemantics INSTANCE = new StandardBagSemantics();
|
||||
|
||||
private StandardBagSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.BAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentBag( session, collectionDescriptor );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentBag( session, collectionDescriptor, (Collection) rawCollection );
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* CollectionSemantics implementation for id-bags
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardIdentifierBagSemantics<E> extends AbstractBagSemantics<Collection<?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardIdentifierBagSemantics INSTANCE = new StandardIdentifierBagSemantics();
|
||||
|
||||
private StandardIdentifierBagSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.IDBAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection<E> instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentIdentifierBag( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentIdentifierBag( session, collectionDescriptor, (Collection) rawCollection );
|
||||
}
|
||||
}
|
|
@ -0,0 +1,74 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* Hibernate's standard CollectionSemantics for Lists
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardListSemantics implements CollectionSemantics<List> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardListSemantics INSTANCE = new StandardListSemantics();
|
||||
|
||||
private StandardListSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.LIST;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
return CollectionHelper.arrayList( anticipatedSize );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public Iterator getElementIterator(List rawCollection) {
|
||||
return rawCollection.iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitElements(List rawCollection, Consumer action) {
|
||||
rawCollection.forEach( action );
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentList( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentList( session, collectionDescriptor, (List) rawCollection );
|
||||
}
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* CollectionSemantics for maps
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardMapSemantics extends AbstractMapSemantics<Map<?,?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardMapSemantics INSTANCE = new StandardMapSemantics();
|
||||
|
||||
private StandardMapSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.MAP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<?, ?> instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
return CollectionHelper.mapOfSize( anticipatedSize );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentMap( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentMap( session, collectionDescriptor, (Map) rawCollection );
|
||||
}
|
||||
}
|
|
@ -0,0 +1,62 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.model.mapping.PersistentCollectionDescriptor;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardOrderedMapSemantics extends AbstractMapSemantics<LinkedHashMap<?,?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardOrderedMapSemantics INSTANCE = new StandardOrderedMapSemantics();
|
||||
|
||||
private StandardOrderedMapSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ORDERED_MAP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LinkedHashMap<?, ?> instantiateRaw(
|
||||
int anticipatedSize,
|
||||
PersistentCollectionDescriptor collectionDescriptor) {
|
||||
return anticipatedSize < 1 ? new LinkedHashMap<>() : new LinkedHashMap<>( anticipatedSize );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> instantiateWrapper(
|
||||
Object key,
|
||||
PersistentCollectionDescriptor<?, LinkedHashMap<?, ?>, E> collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentMap<>( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
PersistentCollectionDescriptor<?, LinkedHashMap<?, ?>, E> collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentMap<>( session, collectionDescriptor, (Map) rawCollection );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterator getElementIterator(LinkedHashMap rawCollection) {
|
||||
return rawCollection.entrySet().iterator();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,62 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.Set;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.model.mapping.PersistentCollectionDescriptor;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardOrderedSetSemantics extends AbstractSetSemantics<LinkedHashSet<?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardOrderedSetSemantics INSTANCE = new StandardOrderedSetSemantics();
|
||||
|
||||
private StandardOrderedSetSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ORDERED_SET;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LinkedHashSet<?> instantiateRaw(
|
||||
int anticipatedSize,
|
||||
PersistentCollectionDescriptor collectionDescriptor) {
|
||||
return anticipatedSize < 1 ? new LinkedHashSet() : new LinkedHashSet<>( anticipatedSize );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> instantiateWrapper(
|
||||
Object key,
|
||||
PersistentCollectionDescriptor<?, LinkedHashSet<?>, E> collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSet( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
PersistentCollectionDescriptor<?, LinkedHashSet<?>, E> collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSet( session, collectionDescriptor, (Set) rawCollection );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterator getElementIterator(LinkedHashSet rawCollection) {
|
||||
return rawCollection.iterator();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardSetSemantics extends AbstractSetSemantics<Set<?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardSetSemantics INSTANCE = new StandardSetSemantics();
|
||||
|
||||
private StandardSetSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SET;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<?> instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
return anticipatedSize < 1 ? new HashSet<>() : new HashSet<>( anticipatedSize );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
//noinspection unchecked
|
||||
return new PersistentSet( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <E> PersistentCollection<E> wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
//noinspection unchecked
|
||||
return new PersistentSet( session, collectionDescriptor, (Set) rawCollection );
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.SortedMap;
|
||||
import java.util.TreeMap;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardSortedMapSemantics extends AbstractMapSemantics<SortedMap<?,?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardSortedMapSemantics INSTANCE = new StandardSortedMapSemantics();
|
||||
|
||||
private StandardSortedMapSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SORTED_MAP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public TreeMap<?, ?> instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
return new TreeMap<>( collectionDescriptor.getSortingComparator() );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSortedMap( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSortedMap( session, collectionDescriptor, (SortedMap) rawCollection );
|
||||
}
|
||||
}
|
|
@ -0,0 +1,65 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.internal;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.SortedSet;
|
||||
import java.util.TreeSet;
|
||||
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class StandardSortedSetSemantics extends AbstractSetSemantics<SortedSet<?>> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final StandardSortedSetSemantics INSTANCE = new StandardSortedSetSemantics();
|
||||
|
||||
private StandardSortedSetSemantics() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SORTED_SET;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SortedSet instantiateRaw(
|
||||
int anticipatedSize,
|
||||
CollectionPersister collectionDescriptor) {
|
||||
return new TreeSet<>( collectionDescriptor.getSortingComparator() );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection instantiateWrapper(
|
||||
Object key,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSortedSet( session, collectionDescriptor, key );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public PersistentCollection wrap(
|
||||
Object rawCollection,
|
||||
CollectionPersister collectionDescriptor,
|
||||
SharedSessionContractImplementor session) {
|
||||
return new PersistentSortedSet( session, collectionDescriptor, (SortedSet) rawCollection );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <E> Iterator<E> getElementIterator(SortedSet<?> rawCollection) {
|
||||
return (Iterator<E>) rawCollection.iterator();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.spi;
|
||||
|
||||
import org.hibernate.mapping.Collection;
|
||||
|
||||
/**
|
||||
* todo (6.0) ...
|
||||
*
|
||||
* Ideally would act as the contract that allows pluggable resolution of
|
||||
* non-Java Collection types - maybe as part of a generalized reflection
|
||||
* on the attribute to determine its nature/classification
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface CollectionSemanticsResolver {
|
||||
// really need some form of access to the attribute site
|
||||
CollectionSemantics resolveRepresentation(Collection bootDescriptor);
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.collection.spi;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.function.BiConsumer;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
/**
|
||||
* Extension of CollectionSemantics for Maps
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface MapSemantics<M> extends CollectionSemantics<M> {
|
||||
Iterator getKeyIterator(M rawMap);
|
||||
|
||||
void visitKeys(M rawMap, Consumer action);
|
||||
|
||||
void visitEntries(M rawMap, BiConsumer action);
|
||||
}
|
|
@ -12,7 +12,7 @@ import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
|||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
|
||||
/**
|
||||
* A container for {@link AttributeNode}s.
|
||||
* A container for {@link AttributeNode} references.
|
||||
*
|
||||
* Acts as a "bridge" between JPA's {@link javax.persistence.EntityGraph} and {@link javax.persistence.Subgraph}
|
||||
*
|
||||
|
|
|
@ -12,6 +12,8 @@ import javax.persistence.EntityGraph;
|
|||
import javax.persistence.Subgraph;
|
||||
import javax.persistence.metamodel.Attribute;
|
||||
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
|
||||
/**
|
||||
* Hibernate extension to the JPA {@link EntityGraph} contract.
|
||||
*
|
||||
|
@ -24,7 +26,7 @@ public interface RootGraph<J> extends Graph<J>, EntityGraph<J> {
|
|||
|
||||
boolean appliesTo(String entityName);
|
||||
|
||||
boolean appliesTo(Class entityType);
|
||||
boolean appliesTo(Class<? super J> entityType);
|
||||
|
||||
@Override
|
||||
RootGraph<J> makeRootGraph(String name, boolean mutable);
|
||||
|
@ -59,18 +61,20 @@ public interface RootGraph<J> extends Graph<J>, EntityGraph<J> {
|
|||
}
|
||||
|
||||
for ( Attribute<J, ?> attribute : attributes ) {
|
||||
addAttributeNode( attribute );
|
||||
addAttributeNode( (PersistentAttribute) attribute );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
default <X> SubGraph<X> addSubgraph(Attribute<J, X> attribute) {
|
||||
return addSubGraph( attribute );
|
||||
//noinspection unchecked
|
||||
return addSubGraph( (PersistentAttribute) attribute );
|
||||
}
|
||||
|
||||
@Override
|
||||
default <X> SubGraph<? extends X> addSubgraph(Attribute<J, X> attribute, Class<? extends X> type) {
|
||||
return addSubGraph( attribute, type );
|
||||
//noinspection unchecked
|
||||
return addSubGraph( (PersistentAttribute) attribute, type );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -85,12 +89,14 @@ public interface RootGraph<J> extends Graph<J>, EntityGraph<J> {
|
|||
|
||||
@Override
|
||||
default <X> SubGraph<X> addKeySubgraph(Attribute<J, X> attribute) {
|
||||
return addKeySubGraph( attribute );
|
||||
//noinspection unchecked
|
||||
return addKeySubGraph( (PersistentAttribute) attribute );
|
||||
}
|
||||
|
||||
@Override
|
||||
default <X> SubGraph<? extends X> addKeySubgraph(Attribute<J, X> attribute, Class<? extends X> type) {
|
||||
return addKeySubGraph( attribute, type );
|
||||
//noinspection unchecked
|
||||
return addKeySubGraph( (PersistentAttribute) attribute, type );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -12,7 +12,6 @@ import java.util.HashMap;
|
|||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.AttributeNode;
|
||||
import org.hibernate.graph.CannotBecomeEntityGraphException;
|
||||
import org.hibernate.graph.CannotContainSubGraphException;
|
||||
|
@ -23,6 +22,7 @@ import org.hibernate.graph.spi.GraphImplementor;
|
|||
import org.hibernate.graph.spi.RootGraphImplementor;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
|
||||
|
@ -39,14 +39,14 @@ public abstract class AbstractGraph<J> extends AbstractGraphNode<J> implements G
|
|||
public AbstractGraph(
|
||||
ManagedDomainType<J> managedType,
|
||||
boolean mutable,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( mutable, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( mutable, jpaMetamodel );
|
||||
this.managedType = managedType;
|
||||
}
|
||||
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
protected AbstractGraph(boolean mutable, GraphImplementor<J> original) {
|
||||
this( original.getGraphedType(), mutable, original.sessionFactory() );
|
||||
this( original.getGraphedType(), mutable, original.jpaMetamodel() );
|
||||
|
||||
this.attrNodeMap = CollectionHelper.concurrentMap( original.getAttributeNodeList().size() );
|
||||
original.visitAttributeNodes(
|
||||
|
@ -58,8 +58,8 @@ public abstract class AbstractGraph<J> extends AbstractGraphNode<J> implements G
|
|||
}
|
||||
|
||||
@Override
|
||||
public SessionFactoryImplementor sessionFactory() {
|
||||
return super.sessionFactory();
|
||||
public JpaMetamodel jpaMetamodel() {
|
||||
return super.jpaMetamodel();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -196,7 +196,7 @@ public abstract class AbstractGraph<J> extends AbstractGraphNode<J> implements G
|
|||
}
|
||||
|
||||
if ( attrNode == null ) {
|
||||
attrNode = new AttributeNodeImpl<>( isMutable(), attribute, sessionFactory() );
|
||||
attrNode = new AttributeNodeImpl<>( isMutable(), attribute, jpaMetamodel() );
|
||||
attrNodeMap.put( attribute, attrNode );
|
||||
}
|
||||
|
||||
|
|
|
@ -6,23 +6,23 @@
|
|||
*/
|
||||
package org.hibernate.graph.internal;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.spi.GraphNodeImplementor;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public abstract class AbstractGraphNode<J> implements GraphNodeImplementor<J> {
|
||||
private final SessionFactoryImplementor sessionFactory;
|
||||
private final JpaMetamodel jpaMetamodel;
|
||||
private final boolean mutable;
|
||||
|
||||
public AbstractGraphNode(boolean mutable, SessionFactoryImplementor sessionFactory) {
|
||||
this.sessionFactory = sessionFactory;
|
||||
public AbstractGraphNode(boolean mutable, JpaMetamodel jpaMetamodel) {
|
||||
this.jpaMetamodel = jpaMetamodel;
|
||||
this.mutable = mutable;
|
||||
}
|
||||
|
||||
protected SessionFactoryImplementor sessionFactory() {
|
||||
return sessionFactory;
|
||||
protected JpaMetamodel jpaMetamodel() {
|
||||
return jpaMetamodel;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -11,12 +11,12 @@ import java.util.HashMap;
|
|||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.CannotContainSubGraphException;
|
||||
import org.hibernate.graph.SubGraph;
|
||||
import org.hibernate.graph.spi.AttributeNodeImplementor;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
import org.hibernate.metamodel.model.domain.SimpleDomainType;
|
||||
|
@ -40,8 +40,8 @@ public class AttributeNodeImpl<J>
|
|||
public <X> AttributeNodeImpl(
|
||||
boolean mutable,
|
||||
PersistentAttribute<X, J> attribute,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
this( mutable, attribute, null, null, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
this( mutable, attribute, null, null, jpaMetamodel );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -52,8 +52,8 @@ public class AttributeNodeImpl<J>
|
|||
PersistentAttribute<?, J> attribute,
|
||||
Map<Class<? extends J>, SubGraphImplementor<? extends J>> subGraphMap,
|
||||
Map<Class<? extends J>, SubGraphImplementor<? extends J>> keySubGraphMap,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( mutable, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( mutable, jpaMetamodel );
|
||||
this.attribute = attribute;
|
||||
this.subGraphMap = subGraphMap;
|
||||
this.keySubGraphMap = keySubGraphMap;
|
||||
|
@ -152,7 +152,7 @@ public class AttributeNodeImpl<J>
|
|||
|
||||
@SuppressWarnings({"WeakerAccess", "unchecked"})
|
||||
protected <S extends J> void internalAddSubGraph(Class<S> subType, SubGraphImplementor<S> subGraph) {
|
||||
log.tracef( "Adding sub-graph : ( (%s) %s )", subGraph.getGraphedType().getName(), getAttributeName() );
|
||||
log.tracef( "Adding sub-graph : ( (%s) %s )", subGraph.getGraphedType().getTypeName(), getAttributeName() );
|
||||
|
||||
if ( subGraphMap == null ) {
|
||||
subGraphMap = new HashMap<>();
|
||||
|
@ -265,7 +265,7 @@ public class AttributeNodeImpl<J>
|
|||
this.attribute,
|
||||
makeMapCopy( mutable, (Map) subGraphMap ),
|
||||
makeMapCopy( mutable, (Map) keySubGraphMap ),
|
||||
sessionFactory()
|
||||
jpaMetamodel()
|
||||
);
|
||||
}
|
||||
|
||||
|
|
|
@ -9,13 +9,13 @@ package org.hibernate.graph.internal;
|
|||
import javax.persistence.EntityGraph;
|
||||
|
||||
import org.hibernate.cfg.NotYetImplementedException;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.SubGraph;
|
||||
import org.hibernate.graph.spi.GraphImplementor;
|
||||
import org.hibernate.graph.spi.RootGraphImplementor;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.IdentifiableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
|
||||
/**
|
||||
* The Hibernate implementation of the JPA EntityGraph contract.
|
||||
|
@ -29,17 +29,17 @@ public class RootGraphImpl<J> extends AbstractGraph<J> implements EntityGraph<J>
|
|||
String name,
|
||||
EntityDomainType<J> entityType,
|
||||
boolean mutable,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( entityType, mutable, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( entityType, mutable, jpaMetamodel );
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public RootGraphImpl(String name, EntityDomainType<J> entityType, SessionFactoryImplementor sessionFactory) {
|
||||
public RootGraphImpl(String name, EntityDomainType<J> entityType, JpaMetamodel jpaMetamodel) {
|
||||
this(
|
||||
name,
|
||||
entityType,
|
||||
true,
|
||||
sessionFactory
|
||||
jpaMetamodel
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -96,11 +96,11 @@ public class RootGraphImpl<J> extends AbstractGraph<J> implements EntityGraph<J>
|
|||
|
||||
@Override
|
||||
public boolean appliesTo(String entityName) {
|
||||
return appliesTo( sessionFactory().getMetamodel().entity( entityName ) );
|
||||
return appliesTo( jpaMetamodel().entity( entityName ) );
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean appliesTo(Class entityType) {
|
||||
return appliesTo( sessionFactory().getMetamodel().entity( entityType ) );
|
||||
public boolean appliesTo(Class<? super J> type) {
|
||||
return appliesTo( jpaMetamodel().entity( type ) );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,13 +6,9 @@
|
|||
*/
|
||||
package org.hibernate.graph.internal;
|
||||
|
||||
import javax.persistence.metamodel.Attribute;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.spi.AttributeNodeImplementor;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
|
@ -21,8 +17,8 @@ public class SubGraphImpl<J> extends AbstractGraph<J> implements SubGraphImpleme
|
|||
public SubGraphImpl(
|
||||
ManagedDomainType<J> managedType,
|
||||
boolean mutable,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( managedType, mutable, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( managedType, mutable, jpaMetamodel );
|
||||
}
|
||||
|
||||
public SubGraphImpl(boolean mutable, AbstractGraph<J> original) {
|
||||
|
@ -48,12 +44,6 @@ public class SubGraphImpl<J> extends AbstractGraph<J> implements SubGraphImpleme
|
|||
return super.addKeySubGraph( attributeName );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <AJ> AttributeNodeImplementor<AJ> addAttributeNode(Attribute<? extends J, AJ> attribute) {
|
||||
return addAttributeNode( (PersistentAttribute) attribute );
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean appliesTo(ManagedDomainType<? super J> managedType) {
|
||||
if ( this.getGraphedType().equals( managedType ) ) {
|
||||
|
@ -73,6 +63,6 @@ public class SubGraphImpl<J> extends AbstractGraph<J> implements SubGraphImpleme
|
|||
|
||||
@Override
|
||||
public boolean appliesTo(Class<? super J> javaType) {
|
||||
return appliesTo( sessionFactory().getMetamodel().managedType( javaType ) );
|
||||
return appliesTo( jpaMetamodel().managedType( javaType ) );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,11 +9,11 @@ package org.hibernate.graph.spi;
|
|||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.AttributeNode;
|
||||
import org.hibernate.graph.CannotBecomeEntityGraphException;
|
||||
import org.hibernate.graph.CannotContainSubGraphException;
|
||||
import org.hibernate.graph.Graph;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
|
||||
|
@ -32,7 +32,7 @@ public interface GraphImplementor<J> extends Graph<J>, GraphNodeImplementor<J> {
|
|||
@SuppressWarnings("unchecked")
|
||||
void merge(GraphImplementor<J>... others);
|
||||
|
||||
SessionFactoryImplementor sessionFactory();
|
||||
JpaMetamodel jpaMetamodel();
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
|
|
@ -20,10 +20,12 @@ import javax.persistence.metamodel.PluralAttribute;
|
|||
import javax.persistence.metamodel.Type;
|
||||
|
||||
import org.hibernate.annotations.common.AssertionFailure;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoaderService;
|
||||
import org.hibernate.internal.EntityManagerMessageLogger;
|
||||
import org.hibernate.internal.HEMLogging;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.Component;
|
||||
import org.hibernate.mapping.List;
|
||||
import org.hibernate.mapping.Map;
|
||||
import org.hibernate.mapping.OneToMany;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
|
@ -46,10 +48,10 @@ import org.hibernate.metamodel.model.domain.internal.SingularAttributeImpl;
|
|||
import org.hibernate.property.access.internal.PropertyAccessMapImpl;
|
||||
import org.hibernate.property.access.spi.Getter;
|
||||
import org.hibernate.tuple.entity.EntityMetamodel;
|
||||
import org.hibernate.type.ComponentType;
|
||||
import org.hibernate.type.EmbeddedComponentType;
|
||||
import org.hibernate.type.EntityType;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptorRegistry;
|
||||
|
||||
/**
|
||||
* A factory for building {@link Attribute} instances. Exposes 3 main services for building<ol>
|
||||
|
@ -233,23 +235,50 @@ public class AttributeFactory {
|
|||
}
|
||||
case EMBEDDABLE: {
|
||||
final Component component = (Component) typeContext.getHibernateValue();
|
||||
final EmbeddableTypeImpl<Y> embeddableType;
|
||||
|
||||
Class javaType;
|
||||
if ( component.getComponentClassName() == null ) {
|
||||
javaType = typeContext.getJpaBindableType();
|
||||
if ( component.getComponentClass() != null
|
||||
|| component.getComponentClassName() != null ) {
|
||||
// we should have a non-dynamic embeddable
|
||||
|
||||
final Class embeddableClass;
|
||||
if ( component.getComponentClass() != null ) {
|
||||
embeddableClass = component.getComponentClass();
|
||||
}
|
||||
else {
|
||||
embeddableClass = context.getSessionFactory()
|
||||
.getServiceRegistry()
|
||||
.getService( ClassLoaderService.class )
|
||||
.classForName( component.getComponentClassName() );
|
||||
}
|
||||
|
||||
final EmbeddableDomainType cached = context.locateEmbeddable( embeddableClass );
|
||||
if ( cached != null ) {
|
||||
return cached;
|
||||
}
|
||||
|
||||
final JavaTypeDescriptorRegistry registry = context.getSessionFactory()
|
||||
.getMetamodel()
|
||||
.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry();
|
||||
final JavaTypeDescriptor javaTypeDescriptor = registry.resolveDescriptor( embeddableClass );
|
||||
|
||||
embeddableType = new EmbeddableTypeImpl<Y>(
|
||||
javaTypeDescriptor,
|
||||
context.getSessionFactory().getQueryEngine().getCriteriaBuilder()
|
||||
);
|
||||
|
||||
context.registerEmbeddableType( embeddableType );
|
||||
|
||||
return embeddableType;
|
||||
}
|
||||
else {
|
||||
javaType = component.getComponentClass();
|
||||
embeddableType = new EmbeddableTypeImpl(
|
||||
component.getRoleName(),
|
||||
context.getSessionFactory().getQueryEngine().getCriteriaBuilder()
|
||||
);
|
||||
}
|
||||
|
||||
final EmbeddableTypeImpl<Y> embeddableType = new EmbeddableTypeImpl<Y>(
|
||||
javaType,
|
||||
typeContext.getAttributeMetadata().getOwnerType(),
|
||||
(ComponentType) typeContext.getHibernateValue().getType(),
|
||||
context.getSessionFactory().getQueryEngine().getCriteriaBuilder()
|
||||
);
|
||||
context.registerEmbeddableType( embeddableType );
|
||||
|
||||
final EmbeddableTypeImpl.InFlightAccess<Y> inFlightAccess = embeddableType.getInFlightAccess();
|
||||
final Iterator<Property> subProperties = component.getPropertyIterator();
|
||||
while ( subProperties.hasNext() ) {
|
||||
|
@ -548,6 +577,9 @@ public class AttributeFactory {
|
|||
indexClassification = AttributeClassification.BASIC;
|
||||
}
|
||||
}
|
||||
else if ( value instanceof List ) {
|
||||
indexClassification = AttributeClassification.BASIC;
|
||||
}
|
||||
else {
|
||||
indexClassification = null;
|
||||
}
|
||||
|
@ -780,7 +812,7 @@ public class AttributeFactory {
|
|||
implements PluralAttributeMetadata<X, Y, E> {
|
||||
private final PluralAttribute.CollectionType attributeCollectionType;
|
||||
private final AttributeClassification elementClassification;
|
||||
private final AttributeClassification keyClassification;
|
||||
private final AttributeClassification listIndexOrMapKeyClassification;
|
||||
private final Class elementJavaType;
|
||||
private final Class keyJavaType;
|
||||
private final ValueContext elementValueContext;
|
||||
|
@ -792,14 +824,14 @@ public class AttributeFactory {
|
|||
Member member,
|
||||
AttributeClassification attributeClassification,
|
||||
AttributeClassification elementClassification,
|
||||
AttributeClassification keyClassification) {
|
||||
AttributeClassification listIndexOrMapKeyClassification) {
|
||||
super( propertyMapping, ownerType, member, attributeClassification );
|
||||
this.attributeCollectionType = determineCollectionType( getJavaType() );
|
||||
this.elementClassification = elementClassification;
|
||||
this.keyClassification = keyClassification;
|
||||
this.listIndexOrMapKeyClassification = listIndexOrMapKeyClassification;
|
||||
|
||||
ParameterizedType signatureType = getSignatureType( member );
|
||||
if ( this.keyClassification == null ) {
|
||||
if ( this.listIndexOrMapKeyClassification == null ) {
|
||||
elementJavaType = signatureType != null ?
|
||||
getClassFromGenericArgument( signatureType.getActualTypeArguments()[0] ) :
|
||||
Object.class; //FIXME and honor targetEntity?
|
||||
|
@ -843,7 +875,7 @@ public class AttributeFactory {
|
|||
};
|
||||
|
||||
// interpret the key, if one
|
||||
if ( this.keyClassification != null ) {
|
||||
if ( this.listIndexOrMapKeyClassification != null ) {
|
||||
this.keyValueContext = new ValueContext() {
|
||||
public Value getHibernateValue() {
|
||||
return ( (Map) getPropertyMapping().getValue() ).getIndex();
|
||||
|
@ -854,7 +886,7 @@ public class AttributeFactory {
|
|||
}
|
||||
|
||||
public ValueClassification getValueClassification() {
|
||||
switch ( PluralAttributeMetadataImpl.this.keyClassification ) {
|
||||
switch ( PluralAttributeMetadataImpl.this.listIndexOrMapKeyClassification ) {
|
||||
case EMBEDDED: {
|
||||
return ValueClassification.EMBEDDABLE;
|
||||
}
|
||||
|
@ -968,6 +1000,8 @@ public class AttributeFactory {
|
|||
final EmbeddableDomainType embeddableType = (EmbeddableDomainType<?>) attributeContext.getOwnerType();
|
||||
final String attributeName = attributeContext.getPropertyMapping().getName();
|
||||
|
||||
final Component component = (Component) attributeContext.getPropertyMapping().getValue();
|
||||
|
||||
final Getter getter = embeddableType.getHibernateType()
|
||||
.getComponentTuplizer()
|
||||
.getGetter( embeddableType.getHibernateType().getPropertyIndex( attributeName ) );
|
||||
|
|
|
@ -45,7 +45,6 @@ import org.hibernate.metamodel.model.domain.internal.AttributeContainer;
|
|||
import org.hibernate.metamodel.model.domain.internal.BasicTypeImpl;
|
||||
import org.hibernate.metamodel.model.domain.internal.EntityTypeImpl;
|
||||
import org.hibernate.metamodel.model.domain.internal.MappedSuperclassTypeImpl;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptorRegistry;
|
||||
|
||||
/**
|
||||
|
@ -73,7 +72,7 @@ class MetadataContext {
|
|||
private Map<String, EntityDomainType<?>> entityTypesByEntityName = new HashMap<>();
|
||||
private Map<PersistentClass, EntityDomainType<?>> entityTypesByPersistentClass = new HashMap<>();
|
||||
|
||||
private Set<EmbeddableDomainType<?>> embeddables = new HashSet<>();
|
||||
private Map<Class, EmbeddableDomainType<?>> embeddables = new HashMap<>();
|
||||
|
||||
private Map<MappedSuperclass, MappedSuperclassDomainType<?>> mappedSuperclassByMappedSuperclassMapping = new HashMap<>();
|
||||
private Map<MappedSuperclassDomainType<?>, PersistentClass> mappedSuperClassTypeToPersistentClass = new HashMap<>();
|
||||
|
@ -113,7 +112,7 @@ class MetadataContext {
|
|||
}
|
||||
|
||||
public Set<EmbeddableDomainType<?>> getEmbeddableTypeSet() {
|
||||
return Collections.unmodifiableSet( embeddables );
|
||||
return new HashSet<>( embeddables.values() );
|
||||
}
|
||||
|
||||
public Map<Class<?>, MappedSuperclassType<?>> getMappedSuperclassTypeMap() {
|
||||
|
@ -147,9 +146,10 @@ class MetadataContext {
|
|||
}
|
||||
|
||||
/*package*/ void registerEmbeddableType(EmbeddableDomainType<?> embeddableType) {
|
||||
if ( !( ignoreUnsupported && Map.class.isAssignableFrom( embeddableType.getExpressableJavaTypeDescriptor().getJavaType() ) ) ) {
|
||||
embeddables.add( embeddableType );
|
||||
}
|
||||
assert embeddableType.getJavaType() != null;
|
||||
assert ! Map.class.isAssignableFrom( embeddableType.getJavaType() );
|
||||
|
||||
embeddables.put( embeddableType.getJavaType(), embeddableType );
|
||||
}
|
||||
|
||||
/*package*/ void registerMappedSuperclassType(
|
||||
|
@ -170,6 +170,7 @@ class MetadataContext {
|
|||
*
|
||||
* @return Tne corresponding JPA {@link org.hibernate.type.EntityType}, or null if not yet processed.
|
||||
*/
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public EntityDomainType<?> locateEntityType(PersistentClass persistentClass) {
|
||||
return entityTypesByPersistentClass.get( persistentClass );
|
||||
}
|
||||
|
@ -194,16 +195,17 @@ class MetadataContext {
|
|||
*
|
||||
* @return The corresponding JPA {@link org.hibernate.type.EntityType}, or null.
|
||||
*/
|
||||
@SuppressWarnings({"unchecked"})
|
||||
@SuppressWarnings({"unchecked", "WeakerAccess"})
|
||||
public <E> EntityDomainType<E> locateEntityType(String entityName) {
|
||||
return (EntityDomainType) entityTypesByEntityName.get( entityName );
|
||||
}
|
||||
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public Map<String, EntityDomainType<?>> getEntityTypesByEntityName() {
|
||||
return Collections.unmodifiableMap( entityTypesByEntityName );
|
||||
}
|
||||
|
||||
@SuppressWarnings({"unchecked"})
|
||||
@SuppressWarnings({"unchecked", "WeakerAccess"})
|
||||
public void wrapUp() {
|
||||
if ( LOG.isTraceEnabled() ) {
|
||||
LOG.trace( "Wrapping up metadata context..." );
|
||||
|
@ -215,7 +217,6 @@ class MetadataContext {
|
|||
//we need to process types from superclasses to subclasses
|
||||
for ( Object mapping : orderedMappings ) {
|
||||
if ( PersistentClass.class.isAssignableFrom( mapping.getClass() ) ) {
|
||||
@SuppressWarnings("unchecked")
|
||||
final PersistentClass safeMapping = (PersistentClass) mapping;
|
||||
if ( LOG.isTraceEnabled() ) {
|
||||
LOG.trace( "Starting entity [" + safeMapping.getEntityName() + ']' );
|
||||
|
@ -258,7 +259,6 @@ class MetadataContext {
|
|||
}
|
||||
}
|
||||
else if ( MappedSuperclass.class.isAssignableFrom( mapping.getClass() ) ) {
|
||||
@SuppressWarnings("unchecked")
|
||||
final MappedSuperclass safeMapping = (MappedSuperclass) mapping;
|
||||
if ( LOG.isTraceEnabled() ) {
|
||||
LOG.trace( "Starting mapped superclass [" + safeMapping.getMappedClass().getName() + ']' );
|
||||
|
@ -299,7 +299,7 @@ class MetadataContext {
|
|||
}
|
||||
|
||||
if ( staticMetamodelScanEnabled ) {
|
||||
for ( EmbeddableDomainType embeddable : embeddables ) {
|
||||
for ( EmbeddableDomainType embeddable : embeddables.values() ) {
|
||||
populateStaticMetamodel( embeddable );
|
||||
}
|
||||
}
|
||||
|
@ -307,7 +307,7 @@ class MetadataContext {
|
|||
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private <X> void applyIdMetadata(PersistentClass persistentClass, IdentifiableDomainType<?> identifiableType) {
|
||||
private void applyIdMetadata(PersistentClass persistentClass, IdentifiableDomainType<?> identifiableType) {
|
||||
if ( persistentClass.hasIdentifierProperty() ) {
|
||||
final Property declaredIdentifierProperty = persistentClass.getDeclaredIdentifierProperty();
|
||||
if ( declaredIdentifierProperty != null ) {
|
||||
|
@ -551,13 +551,14 @@ class MetadataContext {
|
|||
}
|
||||
|
||||
public Set<MappedSuperclass> getUnusedMappedSuperclasses() {
|
||||
return new HashSet<MappedSuperclass>( knownMappedSuperclasses );
|
||||
return new HashSet<>( knownMappedSuperclasses );
|
||||
}
|
||||
|
||||
private final Map<Class<?>,BasicDomainType<?>> basicDomainTypeMap = new HashMap<>();
|
||||
|
||||
public <J> BasicDomainType<J> resolveBasicType(Class<J> javaType) {
|
||||
return basicDomainTypeMap.computeIfAbsent(
|
||||
//noinspection unchecked
|
||||
return (BasicDomainType) basicDomainTypeMap.computeIfAbsent(
|
||||
javaType,
|
||||
jt -> {
|
||||
final JavaTypeDescriptorRegistry registry = getSessionFactory()
|
||||
|
@ -566,6 +567,11 @@ class MetadataContext {
|
|||
.getJavaTypeDescriptorRegistry();
|
||||
return new BasicTypeImpl<>( registry.resolveDescriptor( javaType ) );
|
||||
}
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
public <J> EmbeddableDomainType<J> locateEmbeddable(Class<J> embeddableClass) {
|
||||
//noinspection unchecked
|
||||
return (EmbeddableDomainType<J>) embeddables.get( embeddableClass );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,27 +6,26 @@
|
|||
*/
|
||||
package org.hibernate.metamodel.model.domain;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public abstract class AbstractDomainType<J> implements DomainType<J> {
|
||||
private final SessionFactoryImplementor sessionFactory;
|
||||
public abstract class AbstractDomainType<J> implements SimpleDomainType<J> {
|
||||
private final JpaMetamodel jpaMetamodel;
|
||||
|
||||
private final JavaTypeDescriptor<J> javaTypeDescriptor;
|
||||
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public AbstractDomainType(
|
||||
JavaTypeDescriptor<J> javaTypeDescriptor,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
this.javaTypeDescriptor = javaTypeDescriptor;
|
||||
this.sessionFactory = sessionFactory;
|
||||
this.jpaMetamodel = jpaMetamodel;
|
||||
}
|
||||
|
||||
protected SessionFactoryImplementor sessionFactory() {
|
||||
return sessionFactory;
|
||||
protected JpaMetamodel jpaMetamodel() {
|
||||
return jpaMetamodel;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -13,8 +13,6 @@ import java.util.function.Consumer;
|
|||
import javax.persistence.metamodel.IdentifiableType;
|
||||
import javax.persistence.metamodel.SingularAttribute;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.metamodel.RepresentationMode;
|
||||
import org.hibernate.metamodel.model.domain.internal.AttributeContainer;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
|
@ -48,8 +46,8 @@ public abstract class AbstractIdentifiableType<J>
|
|||
boolean hasIdClass,
|
||||
boolean hasIdentifierProperty,
|
||||
boolean versioned,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( typeName, javaTypeDescriptor, superType, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( typeName, javaTypeDescriptor, superType, jpaMetamodel );
|
||||
this.hasIdClass = hasIdClass;
|
||||
this.hasIdentifierProperty = hasIdentifierProperty;
|
||||
this.isVersioned = versioned;
|
||||
|
|
|
@ -12,6 +12,7 @@ import java.util.HashMap;
|
|||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
import javax.persistence.metamodel.Attribute;
|
||||
import javax.persistence.metamodel.CollectionAttribute;
|
||||
import javax.persistence.metamodel.ListAttribute;
|
||||
|
@ -21,7 +22,6 @@ import javax.persistence.metamodel.PluralAttribute;
|
|||
import javax.persistence.metamodel.SetAttribute;
|
||||
import javax.persistence.metamodel.SingularAttribute;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.internal.SubGraphImpl;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.metamodel.RepresentationMode;
|
||||
|
@ -49,8 +49,8 @@ public abstract class AbstractManagedType<J>
|
|||
String hibernateTypeName,
|
||||
JavaTypeDescriptor<J> javaTypeDescriptor,
|
||||
ManagedDomainType<? super J> superType,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( javaTypeDescriptor, sessionFactory );
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super( javaTypeDescriptor, jpaMetamodel );
|
||||
this.hibernateTypeName = hibernateTypeName;
|
||||
this.superType = superType;
|
||||
|
||||
|
@ -74,6 +74,20 @@ public abstract class AbstractManagedType<J>
|
|||
return representationMode;
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public void visitAttributes(Consumer<PersistentAttribute<? super J, ?>> action) {
|
||||
visitDeclaredAttributes( (Consumer) action );
|
||||
if ( getSuperType() != null ) {
|
||||
getSuperType().visitAttributes( (Consumer) action );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitDeclaredAttributes(Consumer<PersistentAttribute<J, ?>> action) {
|
||||
declaredSingularAttributes.values().forEach( action );
|
||||
declaredPluralAttributes.values().forEach( action );
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
|
@ -555,17 +569,17 @@ public abstract class AbstractManagedType<J>
|
|||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public SubGraphImplementor<J> makeSubGraph() {
|
||||
return new SubGraphImpl( this, true, sessionFactory() );
|
||||
return new SubGraphImpl( this, true, jpaMetamodel() );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <S extends J> ManagedDomainType<S> findSubType(String subTypeName) {
|
||||
return DomainModelHelper.resolveSubType( this, subTypeName, sessionFactory() );
|
||||
return DomainModelHelper.resolveSubType( this, subTypeName, jpaMetamodel() );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <S extends J> ManagedDomainType<S> findSubType(Class<S> subType) {
|
||||
return DomainModelHelper.resolveSubType( this, subType, sessionFactory() );
|
||||
return DomainModelHelper.resolveSubType( this, subType, jpaMetamodel() );
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,86 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.metamodel.model.domain;
|
||||
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
import javax.persistence.metamodel.EmbeddableType;
|
||||
import javax.persistence.metamodel.EntityType;
|
||||
import javax.persistence.metamodel.ManagedType;
|
||||
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
* Hibernate extension to the JPA {@link javax.persistence.metamodel.Metamodel} contract
|
||||
*
|
||||
* @see org.hibernate.metamodel.spi.RuntimeModel
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface JpaMetamodel extends javax.persistence.metamodel.Metamodel {
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// Context
|
||||
|
||||
/**
|
||||
* todo (6.0) : should we expose JpaMetamodel from TypeConfiguration?
|
||||
*/
|
||||
TypeConfiguration getTypeConfiguration();
|
||||
|
||||
default ServiceRegistry getServiceRegistry() {
|
||||
return getTypeConfiguration().getServiceRegistry();
|
||||
}
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// Extended features
|
||||
|
||||
/**
|
||||
* Access to an entity supporting Hibernate's entity-name feature
|
||||
*/
|
||||
<X> EntityDomainType<X> entity(String entityName);
|
||||
|
||||
/**
|
||||
* Specialized handling for resolving entity-name references in
|
||||
* an HQL query
|
||||
*/
|
||||
<X> EntityDomainType<X> resolveHqlEntityReference(String entityName);
|
||||
|
||||
void visitManagedTypes(Consumer<ManagedDomainType<?>> action);
|
||||
|
||||
void visitEntityTypes(Consumer<EntityDomainType<?>> action);
|
||||
void visitRootEntityTypes(Consumer<EntityDomainType<?>> action);
|
||||
|
||||
void visitEmbeddables(Consumer<EmbeddableDomainType<?>> action);
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// Covariant returns
|
||||
|
||||
@Override
|
||||
<X> ManagedDomainType<X> managedType(Class<X> cls);
|
||||
|
||||
@Override
|
||||
<X> EntityDomainType<X> entity(Class<X> cls);
|
||||
|
||||
@Override
|
||||
<X> EmbeddableDomainType<X> embeddable(Class<X> cls);
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// JPA defined bulk accessors
|
||||
|
||||
@Override
|
||||
Set<ManagedType<?>> getManagedTypes();
|
||||
|
||||
@Override
|
||||
Set<EntityType<?>> getEntities();
|
||||
|
||||
@Override
|
||||
Set<EmbeddableType<?>> getEmbeddables();
|
||||
}
|
|
@ -21,25 +21,24 @@ public interface ManagedDomainType<J> extends SimpleDomainType<J>, ManagedType<J
|
|||
/**
|
||||
* Get the type name.
|
||||
*
|
||||
* For dynamic models ({@link RepresentationMode#MAP}), this returns the symbolic name
|
||||
* Generally speaking, this returns the name of the Java class. However, for
|
||||
* dynamic models ({@link RepresentationMode#MAP}), this returns the symbolic name
|
||||
* since the Java type is {@link java.util.Map}
|
||||
*
|
||||
* For typed models, this returns the name of the Java class
|
||||
*
|
||||
* @return The type name.
|
||||
*
|
||||
* @see #getRepresentationMode()
|
||||
*/
|
||||
String getTypeName();
|
||||
|
||||
RepresentationMode getRepresentationMode();
|
||||
|
||||
/**
|
||||
* This type's super type descriptor. Note : we define this on the managed
|
||||
* type descriptor in anticipation of supporting embeddable inheritance
|
||||
*/
|
||||
ManagedDomainType<? super J> getSuperType();
|
||||
|
||||
RepresentationMode getRepresentationMode();
|
||||
|
||||
void visitAttributes(Consumer<PersistentAttribute<? super J,?>> action);
|
||||
void visitDeclaredAttributes(Consumer<PersistentAttribute<J,?>> action);
|
||||
|
||||
|
|
|
@ -61,11 +61,6 @@ public abstract class AbstractAttribute<D,J,B> implements PersistentAttribute<D,
|
|||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPathName() {
|
||||
return getName();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<J> getJavaType() {
|
||||
return attributeType.getJavaType();
|
||||
|
|
|
@ -42,9 +42,9 @@ public abstract class AbstractPluralAttribute<D,C,E>
|
|||
AbstractManagedType<X> ownerType,
|
||||
SimpleDomainType<E> attrType,
|
||||
JavaTypeDescriptor<C> collectionClass,
|
||||
SimpleDomainType<K> keyType,
|
||||
SimpleDomainType<K> listIndexOrMapKeyType,
|
||||
NodeBuilder nodeBuilder) {
|
||||
return new PluralAttributeBuilder<>( ownerType, attrType, collectionClass, keyType, nodeBuilder );
|
||||
return new PluralAttributeBuilder<>( ownerType, attrType, collectionClass, listIndexOrMapKeyType, nodeBuilder );
|
||||
}
|
||||
|
||||
private final CollectionClassification classification;
|
||||
|
@ -94,6 +94,11 @@ public abstract class AbstractPluralAttribute<D,C,E>
|
|||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPathName() {
|
||||
return getName();
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return classification;
|
||||
|
|
|
@ -11,8 +11,11 @@ import java.util.Collection;
|
|||
import org.hibernate.NotYetImplementedFor6Exception;
|
||||
import org.hibernate.metamodel.model.domain.BagPersistentAttribute;
|
||||
import org.hibernate.query.sqm.SqmPathSource;
|
||||
import org.hibernate.query.sqm.produce.path.spi.SemanticPathPart;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationState;
|
||||
import org.hibernate.query.sqm.tree.SqmJoinType;
|
||||
import org.hibernate.query.sqm.tree.domain.SqmBagJoin;
|
||||
import org.hibernate.query.sqm.tree.from.SqmAttributeJoin;
|
||||
import org.hibernate.query.sqm.tree.from.SqmFrom;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
|
@ -34,4 +37,22 @@ class BagAttributeImpl<X, E>
|
|||
public SqmPathSource<?> findSubPathSource(String name) {
|
||||
throw new NotYetImplementedFor6Exception();
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmAttributeJoin createSqmJoin(
|
||||
SqmFrom lhs,
|
||||
SqmJoinType joinType,
|
||||
String alias,
|
||||
boolean fetched,
|
||||
SqmCreationState creationState) {
|
||||
//noinspection unchecked
|
||||
return new SqmBagJoin(
|
||||
lhs,
|
||||
this,
|
||||
alias,
|
||||
joinType,
|
||||
fetched,
|
||||
creationState.getCreationContext().getQueryEngine().getCriteriaBuilder()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,8 +16,8 @@ import org.hibernate.metamodel.model.domain.BasicDomainType;
|
|||
import org.hibernate.metamodel.model.domain.DomainType;
|
||||
import org.hibernate.metamodel.model.domain.EmbeddableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.spi.MetamodelImplementor;
|
||||
import org.hibernate.persister.entity.EntityPersister;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.query.sqm.SqmPathSource;
|
||||
|
@ -33,32 +33,26 @@ public class DomainModelHelper {
|
|||
public static <T, S extends T> ManagedDomainType<S> resolveSubType(
|
||||
ManagedDomainType<T> baseType,
|
||||
String subTypeName,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
final MetamodelImplementor metamodel = sessionFactory.getMetamodel();
|
||||
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
if ( baseType instanceof EmbeddableDomainType<?> ) {
|
||||
// todo : at least validate the string is a valid sub-type of the embeddable class?
|
||||
return (ManagedDomainType) baseType;
|
||||
}
|
||||
|
||||
final String importedClassName = metamodel.getImportedClassName( subTypeName );
|
||||
if ( importedClassName != null ) {
|
||||
// first, try to find it by name directly..
|
||||
ManagedDomainType<S> subManagedType = metamodel.entity( importedClassName );
|
||||
if ( subManagedType != null ) {
|
||||
return subManagedType;
|
||||
}
|
||||
// first, try to find it by name directly..
|
||||
ManagedDomainType<S> subManagedType = jpaMetamodel.entity( subTypeName );
|
||||
if ( subManagedType != null ) {
|
||||
return subManagedType;
|
||||
}
|
||||
|
||||
// it could still be a mapped-superclass
|
||||
try {
|
||||
final Class<S> subTypeClass = sessionFactory.getServiceRegistry()
|
||||
.getService( ClassLoaderService.class )
|
||||
.classForName( importedClassName );
|
||||
|
||||
return metamodel.managedType( subTypeClass );
|
||||
}
|
||||
catch (Exception ignore) {
|
||||
}
|
||||
// it could still be a mapped-superclass
|
||||
try {
|
||||
final Class javaType = jpaMetamodel.getServiceRegistry()
|
||||
.getService( ClassLoaderService.class )
|
||||
.classForName( subTypeName );
|
||||
return jpaMetamodel.managedType( javaType );
|
||||
}
|
||||
catch (Exception ignore) {
|
||||
}
|
||||
|
||||
throw new IllegalArgumentException( "Unknown sub-type name (" + baseType.getTypeName() + ") : " + subTypeName );
|
||||
|
@ -67,10 +61,9 @@ public class DomainModelHelper {
|
|||
public static <S> ManagedDomainType<S> resolveSubType(
|
||||
ManagedDomainType<? super S> baseType,
|
||||
Class<S> subTypeClass,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
// todo : validate the hierarchy-ness...
|
||||
final MetamodelImplementor metamodel = sessionFactory.getMetamodel();
|
||||
return metamodel.managedType( subTypeClass );
|
||||
return jpaMetamodel.managedType( subTypeClass );
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -9,13 +9,11 @@ package org.hibernate.metamodel.model.domain.internal;
|
|||
import java.io.Serializable;
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.internal.SubGraphImpl;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.metamodel.model.domain.AbstractManagedType;
|
||||
import org.hibernate.metamodel.model.domain.EmbeddableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.type.ComponentType;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
/**
|
||||
|
@ -29,33 +27,20 @@ public class EmbeddableTypeImpl<J>
|
|||
extends AbstractManagedType<J>
|
||||
implements EmbeddableDomainType<J>, Serializable {
|
||||
|
||||
private final ManagedDomainType<?> parent;
|
||||
private final ComponentType hibernateType;
|
||||
|
||||
public EmbeddableTypeImpl(
|
||||
JavaTypeDescriptor<J> javaTypeDescriptor,
|
||||
ManagedDomainType<?> parent,
|
||||
ComponentType hibernateType,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
super( javaTypeDescriptor.getJavaType().getName(), javaTypeDescriptor, null, sessionFactory );
|
||||
this.parent = parent;
|
||||
this.hibernateType = hibernateType;
|
||||
public EmbeddableTypeImpl(JavaTypeDescriptor<J> javaTypeDescriptor, NodeBuilder nodeBuilder) {
|
||||
super( javaTypeDescriptor.getJavaType().getName(), javaTypeDescriptor, null, nodeBuilder.getDomainModel() );
|
||||
}
|
||||
|
||||
public EmbeddableTypeImpl(
|
||||
String name,
|
||||
ManagedDomainType<?> parent,
|
||||
ComponentType hibernateType,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
NodeBuilder nodeBuilder) {
|
||||
//noinspection unchecked
|
||||
super(
|
||||
name,
|
||||
(JavaTypeDescriptor) sessionFactory.getMetamodel().getTypeConfiguration().getJavaTypeDescriptorRegistry().getDescriptor( Map.class ),
|
||||
(JavaTypeDescriptor) nodeBuilder.getDomainModel().getTypeConfiguration().getJavaTypeDescriptorRegistry().getDescriptor( Map.class ),
|
||||
null,
|
||||
sessionFactory
|
||||
nodeBuilder.getDomainModel()
|
||||
);
|
||||
this.parent = parent;
|
||||
this.hibernateType = hibernateType;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -63,17 +48,9 @@ public class EmbeddableTypeImpl<J>
|
|||
return PersistenceType.EMBEDDABLE;
|
||||
}
|
||||
|
||||
public ManagedDomainType<?> getParent() {
|
||||
return parent;
|
||||
}
|
||||
|
||||
public ComponentType getHibernateType() {
|
||||
return hibernateType;
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <S extends J> SubGraphImplementor<S> makeSubGraph(Class<S> subType) {
|
||||
return new SubGraphImpl( this, true, sessionFactory() );
|
||||
return new SubGraphImpl( this, true, jpaMetamodel() );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,7 +9,6 @@ package org.hibernate.metamodel.model.domain.internal;
|
|||
import java.io.Serializable;
|
||||
import javax.persistence.metamodel.EntityType;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.internal.SubGraphImpl;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
|
@ -17,8 +16,8 @@ import org.hibernate.metamodel.model.domain.AbstractIdentifiableType;
|
|||
import org.hibernate.metamodel.model.domain.DomainType;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.IdentifiableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.query.sqm.SqmPathSource;
|
||||
import org.hibernate.query.sqm.produce.path.spi.SemanticPathPart;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationState;
|
||||
import org.hibernate.query.sqm.tree.domain.SqmPath;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
@ -34,12 +33,11 @@ public class EntityTypeImpl<J>
|
|||
implements EntityDomainType<J>, Serializable {
|
||||
private final String jpaEntityName;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public EntityTypeImpl(
|
||||
JavaTypeDescriptor<J> javaTypeDescriptor,
|
||||
IdentifiableDomainType<? super J> superType,
|
||||
PersistentClass persistentClass,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super(
|
||||
persistentClass.getEntityName(),
|
||||
javaTypeDescriptor,
|
||||
|
@ -47,7 +45,7 @@ public class EntityTypeImpl<J>
|
|||
persistentClass.getDeclaredIdentifierMapper() != null || ( superType != null && superType.hasIdClass() ),
|
||||
persistentClass.hasIdentifierProperty(),
|
||||
persistentClass.isVersioned(),
|
||||
sessionFactory
|
||||
jpaMetamodel
|
||||
);
|
||||
this.jpaEntityName = persistentClass.getJpaEntityName();
|
||||
}
|
||||
|
@ -74,16 +72,7 @@ public class EntityTypeImpl<J>
|
|||
|
||||
@Override
|
||||
public SqmPathSource<?> findSubPathSource(String name) {
|
||||
return findAttribute( name );
|
||||
}
|
||||
|
||||
@Override
|
||||
public SemanticPathPart resolvePathPart(
|
||||
String name,
|
||||
String currentContextKey,
|
||||
boolean isTerminal,
|
||||
SqmCreationState creationState) {
|
||||
return findAttribute( name );
|
||||
return (SqmPathSource<?>) findAttribute( name );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -124,7 +113,7 @@ public class EntityTypeImpl<J>
|
|||
);
|
||||
}
|
||||
|
||||
return new SubGraphImpl( this, true, sessionFactory() );
|
||||
return new SubGraphImpl( this, true, jpaMetamodel() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -0,0 +1,146 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.metamodel.model.domain.internal;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoaderService;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoadingException;
|
||||
import org.hibernate.metamodel.model.domain.EmbeddableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.query.sqm.tree.domain.SqmPolymorphicRootDescriptor;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class JpaMetamodelImpl implements JpaMetamodel {
|
||||
private static final String INVALID_IMPORT = "";
|
||||
|
||||
private final TypeConfiguration typeConfiguration;
|
||||
|
||||
private final Map<String, EntityDomainType<?>> entityDescriptorMap;
|
||||
private final Map<Class, EntityDomainType<?>> strictEntityDescriptorMap;
|
||||
private final Map<Class, EmbeddableDomainType<?>> embeddableDescriptorMap;
|
||||
private final Map<Class,String> entityProxyInterfaceMap = new ConcurrentHashMap<>();
|
||||
|
||||
private final Map<String,String> nameToImportNameMap = new ConcurrentHashMap<>();
|
||||
private final Map<Class, SqmPolymorphicRootDescriptor<?>> polymorphicEntityReferenceMap = new ConcurrentHashMap<>();
|
||||
|
||||
public JpaMetamodelImpl(TypeConfiguration typeConfiguration) {
|
||||
this.typeConfiguration = typeConfiguration;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <X> EntityDomainType<X> resolveHqlEntityReference(String entityName) {
|
||||
final String rename = resolveImportedName( entityName );
|
||||
if ( rename != null ) {
|
||||
entityName = rename;
|
||||
}
|
||||
|
||||
final EntityDomainType<X> entityDescriptor = entity( entityName );
|
||||
if ( entityDescriptor != null ) {
|
||||
return entityDescriptor;
|
||||
}
|
||||
|
||||
final Class<X> requestedClass = resolveRequestedClass( entityName );
|
||||
if ( requestedClass != null ) {
|
||||
return resolveEntityReference( requestedClass );
|
||||
}
|
||||
|
||||
throw new IllegalArgumentException( "Could not resolve entity reference " + entityName );
|
||||
}
|
||||
|
||||
private String resolveImportedName(String name) {
|
||||
String result = nameToImportNameMap.get( name );
|
||||
if ( result == null ) {
|
||||
// see if the name is a fully-qualified class name
|
||||
try {
|
||||
getServiceRegistry().getService( ClassLoaderService.class ).classForName( name );
|
||||
|
||||
// it is a fully-qualified class name - add it to the cache
|
||||
// so we do not keep trying later
|
||||
nameToImportNameMap.put( name, name );
|
||||
return name;
|
||||
}
|
||||
catch ( ClassLoadingException cnfe ) {
|
||||
// it is a NOT fully-qualified class name - add a marker entry
|
||||
// so we do not keep trying later
|
||||
nameToImportNameMap.put( name, INVALID_IMPORT );
|
||||
return null;
|
||||
}
|
||||
}
|
||||
else {
|
||||
// explicitly check for same instance
|
||||
//noinspection StringEquality
|
||||
if ( result == INVALID_IMPORT ) {
|
||||
return null;
|
||||
}
|
||||
else {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private <X> Class<X> resolveRequestedClass(String entityName) {
|
||||
try {
|
||||
return getServiceRegistry().getService( ClassLoaderService.class ).classForName( entityName );
|
||||
}
|
||||
catch (ClassLoadingException e) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public <T> EntityDomainType<T> resolveEntityReference(Class<T> javaType) {
|
||||
// try the incoming Java type as a "strict" entity reference
|
||||
{
|
||||
final EntityDomainType<?> descriptor = strictEntityDescriptorMap.get( javaType );
|
||||
if ( descriptor != null ) {
|
||||
return (EntityDomainType<T>) descriptor;
|
||||
}
|
||||
}
|
||||
|
||||
// Next, try it as a proxy interface reference
|
||||
{
|
||||
final String proxyEntityName = entityProxyInterfaceMap.get( javaType );
|
||||
if ( proxyEntityName != null ) {
|
||||
return (EntityDomainType<T>) entityDescriptorMap.get( proxyEntityName );
|
||||
}
|
||||
}
|
||||
|
||||
// otherwise, try to handle it as a polymorphic reference
|
||||
{
|
||||
if ( polymorphicEntityReferenceMap.containsKey( javaType ) ) {
|
||||
return (EntityDomainType<T>) polymorphicEntityReferenceMap.get( javaType );
|
||||
}
|
||||
|
||||
final Set<EntityDomainType<?>> matchingDescriptors = new HashSet<>();
|
||||
visitEntityTypes(
|
||||
entityDomainType -> {
|
||||
if ( javaType.isAssignableFrom( entityDomainType.getJavaType() ) ) {
|
||||
matchingDescriptors.add( entityDomainType );
|
||||
}
|
||||
}
|
||||
);
|
||||
if ( !matchingDescriptors.isEmpty() ) {
|
||||
final SqmPolymorphicRootDescriptor descriptor = new SqmPolymorphicRootDescriptor(
|
||||
typeConfiguration.getJavaTypeDescriptorRegistry().resolveDescriptor( javaType ),
|
||||
matchingDescriptors
|
||||
);
|
||||
polymorphicEntityReferenceMap.put( javaType, descriptor );
|
||||
return descriptor;
|
||||
}
|
||||
}
|
||||
|
||||
throw new IllegalArgumentException( "Could not resolve entity reference : " + javaType.getName() );
|
||||
}
|
||||
}
|
|
@ -8,6 +8,7 @@ package org.hibernate.metamodel.model.domain.internal;
|
|||
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.metamodel.ValueClassification;
|
||||
import org.hibernate.metamodel.model.domain.ListPersistentAttribute;
|
||||
import org.hibernate.query.sqm.SqmPathSource;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationState;
|
||||
|
@ -22,10 +23,17 @@ import org.hibernate.query.sqm.tree.from.SqmFrom;
|
|||
class ListAttributeImpl<X, E> extends AbstractPluralAttribute<X, List<E>, E> implements ListPersistentAttribute<X, E> {
|
||||
private final SqmPathSource<Integer> indexPathSource;
|
||||
|
||||
ListAttributeImpl(PluralAttributeBuilder<X, List<E>, E, ?> xceBuilder) {
|
||||
super( xceBuilder );
|
||||
ListAttributeImpl(PluralAttributeBuilder<X, List<E>, E, ?> builder) {
|
||||
super( builder );
|
||||
|
||||
indexPathSource =
|
||||
//noinspection unchecked
|
||||
this.indexPathSource = (SqmPathSource) DomainModelHelper.resolveSqmPathSource(
|
||||
ValueClassification.BASIC,
|
||||
getName(),
|
||||
builder.getListIndexOrMapKeyType(),
|
||||
BindableType.PLURAL_ATTRIBUTE,
|
||||
builder.getNodeBuilder()
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -33,6 +41,11 @@ class ListAttributeImpl<X, E> extends AbstractPluralAttribute<X, List<E>, E> imp
|
|||
return CollectionType.LIST;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmPathSource<Integer> getIndexPathSource() {
|
||||
return indexPathSource;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmAttributeJoin createSqmJoin(
|
||||
SqmFrom lhs,
|
||||
|
|
|
@ -7,12 +7,11 @@
|
|||
package org.hibernate.metamodel.model.domain.internal;
|
||||
|
||||
import org.hibernate.cfg.NotYetImplementedException;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.mapping.MappedSuperclass;
|
||||
import org.hibernate.metamodel.RepresentationMode;
|
||||
import org.hibernate.metamodel.model.domain.AbstractIdentifiableType;
|
||||
import org.hibernate.metamodel.model.domain.IdentifiableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.MappedSuperclassDomainType;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
|
@ -25,7 +24,7 @@ public class MappedSuperclassTypeImpl<X> extends AbstractIdentifiableType<X> imp
|
|||
JavaTypeDescriptor<X> javaTypeDescriptor,
|
||||
MappedSuperclass mappedSuperclass,
|
||||
IdentifiableDomainType<? super X> superType,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
JpaMetamodel jpaMetamodel) {
|
||||
super(
|
||||
javaTypeDescriptor.getJavaType().getName(),
|
||||
javaTypeDescriptor,
|
||||
|
@ -33,7 +32,7 @@ public class MappedSuperclassTypeImpl<X> extends AbstractIdentifiableType<X> imp
|
|||
mappedSuperclass.getDeclaredIdentifierMapper() != null || ( superType != null && superType.hasIdClass() ),
|
||||
mappedSuperclass.hasIdentifierProperty(),
|
||||
mappedSuperclass.isVersioned(),
|
||||
sessionFactory
|
||||
jpaMetamodel
|
||||
);
|
||||
}
|
||||
|
||||
|
|
|
@ -13,8 +13,8 @@ import java.util.Map;
|
|||
import java.util.Set;
|
||||
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.metamodel.AttributeClassification;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.SimpleDomainType;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
|
@ -29,7 +29,7 @@ public class PluralAttributeBuilder<D, C, E, K> {
|
|||
|
||||
private final NodeBuilder nodeBuilder;
|
||||
|
||||
private SimpleDomainType<K> keyType;
|
||||
private SimpleDomainType<K> listIndexOrMapKeyType;
|
||||
|
||||
private AttributeClassification attributeClassification;
|
||||
private CollectionClassification collectionClassification;
|
||||
|
@ -42,12 +42,12 @@ public class PluralAttributeBuilder<D, C, E, K> {
|
|||
ManagedDomainType<D> ownerType,
|
||||
SimpleDomainType<E> elementType,
|
||||
JavaTypeDescriptor<C> collectionJavaTypeDescriptor,
|
||||
SimpleDomainType<K> keyType,
|
||||
SimpleDomainType<K> listIndexOrMapKeyType,
|
||||
NodeBuilder nodeBuilder) {
|
||||
this.declaringType = ownerType;
|
||||
this.valueType = elementType;
|
||||
this.collectionJavaTypeDescriptor = collectionJavaTypeDescriptor;
|
||||
this.keyType = keyType;
|
||||
this.listIndexOrMapKeyType = listIndexOrMapKeyType;
|
||||
this.nodeBuilder = nodeBuilder;
|
||||
}
|
||||
|
||||
|
@ -67,8 +67,8 @@ public class PluralAttributeBuilder<D, C, E, K> {
|
|||
return collectionClassification;
|
||||
}
|
||||
|
||||
public SimpleDomainType<K> getKeyType() {
|
||||
return keyType;
|
||||
public SimpleDomainType<K> getListIndexOrMapKeyType() {
|
||||
return listIndexOrMapKeyType;
|
||||
}
|
||||
|
||||
public JavaTypeDescriptor<C> getCollectionJavaTypeDescriptor() {
|
||||
|
|
|
@ -90,6 +90,11 @@ public class SingularAttributeImpl<D,J>
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPathName() {
|
||||
return getName();
|
||||
}
|
||||
|
||||
@Override
|
||||
public SimpleDomainType<J> getSqmPathType() {
|
||||
//noinspection unchecked
|
||||
|
|
|
@ -0,0 +1,175 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.metamodel.spi;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.graph.RootGraph;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.NavigableRole;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.persister.entity.EntityPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
* Access to information about Hibernate's runtime type system
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface RuntimeModel {
|
||||
TypeConfiguration getTypeConfiguration();
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// Entity descriptors
|
||||
|
||||
/**
|
||||
* Given a JPA entity domain type, get the associated Hibernate entity descriptor
|
||||
*/
|
||||
EntityPersister resolveEntityDescriptor(EntityDomainType<?> entityDomainType);
|
||||
|
||||
/**
|
||||
* Visit all entity mapping descriptors defined in the model
|
||||
*/
|
||||
void visitEntityDescriptors(Consumer<EntityPersister> action);
|
||||
|
||||
/**
|
||||
* Get an entity mapping descriptor based on its Hibernate entity-name
|
||||
*
|
||||
* @throws IllegalArgumentException if the name does not refer to an entity
|
||||
*
|
||||
* @see #findEntityDescriptor
|
||||
*/
|
||||
EntityPersister getEntityDescriptor(String entityName);
|
||||
|
||||
/**
|
||||
* Get an entity mapping descriptor based on its NavigableRole.
|
||||
*
|
||||
* @throws IllegalArgumentException if the name does not refer to an entity
|
||||
*
|
||||
* @see #findEntityDescriptor
|
||||
*/
|
||||
EntityPersister getEntityDescriptor(NavigableRole name);
|
||||
|
||||
/**
|
||||
* Get an entity mapping descriptor based on its Class.
|
||||
*
|
||||
* @throws IllegalArgumentException if the name does not refer to an entity
|
||||
*
|
||||
* @see #findEntityDescriptor
|
||||
*/
|
||||
EntityPersister getEntityDescriptor(Class entityJavaType);
|
||||
|
||||
/**
|
||||
* Find an entity mapping descriptor based on its Hibernate entity-name.
|
||||
*
|
||||
* @apiNote Returns {@code null} rather than throwing exception
|
||||
*/
|
||||
EntityPersister findEntityDescriptor(String entityName);
|
||||
|
||||
/**
|
||||
* Find an entity mapping descriptor based on its Class.
|
||||
*
|
||||
* @apiNote Returns {@code null} rather than throwing exception
|
||||
*/
|
||||
EntityPersister findEntityDescriptor(Class entityJavaType);
|
||||
|
||||
/**
|
||||
* Locate an entity mapping descriptor by Class. The passed Class might
|
||||
* refer to either the entity Class directly, or it might name a proxy
|
||||
* interface for the entity. This method accounts for both, preferring the
|
||||
* direct entity name.
|
||||
*
|
||||
* @throws org.hibernate.UnknownEntityTypeException If a matching EntityPersister cannot be located
|
||||
*/
|
||||
EntityPersister locateEntityDescriptor(Class byClass);
|
||||
|
||||
/**
|
||||
* @see #locateEntityDescriptor
|
||||
*
|
||||
* @deprecated (since 6.0) use {@link #locateEntityDescriptor(Class)} instead
|
||||
*/
|
||||
@Deprecated
|
||||
default EntityPersister locateEntityPersister(Class byClass) {
|
||||
return locateEntityDescriptor( byClass );
|
||||
}
|
||||
|
||||
/**
|
||||
* Locate the entity persister by name.
|
||||
*
|
||||
* @return The located EntityPersister, never {@code null}
|
||||
*
|
||||
* @throws org.hibernate.UnknownEntityTypeException If a matching EntityPersister cannot be located
|
||||
*
|
||||
* @deprecated (since 6.0) - use {@link #getEntityDescriptor(String)} instead
|
||||
*/
|
||||
@Deprecated
|
||||
EntityPersister locateEntityPersister(String byName);
|
||||
|
||||
String getImportedName(String name);
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// Collection descriptors
|
||||
|
||||
/**
|
||||
* Visit the mapping descriptors for all collections defined in the model
|
||||
*/
|
||||
void visitCollectionDescriptors(Consumer<CollectionPersister> action);
|
||||
|
||||
/**
|
||||
* Get a collection mapping descriptor based on its role
|
||||
*
|
||||
* @throws IllegalArgumentException if the role does not refer to a collection
|
||||
*
|
||||
* @see #findCollectionDescriptor
|
||||
*/
|
||||
CollectionPersister getCollectionDescriptor(String role);
|
||||
|
||||
/**
|
||||
* Get a collection mapping descriptor based on its role
|
||||
*
|
||||
* @throws IllegalArgumentException if the role does not refer to a collection
|
||||
*
|
||||
* @see #findCollectionDescriptor
|
||||
*/
|
||||
CollectionPersister getCollectionDescriptor(NavigableRole role);
|
||||
|
||||
/**
|
||||
* Find a collection mapping descriptor based on its role. Returns
|
||||
* {@code null} if the role does not refer to a collection
|
||||
*
|
||||
* @see #findCollectionDescriptor
|
||||
*/
|
||||
CollectionPersister findCollectionDescriptor(NavigableRole role);
|
||||
|
||||
/**
|
||||
* Find a collection mapping descriptor based on its role. Returns
|
||||
* {@code null} if the role does not refer to a collection
|
||||
*
|
||||
* @see #findCollectionDescriptor
|
||||
*/
|
||||
CollectionPersister findCollectionDescriptor(String role);
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// JPA entity graphs
|
||||
|
||||
RootGraph<?> findNamedGraph(String name);
|
||||
void visitNamedGraphs(Consumer<RootGraph<?>> action);
|
||||
|
||||
RootGraph<?> defaultGraph(String entityName);
|
||||
RootGraph<?> defaultGraph(Class entityJavaType);
|
||||
RootGraph<?> defaultGraph(EntityPersister entityDescriptor);
|
||||
RootGraph<?> defaultGraph(EntityDomainType<?> entityDomainType);
|
||||
|
||||
List<RootGraph<?>> findRootGraphsForType(Class baseEntityJavaType);
|
||||
List<RootGraph<?>> findRootGraphsForType(String baseEntityName);
|
||||
List<RootGraph<?>> findRootGraphsForType(EntityPersister baseEntityDescriptor);
|
||||
|
||||
}
|
|
@ -0,0 +1,82 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.query;
|
||||
|
||||
/**
|
||||
* Defines the comparison operators. We could also get away with
|
||||
* only 3 and use negation...
|
||||
*/
|
||||
public enum ComparisonOperator {
|
||||
EQUAL {
|
||||
public ComparisonOperator negated() {
|
||||
return NOT_EQUAL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return "=";
|
||||
}
|
||||
},
|
||||
|
||||
NOT_EQUAL {
|
||||
public ComparisonOperator negated() {
|
||||
return EQUAL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return "!=";
|
||||
}
|
||||
},
|
||||
|
||||
LESS_THAN {
|
||||
public ComparisonOperator negated() {
|
||||
return GREATER_THAN_OR_EQUAL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return "<";
|
||||
}
|
||||
},
|
||||
|
||||
LESS_THAN_OR_EQUAL {
|
||||
public ComparisonOperator negated() {
|
||||
return GREATER_THAN;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return "<=";
|
||||
}
|
||||
},
|
||||
|
||||
GREATER_THAN {
|
||||
public ComparisonOperator negated() {
|
||||
return LESS_THAN_OR_EQUAL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return ">";
|
||||
}
|
||||
},
|
||||
|
||||
GREATER_THAN_OR_EQUAL {
|
||||
public ComparisonOperator negated() {
|
||||
return LESS_THAN;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String sqlText() {
|
||||
return ">=";
|
||||
}
|
||||
};
|
||||
|
||||
public abstract ComparisonOperator negated();
|
||||
public abstract String sqlText();
|
||||
}
|
|
@ -0,0 +1,37 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.query;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Represents the type of instantiation to be performed.
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public enum DynamicInstantiationNature {
|
||||
/**
|
||||
* The target names a Class to be instantiated. This is the only form
|
||||
* of dynamic instantiation that is JPA-compliant.
|
||||
*/
|
||||
CLASS,
|
||||
/**
|
||||
* The target identified a {@link Map} instantiation. The
|
||||
* result for each "row" will be a Map whose key is the alias (or name
|
||||
* of the selected attribute is no alias) and whose value is the
|
||||
* corresponding value read from the JDBC results. Similar to JPA's
|
||||
* named-Tuple support.
|
||||
*/
|
||||
MAP,
|
||||
/**
|
||||
* The target identified a {@link List} instantiation. The
|
||||
* result for each "row" will be a List rather than an array. Similar
|
||||
* to JPA's positional-Tuple support.
|
||||
*/
|
||||
LIST
|
||||
}
|
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.query.hql.internal;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
import org.antlr.v4.runtime.CharStreams;
|
||||
import org.antlr.v4.runtime.CommonTokenStream;
|
||||
import org.antlr.v4.runtime.Token;
|
||||
|
||||
/**
|
||||
* Leverages Antlr to build a parse tree from an HQL query
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class HqlParseTreeBuilder {
|
||||
private static final Logger log = Logger.getLogger( HqlParseTreeBuilder.class );
|
||||
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final HqlParseTreeBuilder INSTANCE = new HqlParseTreeBuilder();
|
||||
|
||||
public HqlParser parseHql(String hql) {
|
||||
// Build the lexer
|
||||
HqlLexer hqlLexer = new HqlLexer( CharStreams.fromString( hql ) );
|
||||
|
||||
// Build the parser...
|
||||
return new HqlParser( new CommonTokenStream( hqlLexer ) ) {
|
||||
@Override
|
||||
protected void logUseOfReservedWordAsIdentifier(Token token) {
|
||||
log.debugf( "Encountered use of reserved word as identifier : " + token.getText() );
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
|
@ -0,0 +1,133 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.query.hql.internal;
|
||||
|
||||
import org.hibernate.query.QueryLogger;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
import org.antlr.v4.runtime.ParserRuleContext;
|
||||
import org.antlr.v4.runtime.tree.ParseTreeWalker;
|
||||
|
||||
/**
|
||||
* Used to
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public class HqlParseTreePrinter extends HqlParserBaseListener {
|
||||
private static final Logger HQL_LOGGER = QueryLogger.subLogger( "hql.parseTree" );
|
||||
private static final boolean LOG_DEBUG_ENABLED = HQL_LOGGER.isDebugEnabled();
|
||||
|
||||
public static void logStatementParseTree(HqlParser parser) {
|
||||
if ( !LOG_DEBUG_ENABLED ) {
|
||||
return;
|
||||
}
|
||||
|
||||
final HqlParseTreePrinter walker = new HqlParseTreePrinter( parser );
|
||||
ParseTreeWalker.DEFAULT.walk( walker, parser.statement() );
|
||||
|
||||
HQL_LOGGER.debugf( "HQL parse-tree:\n%s", walker.buffer.toString() );
|
||||
|
||||
parser.reset();
|
||||
}
|
||||
|
||||
public static void logOrderByParseTree(HqlParser parser) {
|
||||
if ( !LOG_DEBUG_ENABLED ) {
|
||||
return;
|
||||
}
|
||||
|
||||
final HqlParseTreePrinter walker = new HqlParseTreePrinter( parser );
|
||||
ParseTreeWalker.DEFAULT.walk( walker, parser.orderByClause() );
|
||||
|
||||
HQL_LOGGER.debugf( "Mapping order-by parse-tree:\n%s", walker.buffer.toString() );
|
||||
|
||||
parser.reset();
|
||||
}
|
||||
|
||||
private final HqlParser parser;
|
||||
private final StringBuffer buffer = new StringBuffer();
|
||||
private int depth = 2;
|
||||
|
||||
public HqlParseTreePrinter(HqlParser parser) {
|
||||
this.parser = parser;
|
||||
}
|
||||
|
||||
private enum LineType {
|
||||
ENTER,
|
||||
EXIT
|
||||
}
|
||||
|
||||
@Override
|
||||
public void enterEveryRule(ParserRuleContext ctx) {
|
||||
final String ruleName = parser.getRuleNames()[ctx.getRuleIndex()];
|
||||
|
||||
if ( !ruleName.endsWith( "Keyword" ) ) {
|
||||
applyLine( LineType.ENTER, ruleName, ruleTypeName( ctx.getClass() ), ctx.getText() );
|
||||
}
|
||||
|
||||
super.enterEveryRule( ctx );
|
||||
}
|
||||
|
||||
private String ruleTypeName(Class<? extends ParserRuleContext> ruleCtxClass) {
|
||||
final String name = ruleCtxClass.getSimpleName();
|
||||
|
||||
final int position = name.lastIndexOf( "Context" );
|
||||
if ( position > 1 ) {
|
||||
return name.substring( 0, position );
|
||||
}
|
||||
else {
|
||||
// todo (6.0) : does this ever happen?
|
||||
return name;
|
||||
}
|
||||
}
|
||||
|
||||
private void applyLine(
|
||||
LineType lineType,
|
||||
String ruleName,
|
||||
String ruleTypeName,
|
||||
String ctxText) {
|
||||
applyLinePadding( lineType );
|
||||
|
||||
buffer.append( '[' ).append( ruleName );
|
||||
|
||||
if ( ! ruleTypeName.equalsIgnoreCase( ruleName ) ) {
|
||||
buffer.append( " (" ).append( ruleTypeName ).append( ')' );
|
||||
}
|
||||
|
||||
buffer.append( ']' )
|
||||
.append( " - `" ).append( ctxText ).append( '`' )
|
||||
.append( '\n' );
|
||||
}
|
||||
|
||||
private void applyLinePadding(LineType lineType) {
|
||||
if ( lineType == LineType.ENTER ) {
|
||||
pad( depth++ );
|
||||
buffer.append( "-> " );
|
||||
}
|
||||
else {
|
||||
pad( --depth );
|
||||
buffer.append( "<- " );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private String pad(int depth) {
|
||||
for ( int i = 0; i < depth; i++ ) {
|
||||
buffer.append( " " );
|
||||
}
|
||||
return buffer.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void exitEveryRule(ParserRuleContext ctx) {
|
||||
super.exitEveryRule( ctx );
|
||||
|
||||
final String ruleName = parser.getRuleNames()[ctx.getRuleIndex()];
|
||||
|
||||
applyLine( LineType.EXIT, ruleName, ruleTypeName( ctx.getClass() ), ctx.getText() );
|
||||
}
|
||||
}
|
|
@ -21,26 +21,16 @@ import org.hibernate.NullPrecedence;
|
|||
import org.hibernate.SortOrder;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoaderService;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoadingException;
|
||||
import org.hibernate.collection.spi.CollectionClassification;
|
||||
import org.hibernate.internal.util.collections.Stack;
|
||||
import org.hibernate.internal.util.collections.StandardStack;
|
||||
import org.hibernate.metamodel.model.mapping.EntityTypeDescriptor;
|
||||
import org.hibernate.metamodel.model.mapping.IdentifiableTypeDescriptor;
|
||||
import org.hibernate.metamodel.model.mapping.PersistentCollectionDescriptor;
|
||||
import org.hibernate.metamodel.model.mapping.spi.AllowableFunctionReturnType;
|
||||
import org.hibernate.metamodel.model.mapping.spi.BagPersistentAttribute;
|
||||
import org.hibernate.metamodel.model.mapping.spi.EntityValuedNavigable;
|
||||
import org.hibernate.metamodel.model.mapping.spi.ListPersistentAttribute;
|
||||
import org.hibernate.metamodel.model.mapping.spi.MapPersistentAttribute;
|
||||
import org.hibernate.metamodel.model.mapping.spi.Navigable;
|
||||
import org.hibernate.metamodel.model.mapping.spi.NavigableContainer;
|
||||
import org.hibernate.metamodel.model.mapping.spi.PluralValuedNavigable;
|
||||
import org.hibernate.metamodel.model.mapping.spi.SingularPersistentAttribute;
|
||||
import org.hibernate.metamodel.model.domain.AllowableFunctionReturnType;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.PluralPersistentAttribute;
|
||||
import org.hibernate.query.BinaryArithmeticOperator;
|
||||
import org.hibernate.query.ComparisonOperator;
|
||||
import org.hibernate.query.QueryLogger;
|
||||
import org.hibernate.query.UnaryArithmeticOperator;
|
||||
import org.hibernate.query.hql.DotIdentifierConsumer;
|
||||
import org.hibernate.query.spi.ComparisonOperator;
|
||||
import org.hibernate.query.sqm.LiteralNumberFormatException;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.query.sqm.ParsingException;
|
||||
|
@ -143,12 +133,8 @@ import org.hibernate.query.sqm.tree.select.SqmSortSpecification;
|
|||
import org.hibernate.query.sqm.tree.select.SqmSubQuery;
|
||||
import org.hibernate.query.sqm.tree.update.SqmUpdateStatement;
|
||||
import org.hibernate.sql.TrimSpec;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.BasicValuedExpressableType;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.EntityValuedExpressableType;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.ExpressableType;
|
||||
import org.hibernate.type.StandardBasicTypes;
|
||||
import org.hibernate.type.descriptor.java.spi.BasicJavaDescriptor;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
|
@ -326,7 +312,7 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
|
||||
@Override
|
||||
public SqmInsertSelectStatement visitInsertStatement(HqlParser.InsertStatementContext ctx) {
|
||||
final EntityTypeDescriptor<?> targetType = visitEntityName( ctx.insertSpec().intoSpec().entityName() );
|
||||
final EntityDomainType<?> targetType = visitEntityName( ctx.insertSpec().intoSpec().entityName() );
|
||||
|
||||
final SqmRoot<?> root = new SqmRoot<>( targetType, null, creationContext.getNodeBuilder() );
|
||||
processingStateStack.getCurrent().getPathRegistry().register( root );
|
||||
|
@ -636,7 +622,7 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
final JavaTypeDescriptor jtd = creationContext.getDomainModel()
|
||||
.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getOrMakeJavaDescriptor( targetJavaType );
|
||||
.resolveDescriptor( targetJavaType );
|
||||
dynamicInstantiation = SqmDynamicInstantiation.forClassInstantiation(
|
||||
jtd,
|
||||
creationContext.getNodeBuilder()
|
||||
|
@ -837,21 +823,21 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
}
|
||||
|
||||
@Override
|
||||
public EntityTypeDescriptor<?> visitEntityName(HqlParser.EntityNameContext parserEntityName) {
|
||||
public EntityDomainType<?> visitEntityName(HqlParser.EntityNameContext parserEntityName) {
|
||||
final String entityName = parserEntityName.dotIdentifierSequence().getText();
|
||||
final EntityValuedExpressableType entityReference = resolveEntityReference( entityName );
|
||||
final EntityDomainType entityReference = resolveEntityReference( entityName );
|
||||
if ( entityReference == null ) {
|
||||
throw new UnknownEntityException( "Could not resolve entity name [" + entityName + "] as DML target", entityName );
|
||||
}
|
||||
|
||||
return entityReference.getEntityDescriptor();
|
||||
return entityReference;
|
||||
}
|
||||
|
||||
private EntityValuedExpressableType resolveEntityReference(String entityName) {
|
||||
private EntityDomainType resolveEntityReference(String entityName) {
|
||||
log.debugf( "Attempting to resolve path [%s] as entity reference...", entityName );
|
||||
EntityValuedExpressableType reference = null;
|
||||
EntityDomainType reference = null;
|
||||
try {
|
||||
reference = creationContext.getDomainModel().resolveEntityReference( entityName );
|
||||
reference = creationContext.getDomainModel().entity( entityName );
|
||||
}
|
||||
catch (Exception ignore) {
|
||||
}
|
||||
|
@ -904,12 +890,12 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
|
||||
log.debugf( "Handling root path - %s", name );
|
||||
|
||||
final EntityTypeDescriptor entityDescriptor = getCreationContext().getDomainModel().resolveEntityReference( name );
|
||||
final EntityDomainType entityDescriptor = getCreationContext().getDomainModel().resolveHqlEntityReference( name );
|
||||
|
||||
if ( entityDescriptor instanceof SqmPolymorphicRootDescriptor ) {
|
||||
if ( getCreationOptions().useStrictJpaCompliance() ) {
|
||||
throw new StrictJpaComplianceViolation(
|
||||
"Encountered unmapped polymorphic reference [" + entityDescriptor.getEntityName()
|
||||
"Encountered unmapped polymorphic reference [" + entityDescriptor.getHibernateEntityName()
|
||||
+ "], but strict JPQL compliance was requested",
|
||||
StrictJpaComplianceViolation.Type.UNMAPPED_POLYMORPHISM
|
||||
);
|
||||
|
@ -974,21 +960,21 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
throw new UnsupportedOperationException( "Unexpected call to #visitCrossJoin, see #consumeCrossJoin" );
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private void consumeCrossJoin(HqlParser.CrossJoinContext parserJoin, SqmRoot sqmRoot) {
|
||||
final String name = parserJoin.pathRoot().entityName().getText();
|
||||
|
||||
SqmTreeCreationLogger.LOGGER.debugf( "Handling root path - %s", name );
|
||||
|
||||
final EntityValuedExpressableType entityType = getCreationContext().getDomainModel().resolveEntityReference( name );
|
||||
final EntityDomainType entityDescriptor = getCreationContext().getDomainModel().resolveHqlEntityReference( name );
|
||||
|
||||
if ( entityType instanceof SqmPolymorphicRootDescriptor ) {
|
||||
if ( entityDescriptor instanceof SqmPolymorphicRootDescriptor ) {
|
||||
throw new SemanticException( "Unmapped polymorphic reference cannot be used as a CROSS JOIN target" );
|
||||
}
|
||||
|
||||
final EntityTypeDescriptor entityDescriptor = entityType.getEntityDescriptor();
|
||||
|
||||
final SqmCrossJoin join = new SqmCrossJoin(
|
||||
entityDescriptor, visitIdentificationVariableDef( parserJoin.pathRoot().identificationVariableDef() ),
|
||||
entityDescriptor,
|
||||
visitIdentificationVariableDef( parserJoin.pathRoot().identificationVariableDef() ),
|
||||
sqmRoot
|
||||
);
|
||||
|
||||
|
@ -1236,7 +1222,7 @@ public class SemanticQueryBuilder extends HqlParserBaseVisitor implements SqmCre
|
|||
public SqmPredicate visitMemberOfPredicate(HqlParser.MemberOfPredicateContext ctx) {
|
||||
final SqmPath sqmPluralPath = consumeDomainPath( ctx.path() );
|
||||
|
||||
if ( sqmPluralPath.getReferencedPathSource() instanceof PluralValuedNavigable ) {
|
||||
if ( sqmPluralPath.getReferencedPathSource() instanceof PluralPersistentAttribute ) {
|
||||
return new SqmMemberOfPredicate( sqmPluralPath, creationContext.getNodeBuilder() );
|
||||
}
|
||||
else {
|
||||
|
|
|
@ -0,0 +1,62 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.query.hql.internal;
|
||||
|
||||
import org.hibernate.QueryException;
|
||||
import org.hibernate.query.sqm.InterpretationException;
|
||||
import org.hibernate.query.hql.SemanticQueryProducer;
|
||||
import org.hibernate.query.sqm.produce.internal.SqmTreePrinter;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationContext;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationOptions;
|
||||
import org.hibernate.query.sqm.tree.SqmStatement;
|
||||
|
||||
/**
|
||||
* Standard implementation of SemanticQueryInterpreter
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class SemanticQueryProducerImpl implements SemanticQueryProducer {
|
||||
private final SqmCreationContext sqmCreationContext;
|
||||
private final SqmCreationOptions sqmCreationOptions;
|
||||
|
||||
public SemanticQueryProducerImpl(
|
||||
SqmCreationContext sqmCreationContext,
|
||||
SqmCreationOptions sqmCreationOptions) {
|
||||
this.sqmCreationContext = sqmCreationContext;
|
||||
this.sqmCreationOptions = sqmCreationOptions;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmStatement interpret(String query) {
|
||||
// final ParsingContext parsingContext = ;
|
||||
|
||||
// first, ask Antlr to build the parse tree
|
||||
final HqlParser parser = HqlParseTreeBuilder.INSTANCE.parseHql( query );
|
||||
|
||||
// Log the parse tree (if enabled)
|
||||
HqlParseTreePrinter.logStatementParseTree( parser );
|
||||
|
||||
// then we perform semantic analysis and build the semantic representation...
|
||||
try {
|
||||
final SqmStatement sqmStatement = SemanticQueryBuilder.buildSemanticModel(
|
||||
parser.statement(),
|
||||
sqmCreationOptions,
|
||||
sqmCreationContext
|
||||
);
|
||||
|
||||
SqmTreePrinter.logTree( sqmStatement );
|
||||
|
||||
return sqmStatement;
|
||||
}
|
||||
catch (QueryException e) {
|
||||
throw e;
|
||||
}
|
||||
catch (Exception e) {
|
||||
throw new InterpretationException( query, e );
|
||||
}
|
||||
}
|
||||
}
|
|
@ -32,6 +32,7 @@ import javax.persistence.criteria.Subquery;
|
|||
import org.hibernate.NullPrecedence;
|
||||
import org.hibernate.SortOrder;
|
||||
import org.hibernate.metamodel.model.domain.DomainType;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.spi.MetamodelImplementor;
|
||||
import org.hibernate.query.criteria.HibernateCriteriaBuilder;
|
||||
import org.hibernate.query.criteria.JpaCoalesce;
|
||||
|
@ -71,7 +72,7 @@ import org.hibernate.type.spi.TypeConfiguration;
|
|||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public interface NodeBuilder extends HibernateCriteriaBuilder {
|
||||
MetamodelImplementor getDomainModel();
|
||||
JpaMetamodel getDomainModel();
|
||||
|
||||
default TypeConfiguration getTypeConfiguration() {
|
||||
return getDomainModel().getTypeConfiguration();
|
||||
|
|
|
@ -37,8 +37,8 @@ import org.hibernate.QueryException;
|
|||
import org.hibernate.SortOrder;
|
||||
import org.hibernate.internal.util.collections.ArrayHelper;
|
||||
import org.hibernate.metamodel.model.domain.DomainType;
|
||||
import org.hibernate.metamodel.model.mapping.spi.AllowableFunctionReturnType;
|
||||
import org.hibernate.metamodel.spi.MetamodelImplementor;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.metamodel.model.domain.AllowableFunctionReturnType;
|
||||
import org.hibernate.query.BinaryArithmeticOperator;
|
||||
import org.hibernate.query.UnaryArithmeticOperator;
|
||||
import org.hibernate.query.criteria.JpaCoalesce;
|
||||
|
@ -97,9 +97,7 @@ import org.hibernate.query.sqm.tree.select.SqmSubQuery;
|
|||
import org.hibernate.query.sqm.tree.update.SqmUpdateStatement;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.sql.TrimSpec;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.BasicValuedExpressableType;
|
||||
import org.hibernate.query.sqm.tree.expression.function.SqmFunction;
|
||||
import org.hibernate.type.spi.StandardSpiBasicTypes;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
import static org.hibernate.query.internal.QueryHelper.highestPrecedenceType;
|
||||
|
@ -112,12 +110,12 @@ import static org.hibernate.query.internal.QueryHelper.highestPrecedenceType;
|
|||
*/
|
||||
public class SqmCriteriaNodeBuilder implements NodeBuilder {
|
||||
private final QueryEngine queryEngine;
|
||||
private final MetamodelImplementor domainModel;
|
||||
private final JpaMetamodel domainModel;
|
||||
private final ServiceRegistry serviceRegistry;
|
||||
|
||||
public SqmCriteriaNodeBuilder(
|
||||
QueryEngine queryEngine,
|
||||
MetamodelImplementor domainModel,
|
||||
JpaMetamodel domainModel,
|
||||
ServiceRegistry serviceRegistry) {
|
||||
this.queryEngine = queryEngine;
|
||||
this.domainModel = domainModel;
|
||||
|
@ -125,7 +123,7 @@ public class SqmCriteriaNodeBuilder implements NodeBuilder {
|
|||
}
|
||||
|
||||
@Override
|
||||
public MetamodelImplementor getDomainModel() {
|
||||
public JpaMetamodel getDomainModel() {
|
||||
return domainModel;
|
||||
}
|
||||
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
package org.hibernate.query.sqm.produce.spi;
|
||||
|
||||
import org.hibernate.Incubating;
|
||||
import org.hibernate.metamodel.spi.MetamodelImplementor;
|
||||
import org.hibernate.metamodel.model.domain.JpaMetamodel;
|
||||
import org.hibernate.query.spi.QueryEngine;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
|
@ -22,12 +22,14 @@ public interface SqmCreationContext {
|
|||
/**
|
||||
* Access to the domain model metadata
|
||||
*/
|
||||
MetamodelImplementor getDomainModel();
|
||||
JpaMetamodel getDomainModel();
|
||||
|
||||
/**
|
||||
* Access to the ServiceRegistry for the context
|
||||
*/
|
||||
ServiceRegistry getServiceRegistry();
|
||||
default ServiceRegistry getServiceRegistry() {
|
||||
return getDomainModel().getServiceRegistry();
|
||||
}
|
||||
|
||||
QueryEngine getQueryEngine();
|
||||
|
||||
|
|
|
@ -23,14 +23,12 @@ import javax.persistence.metamodel.PluralAttribute;
|
|||
import javax.persistence.metamodel.SetAttribute;
|
||||
import javax.persistence.metamodel.SingularAttribute;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.graph.spi.SubGraphImplementor;
|
||||
import org.hibernate.metamodel.RepresentationMode;
|
||||
import org.hibernate.metamodel.model.domain.DomainType;
|
||||
import org.hibernate.metamodel.model.domain.EntityDomainType;
|
||||
import org.hibernate.metamodel.model.domain.IdentifiableDomainType;
|
||||
import org.hibernate.metamodel.model.domain.ManagedDomainType;
|
||||
import org.hibernate.metamodel.model.domain.NavigableRole;
|
||||
import org.hibernate.metamodel.model.domain.PersistentAttribute;
|
||||
import org.hibernate.metamodel.model.domain.PluralPersistentAttribute;
|
||||
import org.hibernate.metamodel.model.domain.SimpleDomainType;
|
||||
|
@ -38,7 +36,6 @@ import org.hibernate.metamodel.model.domain.SingularPersistentAttribute;
|
|||
import org.hibernate.query.sqm.SqmPathSource;
|
||||
import org.hibernate.query.sqm.produce.spi.SqmCreationState;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
* Acts as the EntityValuedNavigable for a "polymorphic query" grouping
|
||||
|
@ -49,17 +46,12 @@ public class SqmPolymorphicRootDescriptor<T> implements EntityDomainType<T> {
|
|||
private final Set<EntityDomainType<?>> implementors;
|
||||
private final Map<String, PersistentAttribute<? super T, ?>> commonAttributes;
|
||||
|
||||
private final NavigableRole navigableRole;
|
||||
private final JavaTypeDescriptor<T> polymorphicJavaDescriptor;
|
||||
private final SessionFactoryImplementor sessionFactory;
|
||||
|
||||
public SqmPolymorphicRootDescriptor(
|
||||
JavaTypeDescriptor<T> polymorphicJavaDescriptor,
|
||||
Set<EntityDomainType<?>> implementors,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
Set<EntityDomainType<?>> implementors) {
|
||||
this.polymorphicJavaDescriptor = polymorphicJavaDescriptor;
|
||||
this.navigableRole = new NavigableRole( polymorphicJavaDescriptor.getJavaType().getName() );
|
||||
this.sessionFactory = sessionFactory;
|
||||
|
||||
this.implementors = implementors;
|
||||
|
||||
|
@ -99,14 +91,6 @@ public class SqmPolymorphicRootDescriptor<T> implements EntityDomainType<T> {
|
|||
return new HashSet<>( implementors );
|
||||
}
|
||||
|
||||
public SessionFactoryImplementor getFactory() {
|
||||
return sessionFactory;
|
||||
}
|
||||
|
||||
public TypeConfiguration getTypeConfiguration() {
|
||||
return getFactory().getMetamodel().getTypeConfiguration();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return polymorphicJavaDescriptor.getJavaType().getName();
|
||||
|
|
|
@ -6,12 +6,12 @@
|
|||
*/
|
||||
package org.hibernate.query.sqm.tree.predicate;
|
||||
|
||||
import org.hibernate.query.ComparisonOperator;
|
||||
import org.hibernate.query.internal.QueryHelper;
|
||||
import org.hibernate.query.spi.ComparisonOperator;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.query.sqm.SqmExpressable;
|
||||
import org.hibernate.query.sqm.consume.spi.SemanticQueryWalker;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmExpression;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.ExpressableType;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
|
@ -31,12 +31,14 @@ public class SqmComparisonPredicate extends AbstractNegatableSqmPredicate {
|
|||
this.rightHandExpression = rightHandExpression;
|
||||
this.operator = operator;
|
||||
|
||||
final ExpressableType<?> expressableType = QueryHelper.highestPrecedenceType(
|
||||
final SqmExpressable expressableType = QueryHelper.highestPrecedenceType(
|
||||
leftHandExpression.getNodeType(),
|
||||
rightHandExpression.getNodeType()
|
||||
);
|
||||
|
||||
//noinspection unchecked
|
||||
leftHandExpression.applyInferableType( expressableType );
|
||||
//noinspection unchecked
|
||||
rightHandExpression.applyInferableType( expressableType );
|
||||
}
|
||||
|
||||
|
|
|
@ -11,21 +11,20 @@ import java.util.List;
|
|||
import java.util.Map;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.query.DynamicInstantiationNature;
|
||||
import org.hibernate.query.criteria.JpaCompoundSelection;
|
||||
import org.hibernate.query.criteria.JpaSelection;
|
||||
import org.hibernate.query.sqm.NodeBuilder;
|
||||
import org.hibernate.query.sqm.consume.spi.SemanticQueryWalker;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmExpression;
|
||||
import org.hibernate.query.sqm.tree.jpa.AbstractJpaSelection;
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.ExpressableType;
|
||||
import org.hibernate.sql.ast.tree.expression.instantiation.DynamicInstantiationNature;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
import static org.hibernate.sql.ast.tree.expression.instantiation.DynamicInstantiationNature.CLASS;
|
||||
import static org.hibernate.sql.ast.tree.expression.instantiation.DynamicInstantiationNature.LIST;
|
||||
import static org.hibernate.sql.ast.tree.expression.instantiation.DynamicInstantiationNature.MAP;
|
||||
import static org.hibernate.query.DynamicInstantiationNature.CLASS;
|
||||
import static org.hibernate.query.DynamicInstantiationNature.LIST;
|
||||
import static org.hibernate.query.DynamicInstantiationNature.MAP;
|
||||
|
||||
/**
|
||||
* Represents a dynamic instantiation ({@code select new XYZ(...) ...}) as part of the SQM.
|
||||
|
@ -166,13 +165,12 @@ public class SqmDynamicInstantiation<T>
|
|||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public <X> X accept(SemanticQueryWalker<X> walker) {
|
||||
return walker.visitDynamicInstantiation( this );
|
||||
}
|
||||
|
||||
public SqmDynamicInstantiation makeShallowCopy() {
|
||||
return new SqmDynamicInstantiation( getInstantiationTarget(), nodeBuilder() );
|
||||
public SqmDynamicInstantiation<T> makeShallowCopy() {
|
||||
return new SqmDynamicInstantiation<>( getInstantiationTarget(), nodeBuilder() );
|
||||
}
|
||||
|
||||
private static class DynamicInstantiationTargetImpl<T> implements SqmDynamicInstantiationTarget<T> {
|
||||
|
@ -196,14 +194,9 @@ public class SqmDynamicInstantiation<T>
|
|||
}
|
||||
|
||||
@Override
|
||||
public JavaTypeDescriptor<T> getJavaTypeDescriptor() {
|
||||
public JavaTypeDescriptor<T> getExpressableJavaTypeDescriptor() {
|
||||
return getTargetTypeDescriptor();
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistenceType getPersistenceType() {
|
||||
return PersistenceType.BASIC;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -224,6 +217,11 @@ public class SqmDynamicInstantiation<T>
|
|||
return list;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getAlias() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JpaSelection<T> alias(String name) {
|
||||
return null;
|
||||
|
@ -233,19 +231,4 @@ public class SqmDynamicInstantiation<T>
|
|||
public boolean isCompoundSelection() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getAlias() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeBuilder nodeBuilder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ExpressableType getNodeType() {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,9 +6,10 @@
|
|||
*/
|
||||
package org.hibernate.query.sqm.tree.select;
|
||||
|
||||
import org.hibernate.sql.ast.produce.metamodel.spi.ExpressableType;
|
||||
import org.hibernate.sql.ast.tree.expression.instantiation.DynamicInstantiationNature;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptor;
|
||||
|
||||
import org.hibernate.query.DynamicInstantiationNature;
|
||||
import org.hibernate.query.sqm.SqmExpressable;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
/**
|
||||
* Represents the thing-to-be-instantiated in a dynamic instantiation expression. Hibernate
|
||||
|
@ -16,7 +17,7 @@ import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptor;
|
|||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface SqmDynamicInstantiationTarget<T> extends ExpressableType<T> {
|
||||
public interface SqmDynamicInstantiationTarget<T> extends SqmExpressable<T> {
|
||||
|
||||
/**
|
||||
* Retrieves the enum describing the nature of this target.
|
||||
|
|
|
@ -0,0 +1,48 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.type.descriptor.java.spi;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.type.descriptor.java.AbstractTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.sql.SqlTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.sql.SqlTypeDescriptorIndicators;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class MapEntryJavaDescriptor extends AbstractTypeDescriptor<Map.Entry> {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final MapEntryJavaDescriptor INSTANCE = new MapEntryJavaDescriptor();
|
||||
|
||||
public MapEntryJavaDescriptor() {
|
||||
super( Map.Entry.class );
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqlTypeDescriptor getJdbcRecommendedSqlType(SqlTypeDescriptorIndicators context) {
|
||||
throw new UnsupportedOperationException( "Unsupported attempt to resolve JDBC type for Map.Entry" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map.Entry fromString(String string) {
|
||||
throw new UnsupportedOperationException( "Unsupported attempt create Map.Entry from String" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <X> X unwrap(Map.Entry value, Class<X> type, SharedSessionContractImplementor session) {
|
||||
throw new UnsupportedOperationException( "Unsupported attempt to unwrap Map.Entry value" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public <X> Map.Entry wrap(X value, SharedSessionContractImplementor session) {
|
||||
throw new UnsupportedOperationException( "Unsupported attempt to wrap Map.Entry value" );
|
||||
}
|
||||
}
|
|
@ -8,6 +8,7 @@ package org.hibernate.type.spi;
|
|||
|
||||
import java.io.InvalidObjectException;
|
||||
import java.io.Serializable;
|
||||
import java.sql.Types;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
|
@ -36,6 +37,7 @@ import org.hibernate.type.Type;
|
|||
import org.hibernate.type.TypeFactory;
|
||||
import org.hibernate.type.TypeResolver;
|
||||
import org.hibernate.type.descriptor.java.spi.JavaTypeDescriptorRegistry;
|
||||
import org.hibernate.type.descriptor.sql.SqlTypeDescriptorIndicators;
|
||||
import org.hibernate.type.descriptor.sql.spi.SqlTypeDescriptorRegistry;
|
||||
import org.hibernate.type.internal.TypeConfigurationRegistry;
|
||||
|
||||
|
@ -66,9 +68,9 @@ public class TypeConfiguration implements SessionFactoryObserver, Serializable {
|
|||
private final String uuid = LocalObjectUuidHelper.generateLocalObjectUuid();
|
||||
|
||||
private final Scope scope;
|
||||
private final transient TypeFactory typeFactory;
|
||||
|
||||
// things available during both boot and runtime ("active") lifecycle phases
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// things available during both boot and runtime lifecycle phases
|
||||
private final transient JavaTypeDescriptorRegistry javaTypeDescriptorRegistry;
|
||||
private final transient SqlTypeDescriptorRegistry sqlTypeDescriptorRegistry;
|
||||
private final transient BasicTypeRegistry basicTypeRegistry;
|
||||
|
@ -78,14 +80,17 @@ public class TypeConfiguration implements SessionFactoryObserver, Serializable {
|
|||
private final transient Map<Integer, Set<String>> jdbcToHibernateTypeContributionMap = new HashMap<>();
|
||||
|
||||
// temporarily needed to support deprecations
|
||||
private final transient TypeFactory typeFactory;
|
||||
private final transient TypeResolver typeResolver;
|
||||
|
||||
public TypeConfiguration() {
|
||||
this.scope = new Scope();
|
||||
this.scope = new Scope( this );
|
||||
|
||||
this.javaTypeDescriptorRegistry = new JavaTypeDescriptorRegistry( this );
|
||||
this.sqlTypeDescriptorRegistry = new SqlTypeDescriptorRegistry( this );
|
||||
|
||||
this.basicTypeRegistry = new BasicTypeRegistry();
|
||||
|
||||
this.typeFactory = new TypeFactory( this );
|
||||
this.typeResolver = new TypeResolver( this, typeFactory );
|
||||
|
||||
|
@ -127,6 +132,10 @@ public class TypeConfiguration implements SessionFactoryObserver, Serializable {
|
|||
return Collections.unmodifiableMap( importMap );
|
||||
}
|
||||
|
||||
public SqlTypeDescriptorIndicators getCurrentBaseSqlTypeIndicators() {
|
||||
return scope.getCurrentBaseSqlTypeIndicators();
|
||||
}
|
||||
|
||||
public Map<Integer, Set<String>> getJdbcToHibernateTypeContributionMap() {
|
||||
return jdbcToHibernateTypeContributionMap;
|
||||
}
|
||||
|
@ -271,16 +280,34 @@ public class TypeConfiguration implements SessionFactoryObserver, Serializable {
|
|||
* Each stage or phase is consider a "scope" for the TypeConfiguration.
|
||||
*/
|
||||
private static class Scope implements Serializable {
|
||||
private final TypeConfiguration typeConfiguration;
|
||||
|
||||
// todo (6.0) : consider a proper contract implemented by both SessionFactory (or its metamodel) and boot's MetadataImplementor
|
||||
// 1) type-related info from MetadataBuildingOptions
|
||||
// 2) ServiceRegistry
|
||||
private transient MetadataBuildingContext metadataBuildingContext;
|
||||
private transient SessionFactoryImplementor sessionFactory;
|
||||
|
||||
private String sessionFactoryName;
|
||||
private String sessionFactoryUuid;
|
||||
|
||||
private transient SqlTypeDescriptorIndicators currentSqlTypeIndicators = new SqlTypeDescriptorIndicators() {
|
||||
@Override
|
||||
public TypeConfiguration getTypeConfiguration() {
|
||||
return typeConfiguration;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getPreferredSqlTypeCodeForBoolean() {
|
||||
return Types.BOOLEAN;
|
||||
}
|
||||
};
|
||||
|
||||
public Scope(TypeConfiguration typeConfiguration) {
|
||||
this.typeConfiguration = typeConfiguration;
|
||||
}
|
||||
|
||||
public SqlTypeDescriptorIndicators getCurrentBaseSqlTypeIndicators() {
|
||||
return currentSqlTypeIndicators;
|
||||
}
|
||||
|
||||
public MetadataBuildingContext getMetadataBuildingContext() {
|
||||
if ( metadataBuildingContext == null ) {
|
||||
throw new HibernateException( "TypeConfiguration is not currently scoped to MetadataBuildingContext" );
|
||||
|
|
Loading…
Reference in New Issue