Search in sources :

Example 1 with NamedParameterDescriptor

use of org.hibernate.engine.query.spi.NamedParameterDescriptor in project hibernate-orm by hibernate.

the class QueryParameterBindingsImpl method expandListValuedParameters.

/**
 * @deprecated (since 5.2) expected changes to "collection-valued parameter binding" in 6.0
 */
@Deprecated
@SuppressWarnings("unchecked")
public String expandListValuedParameters(String queryString, SharedSessionContractImplementor session) {
    if (queryString == null) {
        return null;
    }
    if (parameterListBindingMap == null || parameterListBindingMap.isEmpty()) {
        return queryString;
    }
    // more-or-less... for each entry in parameterListBindingMap we will create an
    // entry in parameterBindingMap for each of the values in the bound value list.  afterwards
    // we will clear the parameterListBindingMap.
    // 
    // NOTE that this is essentially the legacy logical prior to modeling QueryParameterBinding/QueryParameterListBinding.
    // Fully expect the details of how this is handled in 6.0
    // HHH-1123
    // Some DBs limit number of IN expressions.  For now, warn...
    final Dialect dialect = session.getFactory().getServiceRegistry().getService(JdbcServices.class).getJdbcEnvironment().getDialect();
    final int inExprLimit = dialect.getInExpressionCountLimit();
    int maxOrdinalPosition = getMaxOrdinalPosition();
    for (Map.Entry<QueryParameter, QueryParameterListBinding> entry : parameterListBindingMap.entrySet()) {
        final QueryParameter sourceParam = entry.getKey();
        final Collection bindValues = entry.getValue().getBindValues();
        if (inExprLimit > 0 && bindValues.size() > inExprLimit) {
            log.tooManyInExpressions(dialect.getClass().getName(), inExprLimit, sourceParam.getName(), bindValues.size());
        }
        final String sourceToken;
        if (sourceParam instanceof NamedParameterDescriptor) {
            sourceToken = ":" + NamedParameterDescriptor.class.cast(sourceParam).getName();
        } else {
            sourceToken = "?" + OrdinalParameterDescriptor.class.cast(sourceParam).getPosition();
        }
        final int loc = StringHelper.indexOfIdentifierWord(queryString, sourceToken);
        if (loc < 0) {
            continue;
        }
        final String beforePlaceholder = queryString.substring(0, loc);
        final String afterPlaceholder = queryString.substring(loc + sourceToken.length());
        // check if placeholder is already immediately enclosed in parentheses
        // (ignoring whitespace)
        boolean isEnclosedInParens = StringHelper.getLastNonWhitespaceCharacter(beforePlaceholder) == '(' && StringHelper.getFirstNonWhitespaceCharacter(afterPlaceholder) == ')';
        if (bindValues.size() == 1 && isEnclosedInParens) {
            // short-circuit for performance when only 1 value and the
            // placeholder is already enclosed in parentheses...
            final QueryParameterBinding syntheticBinding = makeBinding(entry.getValue().getBindType());
            syntheticBinding.setBindValue(bindValues.iterator().next());
            parameterBindingMap.put(sourceParam, syntheticBinding);
            continue;
        }
        StringBuilder expansionList = new StringBuilder();
        int i = 0;
        for (Object bindValue : entry.getValue().getBindValues()) {
            if (i > 0) {
                expansionList.append(", ");
            }
            final QueryParameter syntheticParam;
            if (sourceParam instanceof NamedParameterDescriptor) {
                // in the case of a named parameter, for each value in the bound list-of-values we:
                // 1) create a synthetic named parameter
                // 2) expand the queryString to include each synthetic named param in place of the original
                // 3) create a new synthetic binding for just that single value under the synthetic name
                final String syntheticName = NamedParameterDescriptor.class.cast(sourceParam).getName() + '_' + i;
                expansionList.append(":").append(syntheticName);
                syntheticParam = new NamedParameterDescriptor(syntheticName, sourceParam.getType(), sourceParam.getSourceLocations());
            } else {
                // for the first item, we reuse the original parameter to avoid gaps in the positions
                if (i == 0) {
                    syntheticParam = sourceParam;
                } else {
                    int syntheticPosition = ++maxOrdinalPosition;
                    syntheticParam = new OrdinalParameterDescriptor(syntheticPosition, syntheticPosition - jdbcStyleOrdinalCountBase, sourceParam.getType(), sourceParam.getSourceLocations());
                }
                expansionList.append("?").append(syntheticParam.getPosition());
            }
            final QueryParameterBinding syntheticBinding = makeBinding(entry.getValue().getBindType());
            syntheticBinding.setBindValue(bindValue);
            parameterBindingMap.put(syntheticParam, syntheticBinding);
            i++;
        }
        queryString = StringHelper.replace(beforePlaceholder, afterPlaceholder, sourceToken, expansionList.toString(), true, true);
    }
    if (parameterListBindingMap != null) {
        parameterListBindingMap.clear();
    }
    return queryString;
}
Also used : QueryParameter(org.hibernate.query.QueryParameter) QueryParameterBinding(org.hibernate.query.spi.QueryParameterBinding) QueryParameterListBinding(org.hibernate.query.spi.QueryParameterListBinding) OrdinalParameterDescriptor(org.hibernate.engine.query.spi.OrdinalParameterDescriptor) Dialect(org.hibernate.dialect.Dialect) Collection(java.util.Collection) NamedParameterDescriptor(org.hibernate.engine.query.spi.NamedParameterDescriptor) HashMap(java.util.HashMap) Map(java.util.Map) TreeMap(java.util.TreeMap)

