[#3131] Query.getBindValues() should not return inlined bind values

This commit is contained in:
Lukas Eder 2014-03-17 15:45:44 +01:00
parent ab29b4a73f
commit ff3f9186cd
5 changed files with 110 additions and 10 deletions

View File

@ -223,6 +223,10 @@ public interface DSLContext {
* <p>
* The returned <code>List</code> is immutable. To modify bind values, use
* {@link #extractParams(QueryPart)} instead.
* <p>
* Unlike {@link #extractParams(QueryPart)}, which returns also inlined
* parameters, this returns only actual bind values that will render an
* actual bind value as a question mark <code>"?"</code>
*/
List<Object> extractBindValues(QueryPart part);

View File

@ -176,6 +176,10 @@ public interface Query extends QueryPart, Attachable {
* Retrieve the bind values that will be bound by this Query. This
* <code>List</code> cannot be modified. To modify bind values, use
* {@link #getParams()} instead.
* <p>
* Unlike {@link #getParams()}, which returns also inlined parameters, this
* returns only actual bind values that will render an actual bind value as
* a question mark <code>"?"</code>
*
* @see DSLContext#extractBindValues(QueryPart)
*/

View File

@ -309,7 +309,7 @@ public class DefaultDSLContext implements DSLContext, Serializable {
public List<Object> extractBindValues(QueryPart part) {
List<Object> result = new ArrayList<Object>();
for (Param<?> param : extractParams(part).values()) {
for (Param<?> param : extractParams0(part, false).values()) {
result.add(param.getValue());
}
@ -318,7 +318,11 @@ public class DefaultDSLContext implements DSLContext, Serializable {
@Override
public Map<String, Param<?>> extractParams(QueryPart part) {
ParamCollector collector = new ParamCollector(configuration);
return extractParams0(part, true);
}
final Map<String, Param<?>> extractParams0(QueryPart part, boolean includeInlinedParams) {
ParamCollector collector = new ParamCollector(configuration, includeInlinedParams);
collector.visit(part);
return Collections.unmodifiableMap(collector.result);
}

View File

@ -61,10 +61,13 @@ import org.jooq.tools.StringUtils;
*/
class ParamCollector extends AbstractBindContext {
final Map<String, Param<?>> result = new LinkedHashMap<String, Param<?>>();
final Map<String, Param<?>> result = new LinkedHashMap<String, Param<?>>();
private final boolean includeInlinedParams;
ParamCollector(Configuration configuration) {
ParamCollector(Configuration configuration, boolean includeInlinedParams) {
super(configuration);
this.includeInlinedParams = includeInlinedParams;
}
@Override
@ -76,13 +79,17 @@ class ParamCollector extends AbstractBindContext {
protected final void bindInternal(QueryPartInternal internal) {
if (internal instanceof Param) {
Param<?> param = (Param<?>) internal;
String i = String.valueOf(nextIndex());
if (StringUtils.isBlank(param.getParamName())) {
result.put(i, param);
}
else {
result.put(param.getParamName(), param);
// [#3131] Inlined parameters should not be returned in some contexts
if (includeInlinedParams || !param.isInline()) {
String i = String.valueOf(nextIndex());
if (StringUtils.isBlank(param.getParamName())) {
result.put(i, param);
}
else {
result.put(param.getParamName(), param);
}
}
}
else {

View File

@ -0,0 +1,81 @@
/**
* Copyright (c) 2009-2014, Data Geekery GmbH (http://www.datageekery.com)
* All rights reserved.
*
* This work is dual-licensed
* - under the Apache Software License 2.0 (the "ASL")
* - under the jOOQ License and Maintenance Agreement (the "jOOQ License")
* =============================================================================
* You may choose which license applies to you:
*
* - If you're using this work with Open Source databases, you may choose
* either ASL or jOOQ License.
* - If you're using this work with at least one commercial database, you must
* choose jOOQ License
*
* For more information, please visit http://www.jooq.org/licenses
*
* Apache Software License 2.0:
* -----------------------------------------------------------------------------
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* jOOQ License and Maintenance Agreement:
* -----------------------------------------------------------------------------
* Data Geekery grants the Customer the non-exclusive, timely limited and
* non-transferable license to install and use the Software under the terms of
* the jOOQ License and Maintenance Agreement.
*
* This library is distributed with a LIMITED WARRANTY. See the jOOQ License
* and Maintenance Agreement for more details: http://www.jooq.org/licensing
*/
package org.jooq.test;
import static java.util.Arrays.asList;
import static org.jooq.impl.DSL.inline;
import static org.jooq.impl.DSL.val;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import java.util.ArrayList;
import java.util.List;
import org.jooq.Param;
import org.jooq.Query;
import org.junit.Test;
/**
* @author Lukas Eder
*/
public class ParamTest extends AbstractTest {
@SuppressWarnings("unchecked")
@Test
public void testData() {
Query query = create.select(val(1), inline(2)).where(val(3).ne(inline(4)));
List<Param<?>> values = new ArrayList<Param<?>>(query.getParams().values());
assertEquals(asList(val(1), inline(2), val(3), inline(4)), values);
assertEquals(1, values.get(0).getValue());
assertEquals(2, values.get(1).getValue());
assertEquals(3, values.get(2).getValue());
assertEquals(4, values.get(3).getValue());
assertFalse(values.get(0).isInline());
assertTrue(values.get(1).isInline());
assertFalse(values.get(2).isInline());
assertTrue(values.get(3).isInline());
assertEquals(asList(1, 3), query.getBindValues());
}
}