HHH-8452 - Better parameter handling for JPA criteria queries
This commit is contained in:
parent
bfe564e810
commit
8cfa73c3a1
|
@ -30,6 +30,7 @@ import javax.persistence.criteria.Predicate;
|
||||||
import javax.persistence.criteria.Root;
|
import javax.persistence.criteria.Root;
|
||||||
import javax.persistence.criteria.Subquery;
|
import javax.persistence.criteria.Subquery;
|
||||||
import javax.persistence.metamodel.EntityType;
|
import javax.persistence.metamodel.EntityType;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
|
@ -123,11 +124,13 @@ public abstract class AbstractManipulationCriteriaQuery<T> implements Compilable
|
||||||
HibernateEntityManagerImplementor entityManager,
|
HibernateEntityManagerImplementor entityManager,
|
||||||
final InterpretedParameterMetadata interpretedParameterMetadata) {
|
final InterpretedParameterMetadata interpretedParameterMetadata) {
|
||||||
|
|
||||||
|
final Map<String,Class> implicitParameterTypes = extractTypeMap( interpretedParameterMetadata.implicitParameterBindings() );
|
||||||
|
|
||||||
QueryImpl jpaqlQuery = entityManager.createQuery(
|
QueryImpl jpaqlQuery = entityManager.createQuery(
|
||||||
jpaqlString,
|
jpaqlString,
|
||||||
null,
|
null,
|
||||||
null,
|
null,
|
||||||
new HibernateEntityManagerImplementor.Options() {
|
new HibernateEntityManagerImplementor.QueryOptions() {
|
||||||
@Override
|
@Override
|
||||||
public List<ValueHandlerFactory.ValueHandler> getValueHandlers() {
|
public List<ValueHandlerFactory.ValueHandler> getValueHandlers() {
|
||||||
return null;
|
return null;
|
||||||
|
@ -135,7 +138,7 @@ public abstract class AbstractManipulationCriteriaQuery<T> implements Compilable
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Class> getNamedParameterExplicitTypes() {
|
public Map<String, Class> getNamedParameterExplicitTypes() {
|
||||||
return interpretedParameterMetadata.implicitParameterTypes();
|
return implicitParameterTypes;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -151,6 +154,14 @@ public abstract class AbstractManipulationCriteriaQuery<T> implements Compilable
|
||||||
|
|
||||||
return jpaqlQuery;
|
return jpaqlQuery;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Map<String, Class> extractTypeMap(List<ImplicitParameterBinding> implicitParameterBindings) {
|
||||||
|
final HashMap<String,Class> map = new HashMap<String, Class>();
|
||||||
|
for ( ImplicitParameterBinding implicitParameter : implicitParameterBindings ) {
|
||||||
|
map.put( implicitParameter.getParameterName(), implicitParameter.getJavaType() );
|
||||||
|
}
|
||||||
|
return map;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -26,7 +26,7 @@ package org.hibernate.jpa.criteria;
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.HashSet;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
@ -44,8 +44,6 @@ import javax.persistence.metamodel.EntityType;
|
||||||
|
|
||||||
import org.jboss.logging.Logger;
|
import org.jboss.logging.Logger;
|
||||||
|
|
||||||
import org.hibernate.internal.util.StringHelper;
|
|
||||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
|
||||||
import org.hibernate.jpa.internal.QueryImpl;
|
import org.hibernate.jpa.internal.QueryImpl;
|
||||||
import org.hibernate.jpa.criteria.compile.CompilableCriteria;
|
import org.hibernate.jpa.criteria.compile.CompilableCriteria;
|
||||||
import org.hibernate.jpa.criteria.compile.CriteriaInterpretation;
|
import org.hibernate.jpa.criteria.compile.CriteriaInterpretation;
|
||||||
|
@ -333,11 +331,13 @@ public class CriteriaQueryImpl<T> extends AbstractNode implements CriteriaQuery<
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public Query buildCompiledQuery(HibernateEntityManagerImplementor entityManager, final InterpretedParameterMetadata parameterMetadata) {
|
public Query buildCompiledQuery(HibernateEntityManagerImplementor entityManager, final InterpretedParameterMetadata parameterMetadata) {
|
||||||
|
|
||||||
|
final Map<String,Class> implicitParameterTypes = extractTypeMap( parameterMetadata.implicitParameterBindings() );
|
||||||
|
|
||||||
QueryImpl jpaqlQuery = entityManager.createQuery(
|
QueryImpl jpaqlQuery = entityManager.createQuery(
|
||||||
jpaqlString,
|
jpaqlString,
|
||||||
getResultType(),
|
getResultType(),
|
||||||
getSelection(),
|
getSelection(),
|
||||||
new HibernateEntityManagerImplementor.Options() {
|
new HibernateEntityManagerImplementor.QueryOptions() {
|
||||||
@Override
|
@Override
|
||||||
public List<ValueHandlerFactory.ValueHandler> getValueHandlers() {
|
public List<ValueHandlerFactory.ValueHandler> getValueHandlers() {
|
||||||
SelectionImplementor selection = (SelectionImplementor) queryStructure.getSelection();
|
SelectionImplementor selection = (SelectionImplementor) queryStructure.getSelection();
|
||||||
|
@ -348,12 +348,12 @@ public class CriteriaQueryImpl<T> extends AbstractNode implements CriteriaQuery<
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Class> getNamedParameterExplicitTypes() {
|
public Map<String, Class> getNamedParameterExplicitTypes() {
|
||||||
return parameterMetadata.implicitParameterTypes();
|
return implicitParameterTypes;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ResultMetadataValidator getResultMetadataValidator() {
|
public ResultMetadataValidator getResultMetadataValidator() {
|
||||||
return new HibernateEntityManagerImplementor.Options.ResultMetadataValidator() {
|
return new HibernateEntityManagerImplementor.QueryOptions.ResultMetadataValidator() {
|
||||||
@Override
|
@Override
|
||||||
public void validate(Type[] returnTypes) {
|
public void validate(Type[] returnTypes) {
|
||||||
SelectionImplementor selection = (SelectionImplementor) queryStructure.getSelection();
|
SelectionImplementor selection = (SelectionImplementor) queryStructure.getSelection();
|
||||||
|
@ -377,7 +377,8 @@ public class CriteriaQueryImpl<T> extends AbstractNode implements CriteriaQuery<
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}; }
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -388,10 +389,17 @@ public class CriteriaQueryImpl<T> extends AbstractNode implements CriteriaQuery<
|
||||||
return new CriteriaQueryTypeQueryAdapter(
|
return new CriteriaQueryTypeQueryAdapter(
|
||||||
entityManager,
|
entityManager,
|
||||||
jpaqlQuery,
|
jpaqlQuery,
|
||||||
parameterMetadata.explicitParameterMapping(),
|
parameterMetadata.explicitParameterInfoMap()
|
||||||
parameterMetadata.explicitParameterNameMapping()
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Map<String, Class> extractTypeMap(List<ImplicitParameterBinding> implicitParameterBindings) {
|
||||||
|
final HashMap<String,Class> map = new HashMap<String, Class>();
|
||||||
|
for ( ImplicitParameterBinding implicitParameter : implicitParameterBindings ) {
|
||||||
|
map.put( implicitParameter.getParameterName(), implicitParameter.getJavaType() );
|
||||||
|
}
|
||||||
|
return map;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -56,10 +56,10 @@ public class CriteriaCompiler implements Serializable {
|
||||||
public Query compile(CompilableCriteria criteria) {
|
public Query compile(CompilableCriteria criteria) {
|
||||||
criteria.validate();
|
criteria.validate();
|
||||||
|
|
||||||
final Map<ParameterExpression<?>,String> explicitParameterMapping = new HashMap<ParameterExpression<?>,String>();
|
final Map<ParameterExpression<?>, ExplicitParameterInfo<?>> explicitParameterInfoMap =
|
||||||
final Map<String,ParameterExpression<?>> explicitParameterNameMapping = new HashMap<String,ParameterExpression<?>>();
|
new HashMap<ParameterExpression<?>, ExplicitParameterInfo<?>>();
|
||||||
|
|
||||||
final List<ImplicitParameterBinding> implicitParameterBindings = new ArrayList<ImplicitParameterBinding>();
|
final List<ImplicitParameterBinding> implicitParameterBindings = new ArrayList<ImplicitParameterBinding>();
|
||||||
final Map<String,Class> implicitParameterTypes = new HashMap<String, Class>();
|
|
||||||
|
|
||||||
RenderingContext renderingContext = new RenderingContext() {
|
RenderingContext renderingContext = new RenderingContext() {
|
||||||
private int aliasCount = 0;
|
private int aliasCount = 0;
|
||||||
|
@ -73,22 +73,37 @@ public class CriteriaCompiler implements Serializable {
|
||||||
return "param" + explicitParameterCount++;
|
return "param" + explicitParameterCount++;
|
||||||
}
|
}
|
||||||
|
|
||||||
public String registerExplicitParameter(ParameterExpression<?> criteriaQueryParameter) {
|
@Override
|
||||||
final String jpaqlParameterName;
|
@SuppressWarnings("unchecked")
|
||||||
if ( explicitParameterMapping.containsKey( criteriaQueryParameter ) ) {
|
public ExplicitParameterInfo registerExplicitParameter(ParameterExpression<?> criteriaQueryParameter) {
|
||||||
jpaqlParameterName = explicitParameterMapping.get( criteriaQueryParameter );
|
ExplicitParameterInfo parameterInfo = explicitParameterInfoMap.get( criteriaQueryParameter );
|
||||||
}
|
if ( parameterInfo == null ) {
|
||||||
else {
|
|
||||||
jpaqlParameterName = generateParameterName();
|
|
||||||
explicitParameterMapping.put( criteriaQueryParameter, jpaqlParameterName );
|
|
||||||
}
|
|
||||||
if ( StringHelper.isNotEmpty( criteriaQueryParameter.getName() ) ) {
|
if ( StringHelper.isNotEmpty( criteriaQueryParameter.getName() ) ) {
|
||||||
explicitParameterNameMapping.put(
|
parameterInfo = new ExplicitParameterInfo(
|
||||||
criteriaQueryParameter.getName(),
|
criteriaQueryParameter.getName(),
|
||||||
criteriaQueryParameter
|
null,
|
||||||
|
criteriaQueryParameter.getJavaType()
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
return jpaqlParameterName;
|
else if ( criteriaQueryParameter.getPosition() != null ) {
|
||||||
|
parameterInfo = new ExplicitParameterInfo(
|
||||||
|
null,
|
||||||
|
criteriaQueryParameter.getPosition(),
|
||||||
|
criteriaQueryParameter.getJavaType()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
parameterInfo = new ExplicitParameterInfo(
|
||||||
|
generateParameterName(),
|
||||||
|
null,
|
||||||
|
criteriaQueryParameter.getJavaType()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
explicitParameterInfoMap.put( criteriaQueryParameter, parameterInfo );
|
||||||
|
}
|
||||||
|
|
||||||
|
return parameterInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
public String registerLiteralParameterBinding(final Object literal, final Class javaType) {
|
public String registerLiteralParameterBinding(final Object literal, final Class javaType) {
|
||||||
|
@ -108,7 +123,6 @@ public class CriteriaCompiler implements Serializable {
|
||||||
};
|
};
|
||||||
|
|
||||||
implicitParameterBindings.add( binding );
|
implicitParameterBindings.add( binding );
|
||||||
implicitParameterTypes.put( parameterName, javaType );
|
|
||||||
return parameterName;
|
return parameterName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -129,24 +143,14 @@ public class CriteriaCompiler implements Serializable {
|
||||||
entityManager,
|
entityManager,
|
||||||
new InterpretedParameterMetadata() {
|
new InterpretedParameterMetadata() {
|
||||||
@Override
|
@Override
|
||||||
public Map<ParameterExpression<?>, String> explicitParameterMapping() {
|
public Map<ParameterExpression<?>, ExplicitParameterInfo<?>> explicitParameterInfoMap() {
|
||||||
return explicitParameterMapping;
|
return explicitParameterInfoMap;
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Map<String, ParameterExpression<?>> explicitParameterNameMapping() {
|
|
||||||
return explicitParameterNameMapping;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<ImplicitParameterBinding> implicitParameterBindings() {
|
public List<ImplicitParameterBinding> implicitParameterBindings() {
|
||||||
return implicitParameterBindings;
|
return implicitParameterBindings;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public Map<String, Class> implicitParameterTypes() {
|
|
||||||
return implicitParameterTypes;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,6 +31,7 @@ import javax.persistence.TypedQuery;
|
||||||
import javax.persistence.criteria.ParameterExpression;
|
import javax.persistence.criteria.ParameterExpression;
|
||||||
import java.util.Calendar;
|
import java.util.Calendar;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
import java.util.HashSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
@ -45,151 +46,187 @@ import org.hibernate.jpa.spi.HibernateEntityManagerImplementor;
|
||||||
*/
|
*/
|
||||||
public class CriteriaQueryTypeQueryAdapter<X> implements TypedQuery<X>, HibernateQuery {
|
public class CriteriaQueryTypeQueryAdapter<X> implements TypedQuery<X>, HibernateQuery {
|
||||||
private final HibernateEntityManagerImplementor entityManager;
|
private final HibernateEntityManagerImplementor entityManager;
|
||||||
private final QueryImpl<X> jpaqlQuery;
|
private final QueryImpl<X> jpqlQuery;
|
||||||
private final Map<ParameterExpression<?>, String> explicitParameterMapping;
|
private final Map<ParameterExpression<?>, ExplicitParameterInfo<?>> explicitParameterInfoMap;
|
||||||
private final Map<String, ParameterExpression<?>> explicitParameterNameMapping;
|
|
||||||
|
|
||||||
public CriteriaQueryTypeQueryAdapter(
|
public CriteriaQueryTypeQueryAdapter(
|
||||||
HibernateEntityManagerImplementor entityManager,
|
HibernateEntityManagerImplementor entityManager,
|
||||||
QueryImpl<X> jpaqlQuery,
|
QueryImpl<X> jpqlQuery,
|
||||||
Map<ParameterExpression<?>, String> explicitParameterMapping,
|
Map<ParameterExpression<?>, ExplicitParameterInfo<?>> explicitParameterInfoMap) {
|
||||||
Map<String, ParameterExpression<?>> explicitParameterNameMapping) {
|
|
||||||
this.entityManager = entityManager;
|
this.entityManager = entityManager;
|
||||||
this.jpaqlQuery = jpaqlQuery;
|
this.jpqlQuery = jpqlQuery;
|
||||||
this.explicitParameterMapping = explicitParameterMapping;
|
this.explicitParameterInfoMap = explicitParameterInfoMap;
|
||||||
this.explicitParameterNameMapping = explicitParameterNameMapping;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Query getHibernateQuery() {
|
public Query getHibernateQuery() {
|
||||||
return jpaqlQuery.getHibernateQuery();
|
return jpqlQuery.getHibernateQuery();
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<X> getResultList() {
|
public List<X> getResultList() {
|
||||||
return jpaqlQuery.getResultList();
|
return jpqlQuery.getResultList();
|
||||||
}
|
}
|
||||||
|
|
||||||
public X getSingleResult() {
|
public X getSingleResult() {
|
||||||
return jpaqlQuery.getSingleResult();
|
return jpqlQuery.getSingleResult();
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getMaxResults() {
|
public int getMaxResults() {
|
||||||
return jpaqlQuery.getMaxResults();
|
return jpqlQuery.getMaxResults();
|
||||||
}
|
}
|
||||||
|
|
||||||
public TypedQuery<X> setMaxResults(int i) {
|
public TypedQuery<X> setMaxResults(int i) {
|
||||||
jpaqlQuery.setMaxResults( i );
|
jpqlQuery.setMaxResults( i );
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getFirstResult() {
|
public int getFirstResult() {
|
||||||
return jpaqlQuery.getFirstResult();
|
return jpqlQuery.getFirstResult();
|
||||||
}
|
}
|
||||||
|
|
||||||
public TypedQuery<X> setFirstResult(int i) {
|
public TypedQuery<X> setFirstResult(int i) {
|
||||||
jpaqlQuery.setFirstResult( i );
|
jpqlQuery.setFirstResult( i );
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Map<String, Object> getHints() {
|
public Map<String, Object> getHints() {
|
||||||
return jpaqlQuery.getHints();
|
return jpqlQuery.getHints();
|
||||||
}
|
}
|
||||||
|
|
||||||
public TypedQuery<X> setHint(String name, Object value) {
|
public TypedQuery<X> setHint(String name, Object value) {
|
||||||
jpaqlQuery.setHint( name, value);
|
jpqlQuery.setHint( name, value );
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public FlushModeType getFlushMode() {
|
public FlushModeType getFlushMode() {
|
||||||
return jpaqlQuery.getFlushMode();
|
return jpqlQuery.getFlushMode();
|
||||||
}
|
}
|
||||||
|
|
||||||
public TypedQuery<X> setFlushMode(FlushModeType flushModeType) {
|
public TypedQuery<X> setFlushMode(FlushModeType flushModeType) {
|
||||||
jpaqlQuery.setFlushMode( flushModeType );
|
jpqlQuery.setFlushMode( flushModeType );
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public LockModeType getLockMode() {
|
public LockModeType getLockMode() {
|
||||||
return jpaqlQuery.getLockMode();
|
return jpqlQuery.getLockMode();
|
||||||
}
|
}
|
||||||
|
|
||||||
public TypedQuery<X> setLockMode(LockModeType lockModeType) {
|
public TypedQuery<X> setLockMode(LockModeType lockModeType) {
|
||||||
jpaqlQuery.setLockMode( lockModeType );
|
jpqlQuery.setLockMode( lockModeType );
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public Set getParameters() {
|
public Set<Parameter<?>> getParameters() {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
return explicitParameterMapping.keySet();
|
return new HashSet( explicitParameterInfoMap.values() );
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isBound(Parameter<?> param) {
|
public boolean isBound(Parameter<?> param) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
return jpaqlQuery.isBound( param );
|
return jpqlQuery.isBound( param );
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public <T> T getParameterValue(Parameter<T> param) {
|
public <T> T getParameterValue(Parameter<T> param) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
return ( T ) jpaqlQuery.getParameterValue( mapToNamedParameter( param ) );
|
final ExplicitParameterInfo parameterInfo = resolveParameterInfo( param );
|
||||||
|
if ( parameterInfo.isNamed() ) {
|
||||||
|
return ( T ) jpqlQuery.getParameterValue( parameterInfo.getName() );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return ( T ) jpqlQuery.getParameterValue( parameterInfo.getPosition() );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private <T> ExplicitParameterInfo resolveParameterInfo(Parameter<T> param) {
|
||||||
|
if ( ExplicitParameterInfo.class.isInstance( param ) ) {
|
||||||
|
return (ExplicitParameterInfo) param;
|
||||||
|
}
|
||||||
|
else if ( ParameterExpression.class.isInstance( param ) ) {
|
||||||
|
return explicitParameterInfoMap.get( (ParameterExpression) param );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
for ( ExplicitParameterInfo parameterInfo : explicitParameterInfoMap.values() ) {
|
||||||
|
if ( param.getName() != null && param.getName().equals( parameterInfo.getName() ) ) {
|
||||||
|
return parameterInfo;
|
||||||
|
}
|
||||||
|
else if ( param.getPosition() != null && param.getPosition().equals( parameterInfo.getPosition() ) ) {
|
||||||
|
return parameterInfo;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw new IllegalArgumentException( "Unable to locate parameter [" + param + "] in query" );
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public <T> TypedQuery<X> setParameter(Parameter<T> param, T t) {
|
public <T> TypedQuery<X> setParameter(Parameter<T> param, T t) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
jpaqlQuery.setParameter( mapToNamedParameter( param ), t );
|
final ExplicitParameterInfo parameterInfo = resolveParameterInfo( param );
|
||||||
return this;
|
if ( parameterInfo.isNamed() ) {
|
||||||
|
jpqlQuery.setParameter( parameterInfo.getName(), t );
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
@SuppressWarnings({ "RedundantCast" })
|
jpqlQuery.setParameter( parameterInfo.getPosition(), t );
|
||||||
private Parameter mapToNamedParameter(Parameter criteriaParameter) {
|
}
|
||||||
return jpaqlQuery.getParameter(
|
return this;
|
||||||
explicitParameterMapping.get( criteriaParameter )
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public TypedQuery<X> setParameter(Parameter<Calendar> param, Calendar calendar, TemporalType temporalType) {
|
public TypedQuery<X> setParameter(Parameter<Calendar> param, Calendar calendar, TemporalType temporalType) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
jpaqlQuery.setParameter( mapToNamedParameter( param ), calendar, temporalType );
|
final ExplicitParameterInfo parameterInfo = resolveParameterInfo( param );
|
||||||
|
if ( parameterInfo.isNamed() ) {
|
||||||
|
jpqlQuery.setParameter( parameterInfo.getName(), calendar, temporalType );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
jpqlQuery.setParameter( parameterInfo.getPosition(), calendar, temporalType );
|
||||||
|
}
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public TypedQuery<X> setParameter(Parameter<Date> param, Date date, TemporalType temporalType) {
|
public TypedQuery<X> setParameter(Parameter<Date> param, Date date, TemporalType temporalType) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
jpaqlQuery.setParameter( mapToNamedParameter( param ), date, temporalType );
|
final ExplicitParameterInfo parameterInfo = resolveParameterInfo( param );
|
||||||
|
if ( parameterInfo.isNamed() ) {
|
||||||
|
jpqlQuery.setParameter( parameterInfo.getName(), date, temporalType );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
jpqlQuery.setParameter( parameterInfo.getPosition(), date, temporalType );
|
||||||
|
}
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public <T> T unwrap(Class<T> cls) {
|
public <T> T unwrap(Class<T> cls) {
|
||||||
return jpaqlQuery.unwrap( cls );
|
return jpqlQuery.unwrap( cls );
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public Object getParameterValue(String name) {
|
public Object getParameterValue(String name) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
return getParameterValue( resolveExplicitCriteriaParameterName( name ) );
|
locateParameterByName( name );
|
||||||
|
return jpqlQuery.getParameter( name );
|
||||||
}
|
}
|
||||||
|
|
||||||
private Parameter resolveExplicitCriteriaParameterName(String name) {
|
private ExplicitParameterInfo locateParameterByName(String name) {
|
||||||
Parameter parameter = explicitParameterNameMapping.get( name );
|
for ( ExplicitParameterInfo parameterInfo : explicitParameterInfoMap.values() ) {
|
||||||
if ( parameter == null ) {
|
if ( parameterInfo.isNamed() && parameterInfo.getName().equals( name ) ) {
|
||||||
throw new IllegalArgumentException( "Named parameter [" + name + "] not encountered" );
|
return parameterInfo;
|
||||||
}
|
}
|
||||||
return parameter;
|
}
|
||||||
|
throw new IllegalArgumentException( "Unable to locate parameter registered with that name [" + name + "]" );
|
||||||
}
|
}
|
||||||
|
|
||||||
public Parameter<?> getParameter(String name) {
|
public Parameter<?> getParameter(String name) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
return mapToNamedParameter( resolveExplicitCriteriaParameterName( name ) );
|
return locateParameterByName( name );
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public <T> Parameter<T> getParameter(String name, Class<T> type) {
|
public <T> Parameter<T> getParameter(String name, Class<T> type) {
|
||||||
entityManager.checkOpen( false );
|
entityManager.checkOpen( false );
|
||||||
Parameter parameter = resolveExplicitCriteriaParameterName( name );
|
Parameter parameter = locateParameterByName( name );
|
||||||
if ( type.isAssignableFrom( parameter.getParameterType() ) ) {
|
if ( type.isAssignableFrom( parameter.getParameterType() ) ) {
|
||||||
return parameter;
|
return parameter;
|
||||||
}
|
}
|
||||||
|
@ -202,55 +239,27 @@ public class CriteriaQueryTypeQueryAdapter<X> implements TypedQuery<X>, Hibernat
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public TypedQuery<X> setParameter(String name, Object value) {
|
public TypedQuery<X> setParameter(String name, Object value) {
|
||||||
entityManager.checkOpen( true );
|
entityManager.checkOpen( true );
|
||||||
setParameter(
|
ExplicitParameterInfo parameterInfo = locateParameterByName( name );
|
||||||
resolveExplicitCriteriaParameterName( name, value ),
|
parameterInfo.validateBindValue( value );
|
||||||
value
|
jpqlQuery.setParameter( name, value );
|
||||||
);
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
private Parameter resolveExplicitCriteriaParameterName(String name, Object value) {
|
|
||||||
Parameter parameter = resolveExplicitCriteriaParameterName( name );
|
|
||||||
// todo : is null valid?
|
|
||||||
if ( value != null ) {
|
|
||||||
if ( ! parameter.getParameterType().isInstance( value ) ) {
|
|
||||||
throw new IllegalArgumentException(
|
|
||||||
"Named parameter [" + name + "] type mismatch; expecting ["
|
|
||||||
+ parameter.getParameterType().getName() + "], found ["
|
|
||||||
+ value.getClass().getName() + "]"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return parameter;
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public TypedQuery<X> setParameter(String name, Calendar calendar, TemporalType temporalType) {
|
public TypedQuery<X> setParameter(String name, Calendar calendar, TemporalType temporalType) {
|
||||||
entityManager.checkOpen( true );
|
entityManager.checkOpen( true );
|
||||||
Parameter parameter = resolveExplicitCriteriaParameterName( name );
|
ExplicitParameterInfo parameterInfo = locateParameterByName( name );
|
||||||
if ( ! Calendar.class.isAssignableFrom( parameter.getParameterType() ) ) {
|
parameterInfo.validateCalendarBind();
|
||||||
throw new IllegalArgumentException(
|
jpqlQuery.setParameter( name, calendar, temporalType );
|
||||||
"Named parameter [" + name + "] type mismatch; expecting ["
|
|
||||||
+ Calendar.class.getName() + "], found ["
|
|
||||||
+ parameter.getParameterType().getName() + "]"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
setParameter( parameter, calendar, temporalType );
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked" })
|
@SuppressWarnings({ "unchecked" })
|
||||||
public TypedQuery<X> setParameter(String name, Date date, TemporalType temporalType) {
|
public TypedQuery<X> setParameter(String name, Date date, TemporalType temporalType) {
|
||||||
entityManager.checkOpen( true );
|
entityManager.checkOpen( true );
|
||||||
Parameter parameter = resolveExplicitCriteriaParameterName( name );
|
ExplicitParameterInfo parameterInfo = locateParameterByName( name );
|
||||||
if ( ! Date.class.isAssignableFrom( parameter.getParameterType() ) ) {
|
parameterInfo.validateDateBind();
|
||||||
throw new IllegalArgumentException(
|
jpqlQuery.setParameter( name, date, temporalType );
|
||||||
"Named parameter [" + name + "] type mismatch; expecting ["
|
|
||||||
+ Date.class.getName() + "], found ["
|
|
||||||
+ parameter.getParameterType().getName() + "]"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
setParameter( parameter, date, temporalType );
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,153 @@
|
||||||
|
/*
|
||||||
|
* Hibernate, Relational Persistence for Idiomatic Java
|
||||||
|
*
|
||||||
|
* Copyright (c) 2013, Red Hat Inc. or third-party contributors as
|
||||||
|
* indicated by the @author tags or express copyright attribution
|
||||||
|
* statements applied by the authors. All third-party contributions are
|
||||||
|
* distributed under license by Red Hat Inc.
|
||||||
|
*
|
||||||
|
* This copyrighted material is made available to anyone wishing to use, modify,
|
||||||
|
* copy, or redistribute it subject to the terms and conditions of the GNU
|
||||||
|
* Lesser General Public License, as published by the Free Software Foundation.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
||||||
|
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||||
|
* for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Lesser General Public License
|
||||||
|
* along with this distribution; if not, write to:
|
||||||
|
* Free Software Foundation, Inc.
|
||||||
|
* 51 Franklin Street, Fifth Floor
|
||||||
|
* Boston, MA 02110-1301 USA
|
||||||
|
*/
|
||||||
|
package org.hibernate.jpa.criteria.compile;
|
||||||
|
|
||||||
|
import javax.persistence.Parameter;
|
||||||
|
import java.util.Calendar;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Steve Ebersole
|
||||||
|
*/
|
||||||
|
public class ExplicitParameterInfo<T> implements Parameter<T> {
|
||||||
|
private final String name;
|
||||||
|
private final Integer position;
|
||||||
|
private final Class<T> type;
|
||||||
|
|
||||||
|
public ExplicitParameterInfo(String name, Integer position, Class<T> type) {
|
||||||
|
if ( name == null && position == null ) {
|
||||||
|
throw new IllegalStateException( "Both name and position were null; caller should have generated parameter name" );
|
||||||
|
}
|
||||||
|
if ( name != null && position != null ) {
|
||||||
|
throw new IllegalStateException( "Both name and position were specified" );
|
||||||
|
}
|
||||||
|
|
||||||
|
this.name = name;
|
||||||
|
this.position = position;
|
||||||
|
this.type = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isNamed() {
|
||||||
|
return name != null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Integer getPosition() {
|
||||||
|
return position;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Class<T> getParameterType() {
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Renders this parameter's JPQL form
|
||||||
|
*
|
||||||
|
* @return The rendered form
|
||||||
|
*/
|
||||||
|
public String render() {
|
||||||
|
return isNamed()
|
||||||
|
? ":" + name
|
||||||
|
: "?" + position.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void validateBindValue(Object value) {
|
||||||
|
if ( value == null ) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( ! getParameterType().isInstance( value ) ) {
|
||||||
|
if ( isNamed() ) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Named parameter [%s] type mismatch; expecting [%s] but found [%s]",
|
||||||
|
getName(),
|
||||||
|
getParameterType().getSimpleName(),
|
||||||
|
value.getClass().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Positional parameter [%s] type mismatch; expecting [%s] but found [%s]",
|
||||||
|
getPosition(),
|
||||||
|
getParameterType().getSimpleName(),
|
||||||
|
value.getClass().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void validateCalendarBind() {
|
||||||
|
if ( ! Calendar.class.isAssignableFrom( getParameterType() ) ) {
|
||||||
|
if ( isNamed() ) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Named parameter [%s] type mismatch; Calendar was passed, but parameter defined as [%s]",
|
||||||
|
getName(),
|
||||||
|
getParameterType().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Positional parameter [%s] type mismatch; Calendar was passed, but parameter defined as [%s]",
|
||||||
|
getPosition(),
|
||||||
|
getParameterType().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void validateDateBind() {
|
||||||
|
if ( !Date.class.isAssignableFrom( getParameterType() ) ) {
|
||||||
|
if ( isNamed() ) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Named parameter [%s] type mismatch; Date was passed, but parameter defined as [%s]",
|
||||||
|
getName(),
|
||||||
|
getParameterType().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
String.format(
|
||||||
|
"Positional parameter [%s] type mismatch; Date was passed, but parameter defined as [%s]",
|
||||||
|
getPosition(),
|
||||||
|
getParameterType().getSimpleName()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -40,7 +40,7 @@ public interface ImplicitParameterBinding {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the java type of the "thing" that led to the implicit parameter. Used from
|
* Get the java type of the "thing" that led to the implicit parameter. Used from
|
||||||
* {@link org.hibernate.ejb.HibernateEntityManagerImplementor.Options#getNamedParameterExplicitTypes()}
|
* {@link org.hibernate.jpa.spi.HibernateEntityManagerImplementor.QueryOptions#getNamedParameterExplicitTypes()}
|
||||||
* in determining "guessed type" overriding.
|
* in determining "guessed type" overriding.
|
||||||
*
|
*
|
||||||
* @return The java type
|
* @return The java type
|
||||||
|
|
|
@ -28,11 +28,15 @@ import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Represents information about parameters from a compiled criteria query.
|
||||||
|
*
|
||||||
* @author Steve Ebersole
|
* @author Steve Ebersole
|
||||||
*/
|
*/
|
||||||
public interface InterpretedParameterMetadata {
|
public interface InterpretedParameterMetadata {
|
||||||
public Map<ParameterExpression<?>,String> explicitParameterMapping();
|
public Map<ParameterExpression<?>, ExplicitParameterInfo<?>> explicitParameterInfoMap();
|
||||||
public Map<String,ParameterExpression<?>> explicitParameterNameMapping();
|
|
||||||
|
// public Map<ParameterExpression<?>,String> explicitParameterMapping();
|
||||||
|
// public Map<String,ParameterExpression<?>> explicitParameterNameMapping();
|
||||||
public List<ImplicitParameterBinding> implicitParameterBindings();
|
public List<ImplicitParameterBinding> implicitParameterBindings();
|
||||||
public Map<String,Class> implicitParameterTypes();
|
// public Map<String,Class> implicitParameterTypes();
|
||||||
}
|
}
|
||||||
|
|
|
@ -45,7 +45,7 @@ public interface RenderingContext {
|
||||||
*
|
*
|
||||||
* @return The JPA-QL parameter name
|
* @return The JPA-QL parameter name
|
||||||
*/
|
*/
|
||||||
public String registerExplicitParameter(ParameterExpression<?> criteriaQueryParameter);
|
public ExplicitParameterInfo registerExplicitParameter(ParameterExpression<?> criteriaQueryParameter);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Register a parameter that was not part of the criteria query (at least not as a parameter).
|
* Register a parameter that was not part of the criteria query (at least not as a parameter).
|
||||||
|
|
|
@ -28,6 +28,7 @@ import javax.persistence.criteria.ParameterExpression;
|
||||||
|
|
||||||
import org.hibernate.jpa.criteria.CriteriaBuilderImpl;
|
import org.hibernate.jpa.criteria.CriteriaBuilderImpl;
|
||||||
import org.hibernate.jpa.criteria.ParameterRegistry;
|
import org.hibernate.jpa.criteria.ParameterRegistry;
|
||||||
|
import org.hibernate.jpa.criteria.compile.ExplicitParameterInfo;
|
||||||
import org.hibernate.jpa.criteria.compile.RenderingContext;
|
import org.hibernate.jpa.criteria.compile.RenderingContext;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -85,8 +86,8 @@ public class ParameterExpressionImpl<T>
|
||||||
}
|
}
|
||||||
|
|
||||||
public String render(RenderingContext renderingContext) {
|
public String render(RenderingContext renderingContext) {
|
||||||
final String jpaqlParamName = renderingContext.registerExplicitParameter( this );
|
final ExplicitParameterInfo parameterInfo = renderingContext.registerExplicitParameter( this );
|
||||||
return ':' + jpaqlParamName;
|
return parameterInfo.render();
|
||||||
}
|
}
|
||||||
|
|
||||||
public String renderProjection(RenderingContext renderingContext) {
|
public String renderProjection(RenderingContext renderingContext) {
|
||||||
|
|
|
@ -83,12 +83,10 @@ import org.hibernate.SQLQuery;
|
||||||
import org.hibernate.Session;
|
import org.hibernate.Session;
|
||||||
import org.hibernate.StaleObjectStateException;
|
import org.hibernate.StaleObjectStateException;
|
||||||
import org.hibernate.StaleStateException;
|
import org.hibernate.StaleStateException;
|
||||||
import org.hibernate.procedure.ProcedureCall;
|
|
||||||
import org.hibernate.TransientObjectException;
|
import org.hibernate.TransientObjectException;
|
||||||
import org.hibernate.TypeMismatchException;
|
import org.hibernate.TypeMismatchException;
|
||||||
import org.hibernate.UnresolvableObjectException;
|
import org.hibernate.UnresolvableObjectException;
|
||||||
import org.hibernate.cfg.Environment;
|
import org.hibernate.cfg.Environment;
|
||||||
import org.hibernate.cfg.NotYetImplementedException;
|
|
||||||
import org.hibernate.dialect.lock.LockingStrategyException;
|
import org.hibernate.dialect.lock.LockingStrategyException;
|
||||||
import org.hibernate.dialect.lock.OptimisticEntityLockException;
|
import org.hibernate.dialect.lock.OptimisticEntityLockException;
|
||||||
import org.hibernate.dialect.lock.PessimisticEntityLockException;
|
import org.hibernate.dialect.lock.PessimisticEntityLockException;
|
||||||
|
@ -552,13 +550,13 @@ public abstract class AbstractEntityManagerImpl implements HibernateEntityManage
|
||||||
String jpaqlString,
|
String jpaqlString,
|
||||||
Class<T> resultClass,
|
Class<T> resultClass,
|
||||||
Selection selection,
|
Selection selection,
|
||||||
Options options) {
|
QueryOptions queryOptions) {
|
||||||
try {
|
try {
|
||||||
org.hibernate.Query hqlQuery = internalGetSession().createQuery( jpaqlString );
|
org.hibernate.Query hqlQuery = internalGetSession().createQuery( jpaqlString );
|
||||||
|
|
||||||
if ( options.getValueHandlers() == null ) {
|
if ( queryOptions.getValueHandlers() == null ) {
|
||||||
if ( options.getResultMetadataValidator() != null ) {
|
if ( queryOptions.getResultMetadataValidator() != null ) {
|
||||||
options.getResultMetadataValidator().validate( hqlQuery.getReturnTypes() );
|
queryOptions.getResultMetadataValidator().validate( hqlQuery.getReturnTypes() );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -566,12 +564,12 @@ public abstract class AbstractEntityManagerImpl implements HibernateEntityManage
|
||||||
List tupleElements = Tuple.class.equals( resultClass )
|
List tupleElements = Tuple.class.equals( resultClass )
|
||||||
? ( ( CompoundSelectionImpl<Tuple> ) selection ).getCompoundSelectionItems()
|
? ( ( CompoundSelectionImpl<Tuple> ) selection ).getCompoundSelectionItems()
|
||||||
: null;
|
: null;
|
||||||
if ( options.getValueHandlers() != null || tupleElements != null ) {
|
if ( queryOptions.getValueHandlers() != null || tupleElements != null ) {
|
||||||
hqlQuery.setResultTransformer(
|
hqlQuery.setResultTransformer(
|
||||||
new CriteriaQueryTransformer( options.getValueHandlers(), tupleElements )
|
new CriteriaQueryTransformer( queryOptions.getValueHandlers(), tupleElements )
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
return new QueryImpl<T>( hqlQuery, this, options.getNamedParameterExplicitTypes() );
|
return new QueryImpl<T>( hqlQuery, this, queryOptions.getNamedParameterExplicitTypes() );
|
||||||
}
|
}
|
||||||
catch ( HibernateException he ) {
|
catch ( HibernateException he ) {
|
||||||
throw convert( he );
|
throw convert( he );
|
||||||
|
|
|
@ -131,11 +131,13 @@ public interface HibernateEntityManagerImplementor extends HibernateEntityManage
|
||||||
*/
|
*/
|
||||||
public LockOptions getLockRequest(LockModeType lockModeType, Map<String, Object> properties);
|
public LockOptions getLockRequest(LockModeType lockModeType, Map<String, Object> properties);
|
||||||
|
|
||||||
public static interface Options {
|
public static interface QueryOptions {
|
||||||
public static interface ResultMetadataValidator {
|
public static interface ResultMetadataValidator {
|
||||||
public void validate(Type[] returnTypes);
|
public void validate(Type[] returnTypes);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public ResultMetadataValidator getResultMetadataValidator();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the conversions for the individual tuples in the query results.
|
* Get the conversions for the individual tuples in the query results.
|
||||||
*
|
*
|
||||||
|
@ -150,8 +152,6 @@ public interface HibernateEntityManagerImplementor extends HibernateEntityManage
|
||||||
* @return The
|
* @return The
|
||||||
*/
|
*/
|
||||||
public Map<String, Class> getNamedParameterExplicitTypes();
|
public Map<String, Class> getNamedParameterExplicitTypes();
|
||||||
|
|
||||||
public ResultMetadataValidator getResultMetadataValidator();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -160,10 +160,10 @@ public interface HibernateEntityManagerImplementor extends HibernateEntityManage
|
||||||
* @param jpaqlString The criteria query rendered as a JPA QL string
|
* @param jpaqlString The criteria query rendered as a JPA QL string
|
||||||
* @param resultClass The result type (the type expected in the result list)
|
* @param resultClass The result type (the type expected in the result list)
|
||||||
* @param selection The selection(s)
|
* @param selection The selection(s)
|
||||||
* @param options The options to use to build the query.
|
* @param queryOptions The options to use to build the query.
|
||||||
* @param <T> The query type
|
* @param <T> The query type
|
||||||
*
|
*
|
||||||
* @return The typed query
|
* @return The typed query
|
||||||
*/
|
*/
|
||||||
public <T> QueryImpl<T> createQuery(String jpaqlString, Class<T> resultClass, Selection selection, Options options);
|
public <T> QueryImpl<T> createQuery(String jpaqlString, Class<T> resultClass, Selection selection, QueryOptions queryOptions);
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,6 +24,7 @@
|
||||||
package org.hibernate.jpa.test.criteria;
|
package org.hibernate.jpa.test.criteria;
|
||||||
|
|
||||||
import javax.persistence.EntityManager;
|
import javax.persistence.EntityManager;
|
||||||
|
import javax.persistence.Parameter;
|
||||||
import javax.persistence.TypedQuery;
|
import javax.persistence.TypedQuery;
|
||||||
import javax.persistence.criteria.CriteriaQuery;
|
import javax.persistence.criteria.CriteriaQuery;
|
||||||
import javax.persistence.criteria.ParameterExpression;
|
import javax.persistence.criteria.ParameterExpression;
|
||||||
|
@ -34,6 +35,8 @@ import org.junit.Test;
|
||||||
|
|
||||||
import org.hibernate.jpa.test.BaseEntityManagerFunctionalTestCase;
|
import org.hibernate.jpa.test.BaseEntityManagerFunctionalTestCase;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Steve Ebersole
|
* @author Steve Ebersole
|
||||||
*/
|
*/
|
||||||
|
@ -73,6 +76,26 @@ public class ParameterTest extends BaseEntityManagerFunctionalTestCase {
|
||||||
em.close();
|
em.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNamedParameterMetadata() {
|
||||||
|
EntityManager em = getOrCreateEntityManager();
|
||||||
|
em.getTransaction().begin();
|
||||||
|
CriteriaQuery<MultiTypedBasicAttributesEntity> criteria = em.getCriteriaBuilder()
|
||||||
|
.createQuery( MultiTypedBasicAttributesEntity.class );
|
||||||
|
Root<MultiTypedBasicAttributesEntity> rootEntity = criteria.from( MultiTypedBasicAttributesEntity.class );
|
||||||
|
|
||||||
|
criteria.where(
|
||||||
|
em.getCriteriaBuilder().equal(
|
||||||
|
rootEntity.get( MultiTypedBasicAttributesEntity_.id ),
|
||||||
|
em.getCriteriaBuilder().parameter( Long.class, "id" )
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
TypedQuery<MultiTypedBasicAttributesEntity> query = em.createQuery( criteria );
|
||||||
|
Parameter parameter = query.getParameter( "id" );
|
||||||
|
assertEquals( "id", parameter.getName() );
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Class[] getAnnotatedClasses() {
|
public Class[] getAnnotatedClasses() {
|
||||||
return new Class[] { MultiTypedBasicAttributesEntity.class };
|
return new Class[] { MultiTypedBasicAttributesEntity.class };
|
||||||
|
|
Loading…
Reference in New Issue