Example 2 with NamedParameterDescriptor

use of org.hibernate.engine.query.spi.NamedParameterDescriptor in project hibernate-orm by hibernate.

the class NativeQueryInterpreterStandardImpl method getParameterMetadata.

@Override
public ParameterMetadataImpl getParameterMetadata(String nativeQuery) {
    final ParamLocationRecognizer recognizer = ParamLocationRecognizer.parseLocations(nativeQuery);
    final int size = recognizer.getOrdinalParameterLocationList().size();
    final OrdinalParameterDescriptor[] ordinalDescriptors = new OrdinalParameterDescriptor[size];
    for (int i = 0; i < size; i++) {
        final Integer position = recognizer.getOrdinalParameterLocationList().get(i);
        ordinalDescriptors[i] = new OrdinalParameterDescriptor(i, null, position);
    }
    final Map<String, NamedParameterDescriptor> namedParamDescriptorMap = new HashMap<String, NamedParameterDescriptor>();
    final Map<String, ParamLocationRecognizer.NamedParameterDescription> map = recognizer.getNamedParameterDescriptionMap();
    for (final String name : map.keySet()) {
        final ParamLocationRecognizer.NamedParameterDescription description = map.get(name);
        namedParamDescriptorMap.put(name, new NamedParameterDescriptor(name, null, description.buildPositionsArray(), description.isJpaStyle()));
    }
    return new ParameterMetadataImpl(ordinalDescriptors, namedParamDescriptorMap);
}
Also used : ParamLocationRecognizer(org.hibernate.engine.query.spi.ParamLocationRecognizer) HashMap(java.util.HashMap) OrdinalParameterDescriptor(org.hibernate.engine.query.spi.OrdinalParameterDescriptor) NamedParameterDescriptor(org.hibernate.engine.query.spi.NamedParameterDescriptor) ParameterMetadataImpl(org.hibernate.query.internal.ParameterMetadataImpl)

Aggregations

HashMap (java.util.HashMap)2 NamedParameterDescriptor (org.hibernate.engine.query.spi.NamedParameterDescriptor)2 OrdinalParameterDescriptor (org.hibernate.engine.query.spi.OrdinalParameterDescriptor)2 Collection (java.util.Collection)1 Map (java.util.Map)1 TreeMap (java.util.TreeMap)1 Dialect (org.hibernate.dialect.Dialect)1 ParamLocationRecognizer (org.hibernate.engine.query.spi.ParamLocationRecognizer)1 QueryParameter (org.hibernate.query.QueryParameter)1 ParameterMetadataImpl (org.hibernate.query.internal.ParameterMetadataImpl)1 QueryParameterBinding (org.hibernate.query.spi.QueryParameterBinding)1 QueryParameterListBinding (org.hibernate.query.spi.QueryParameterListBinding)1