Consistent Map<String, ?> declarations and use of LinkedHashMap for incoming JDBC operation parameters

Issue: SPR-12462
This commit is contained in:
Juergen Hoeller 2014-11-24 13:59:09 +01:00
parent 223d849a14
commit 2b4004d176
9 changed files with 204 additions and 197 deletions

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2011 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -65,11 +65,8 @@ public class CallMetaDataContext {
/** List of SqlParameter objects to be used in call execution */ /** List of SqlParameter objects to be used in call execution */
private List<SqlParameter> callParameters = new ArrayList<SqlParameter>(); private List<SqlParameter> callParameters = new ArrayList<SqlParameter>();
/** Default name to use for the return value in the output map */
private String defaultFunctionReturnName = "return";
/** Actual name to use for the return value in the output map */ /** Actual name to use for the return value in the output map */
private String actualFunctionReturnName = null; private String actualFunctionReturnName;
/** Set of in parameter names to exclude use for any not listed */ /** Set of in parameter names to exclude use for any not listed */
private Set<String> limitedInParameterNames = new HashSet<String>(); private Set<String> limitedInParameterNames = new HashSet<String>();
@ -77,16 +74,16 @@ public class CallMetaDataContext {
/** List of SqlParameter names for out parameters */ /** List of SqlParameter names for out parameters */
private List<String> outParameterNames = new ArrayList<String>(); private List<String> outParameterNames = new ArrayList<String>();
/** should we access call parameter meta data info or not */ /** Indicates whether this is a procedure or a function **/
private boolean function = false;
/** Indicates whether this procedure's return value should be included **/
private boolean returnValueRequired = false;
/** Should we access call parameter meta data info or not */
private boolean accessCallParameterMetaData = true; private boolean accessCallParameterMetaData = true;
/** indicates whether this is a procedure or a function **/ /** The provider of call meta data */
private boolean function;
/** indicates whether this procedure's return value should be included **/
private boolean returnValueRequired;
/** the provider of call meta data */
private CallMetaDataProvider metaDataProvider; private CallMetaDataProvider metaDataProvider;
@ -101,7 +98,7 @@ public class CallMetaDataContext {
* Get the name used for the return value of the function. * Get the name used for the return value of the function.
*/ */
public String getFunctionReturnName() { public String getFunctionReturnName() {
return this.actualFunctionReturnName != null ? this.actualFunctionReturnName : this.defaultFunctionReturnName; return (this.actualFunctionReturnName != null ? this.actualFunctionReturnName : "return");
} }
/** /**
@ -571,15 +568,15 @@ public class CallMetaDataContext {
// and the catalog name since the cataog is used for the package name // and the catalog name since the cataog is used for the package name
if (this.metaDataProvider.isSupportsSchemasInProcedureCalls() && if (this.metaDataProvider.isSupportsSchemasInProcedureCalls() &&
!this.metaDataProvider.isSupportsCatalogsInProcedureCalls()) { !this.metaDataProvider.isSupportsCatalogsInProcedureCalls()) {
schemaNameToUse = this.metaDataProvider.catalogNameToUse(this.getCatalogName()); schemaNameToUse = this.metaDataProvider.catalogNameToUse(getCatalogName());
catalogNameToUse = this.metaDataProvider.schemaNameToUse(this.getSchemaName()); catalogNameToUse = this.metaDataProvider.schemaNameToUse(getSchemaName());
} }
else { else {
catalogNameToUse = this.metaDataProvider.catalogNameToUse(this.getCatalogName()); catalogNameToUse = this.metaDataProvider.catalogNameToUse(getCatalogName());
schemaNameToUse = this.metaDataProvider.schemaNameToUse(this.getSchemaName()); schemaNameToUse = this.metaDataProvider.schemaNameToUse(getSchemaName());
} }
String procedureNameToUse = this.metaDataProvider.procedureNameToUse(this.getProcedureName()); String procedureNameToUse = this.metaDataProvider.procedureNameToUse(getProcedureName());
if (this.isFunction() || this.isReturnValueRequired()) { if (isFunction() || isReturnValueRequired()) {
callString = "{? = call " + callString = "{? = call " +
(StringUtils.hasLength(catalogNameToUse) ? catalogNameToUse + "." : "") + (StringUtils.hasLength(catalogNameToUse) ? catalogNameToUse + "." : "") +
(StringUtils.hasLength(schemaNameToUse) ? schemaNameToUse + "." : "") + (StringUtils.hasLength(schemaNameToUse) ? schemaNameToUse + "." : "") +

View File

@ -17,8 +17,8 @@
package org.springframework.jdbc.core.metadata; package org.springframework.jdbc.core.metadata;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap; import java.util.LinkedHashMap;
import java.util.HashSet; import java.util.LinkedHashSet;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Set; import java.util.Set;
@ -39,6 +39,7 @@ import org.springframework.jdbc.support.nativejdbc.NativeJdbcExtractor;
* and execution of operations on a database table. * and execution of operations on a database table.
* *
* @author Thomas Risberg * @author Thomas Risberg
* @author Juergen Hoeller
* @since 2.5 * @since 2.5
*/ */
public class TableMetaDataContext { public class TableMetaDataContext {
@ -217,7 +218,7 @@ public class TableMetaDataContext {
if (declaredColumns.size() > 0) { if (declaredColumns.size() > 0) {
return new ArrayList<String>(declaredColumns); return new ArrayList<String>(declaredColumns);
} }
Set<String> keys = new HashSet<String>(generatedKeyNames.length); Set<String> keys = new LinkedHashSet<String>(generatedKeyNames.length);
for (String key : generatedKeyNames) { for (String key : generatedKeyNames) {
keys.add(key.toUpperCase()); keys.add(key.toUpperCase());
} }
@ -274,9 +275,9 @@ public class TableMetaDataContext {
* Match the provided column names and values with the list of columns used. * Match the provided column names and values with the list of columns used.
* @param inParameters the parameter names and values * @param inParameters the parameter names and values
*/ */
public List<Object> matchInParameterValuesWithInsertColumns(Map<String, Object> inParameters) { public List<Object> matchInParameterValuesWithInsertColumns(Map<String, ?> inParameters) {
List<Object> values = new ArrayList<Object>(); List<Object> values = new ArrayList<Object>();
Map<String, Object> source = new HashMap<String, Object>(); Map<String, Object> source = new LinkedHashMap<String, Object>(inParameters.size());
for (String key : inParameters.keySet()) { for (String key : inParameters.keySet()) {
source.put(key.toLowerCase(), inParameters.get(key)); source.put(key.toLowerCase(), inParameters.get(key));
} }
@ -292,7 +293,7 @@ public class TableMetaDataContext {
* @return the insert string to be used * @return the insert string to be used
*/ */
public String createInsertString(String... generatedKeyNames) { public String createInsertString(String... generatedKeyNames) {
HashSet<String> keys = new HashSet<String>(generatedKeyNames.length); Set<String> keys = new LinkedHashSet<String>(generatedKeyNames.length);
for (String key : generatedKeyNames) { for (String key : generatedKeyNames) {
keys.add(key.toUpperCase()); keys.add(key.toUpperCase());
} }
@ -342,7 +343,8 @@ public class TableMetaDataContext {
public int[] createInsertTypes() { public int[] createInsertTypes() {
int[] types = new int[this.getTableColumns().size()]; int[] types = new int[this.getTableColumns().size()];
List<TableParameterMetaData> parameters = this.metaDataProvider.getTableParameterMetaData(); List<TableParameterMetaData> parameters = this.metaDataProvider.getTableParameterMetaData();
Map<String, TableParameterMetaData> parameterMap = new HashMap<String, TableParameterMetaData>(parameters.size()); Map<String, TableParameterMetaData> parameterMap =
new LinkedHashMap<String, TableParameterMetaData>(parameters.size());
for (TableParameterMetaData tpmd : parameters) { for (TableParameterMetaData tpmd : parameters) {
parameterMap.put(tpmd.getParameterName().toUpperCase(), tpmd); parameterMap.put(tpmd.getParameterName().toUpperCase(), tpmd);
} }

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2012 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -17,7 +17,7 @@
package org.springframework.jdbc.core.namedparam; package org.springframework.jdbc.core.namedparam;
import java.util.Collections; import java.util.Collections;
import java.util.HashMap; import java.util.LinkedHashMap;
import java.util.Map; import java.util.Map;
import org.springframework.jdbc.core.SqlParameterValue; import org.springframework.jdbc.core.SqlParameterValue;
@ -29,8 +29,8 @@ import org.springframework.util.Assert;
* <p>This class is intended for passing in a simple Map of parameter values * <p>This class is intended for passing in a simple Map of parameter values
* to the methods of the {@link NamedParameterJdbcTemplate} class. * to the methods of the {@link NamedParameterJdbcTemplate} class.
* *
* <p>The {@code addValue} methods on this class will make adding several * <p>The {@code addValue} methods on this class will make adding several values
* values easier. The methods return a reference to the {@link MapSqlParameterSource} * easier. The methods return a reference to the {@link MapSqlParameterSource}
* itself, so you can chain several method calls together within a single statement. * itself, so you can chain several method calls together within a single statement.
* *
* @author Thomas Risberg * @author Thomas Risberg
@ -43,7 +43,7 @@ import org.springframework.util.Assert;
*/ */
public class MapSqlParameterSource extends AbstractSqlParameterSource { public class MapSqlParameterSource extends AbstractSqlParameterSource {
private final Map<String, Object> values = new HashMap<String, Object>(); private final Map<String, Object> values = new LinkedHashMap<String, Object>();
/** /**

View File

@ -43,6 +43,7 @@ import org.springframework.util.StringUtils;
* This class provides the base SPI for {@link SimpleJdbcCall}. * This class provides the base SPI for {@link SimpleJdbcCall}.
* *
* @author Thomas Risberg * @author Thomas Risberg
* @author Juergen Hoeller
* @since 2.5 * @since 2.5
*/ */
public abstract class AbstractJdbcCall { public abstract class AbstractJdbcCall {
@ -63,9 +64,8 @@ public abstract class AbstractJdbcCall {
private final Map<String, RowMapper<?>> declaredRowMappers = new LinkedHashMap<String, RowMapper<?>>(); private final Map<String, RowMapper<?>> declaredRowMappers = new LinkedHashMap<String, RowMapper<?>>();
/** /**
* Has this operation been compiled? Compilation means at * Has this operation been compiled? Compilation means at least checking
* least checking that a DataSource and sql have been provided, * that a DataSource or JdbcTemplate has been provided.
* but subclasses may also implement their own custom validation.
*/ */
private boolean compiled = false; private boolean compiled = false;
@ -73,7 +73,7 @@ public abstract class AbstractJdbcCall {
private String callString; private String callString;
/** /**
* Object enabling us to create CallableStatementCreators * A delegate enabling us to create CallableStatementCreators
* efficiently, based on this class's declared parameters. * efficiently, based on this class's declared parameters.
*/ */
private CallableStatementCreatorFactory callableStatementFactory; private CallableStatementCreatorFactory callableStatementFactory;
@ -92,6 +92,7 @@ public abstract class AbstractJdbcCall {
* @param jdbcTemplate the JdbcTemplate to use * @param jdbcTemplate the JdbcTemplate to use
*/ */
protected AbstractJdbcCall(JdbcTemplate jdbcTemplate) { protected AbstractJdbcCall(JdbcTemplate jdbcTemplate) {
Assert.notNull(jdbcTemplate, "JdbcTemplate must not be null");
this.jdbcTemplate = jdbcTemplate; this.jdbcTemplate = jdbcTemplate;
} }
@ -161,6 +162,7 @@ public abstract class AbstractJdbcCall {
/** /**
* Specify whether this call is a function call. * Specify whether this call is a function call.
* The default is {@code false}.
*/ */
public void setFunction(boolean function) { public void setFunction(boolean function) {
this.callMetaDataContext.setFunction(function); this.callMetaDataContext.setFunction(function);
@ -174,7 +176,8 @@ public abstract class AbstractJdbcCall {
} }
/** /**
* Specify whether the call requires a rerurn value. * Specify whether the call requires a return value.
* The default is {@code false}.
*/ */
public void setReturnValueRequired(boolean returnValueRequired) { public void setReturnValueRequired(boolean returnValueRequired) {
this.callMetaDataContext.setReturnValueRequired(returnValueRequired); this.callMetaDataContext.setReturnValueRequired(returnValueRequired);
@ -188,7 +191,8 @@ public abstract class AbstractJdbcCall {
} }
/** /**
* Specify whether the parameter metadata for the call should be used. The default is true. * Specify whether the parameter metadata for the call should be used.
* The default is {@code true}.
*/ */
public void setAccessCallParameterMetaData(boolean accessCallParameterMetaData) { public void setAccessCallParameterMetaData(boolean accessCallParameterMetaData) {
this.callMetaDataContext.setAccessCallParameterMetaData(accessCallParameterMetaData); this.callMetaDataContext.setAccessCallParameterMetaData(accessCallParameterMetaData);
@ -211,10 +215,10 @@ public abstract class AbstractJdbcCall {
/** /**
* Add a declared parameter to the list of parameters for the call. * Add a declared parameter to the list of parameters for the call.
* Only parameters declared as {@code SqlParameter} and {@code SqlInOutParameter} * <p>Only parameters declared as {@code SqlParameter} and {@code SqlInOutParameter} will
* will be used to provide input values. This is different from the {@code StoredProcedure} class * be used to provide input values. This is different from the {@code StoredProcedure}
* which for backwards compatibility reasons allows input values to be provided for parameters declared * class which - for backwards compatibility reasons - allows input values to be provided
* as {@code SqlOutParameter}. * for parameters declared as {@code SqlOutParameter}.
* @param parameter the {@link SqlParameter} to add * @param parameter the {@link SqlParameter} to add
*/ */
public void addDeclaredParameter(SqlParameter parameter) { public void addDeclaredParameter(SqlParameter parameter) {
@ -247,9 +251,9 @@ public abstract class AbstractJdbcCall {
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
/** /**
* Compile this JdbcCall using provided parameters and meta data plus other settings. This * Compile this JdbcCall using provided parameters and meta data plus other settings.
* finalizes the configuration for this object and subsequent attempts to compile are ignored. * <p>This finalizes the configuration for this object and subsequent attempts to compile are
* This will be implicitly called the first time an un-compiled call is executed. * ignored. This will be implicitly called the first time an un-compiled call is executed.
* @throws org.springframework.dao.InvalidDataAccessApiUsageException if the object hasn't * @throws org.springframework.dao.InvalidDataAccessApiUsageException if the object hasn't
* been correctly initialized, for example if no DataSource has been provided * been correctly initialized, for example if no DataSource has been provided
*/ */
@ -267,19 +271,21 @@ public abstract class AbstractJdbcCall {
compileInternal(); compileInternal();
this.compiled = true; this.compiled = true;
if (logger.isDebugEnabled()) { if (logger.isDebugEnabled()) {
logger.debug("SqlCall for " + (isFunction() ? "function" : "procedure") + " [" + getProcedureName() + "] compiled"); logger.debug("SqlCall for " + (isFunction() ? "function" : "procedure") +
" [" + getProcedureName() + "] compiled");
} }
} }
} }
/** /**
* Method to perform the actual compilation. Subclasses can override this template method to perform * Delegate method to perform the actual compilation.
* their own compilation. Invoked after this base class's compilation is complete. * <p>Subclasses can override this template method to perform their own compilation.
* Invoked after this base class's compilation is complete.
*/ */
protected void compileInternal() { protected void compileInternal() {
this.callMetaDataContext.initializeMetaData(getJdbcTemplate().getDataSource()); this.callMetaDataContext.initializeMetaData(getJdbcTemplate().getDataSource());
// iterate over the declared RowMappers and register the corresponding SqlParameter // Iterate over the declared RowMappers and register the corresponding SqlParameter
for (Map.Entry<String, RowMapper<?>> entry : this.declaredRowMappers.entrySet()) { for (Map.Entry<String, RowMapper<?>> entry : this.declaredRowMappers.entrySet()) {
SqlParameter resultSetParameter = SqlParameter resultSetParameter =
this.callMetaDataContext.createReturnResultSetParameter(entry.getKey(), entry.getValue()); this.callMetaDataContext.createReturnResultSetParameter(entry.getKey(), entry.getValue());
@ -332,7 +338,7 @@ public abstract class AbstractJdbcCall {
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
/** /**
* Method that provides execution of the call using the passed in {@link SqlParameterSource} * Delegate method that executes the call using the passed-in {@link SqlParameterSource}.
* @param parameterSource parameter names and values to be used in call * @param parameterSource parameter names and values to be used in call
* @return Map of out parameters * @return Map of out parameters
*/ */
@ -343,18 +349,19 @@ public abstract class AbstractJdbcCall {
} }
/** /**
* Method that provides execution of the call using the passed in array of parameters * Delegate method that executes the call using the passed-in array of parameters.
* @param args array of parameter values; order must match the order declared for the stored procedure * @param args array of parameter values. The order of values must match the order
* declared for the stored procedure.
* @return Map of out parameters * @return Map of out parameters
*/ */
protected Map<String, Object> doExecute(Object[] args) { protected Map<String, Object> doExecute(Object... args) {
checkCompiled(); checkCompiled();
Map<String, ?> params = matchInParameterValuesWithCallParameters(args); Map<String, ?> params = matchInParameterValuesWithCallParameters(args);
return executeCallInternal(params); return executeCallInternal(params);
} }
/** /**
* Method that provides execution of the call using the passed in Map of parameters * Delegate method that executes the call using the passed-in Map of parameters.
* @param args Map of parameter name and values * @param args Map of parameter name and values
* @return Map of out parameters * @return Map of out parameters
*/ */
@ -365,7 +372,7 @@ public abstract class AbstractJdbcCall {
} }
/** /**
* Method to perform the actual call processing * Delegate method to perform the actual call processing.
*/ */
private Map<String, Object> executeCallInternal(Map<String, ?> args) { private Map<String, Object> executeCallInternal(Map<String, ?> args) {
CallableStatementCreator csc = getCallableStatementFactory().newCallableStatementCreator(args); CallableStatementCreator csc = getCallableStatementFactory().newCallableStatementCreator(args);
@ -391,8 +398,8 @@ public abstract class AbstractJdbcCall {
} }
/** /**
* Get a List of all the call parameters to be used for call. This includes any parameters added * Get a List of all the call parameters to be used for call.
* based on meta data processing. * This includes any parameters added based on meta data processing.
*/ */
protected List<SqlParameter> getCallParameters() { protected List<SqlParameter> getCallParameters() {
return this.callMetaDataContext.getCallParameters(); return this.callMetaDataContext.getCallParameters();

View File

@ -78,8 +78,7 @@ public abstract class AbstractJdbcInsert {
/** /**
* Has this operation been compiled? Compilation means at least checking * Has this operation been compiled? Compilation means at least checking
* that a DataSource or JdbcTemplate has been provided, but subclasses * that a DataSource or JdbcTemplate has been provided.
* may also implement their own custom validation.
*/ */
private boolean compiled = false; private boolean compiled = false;
@ -91,14 +90,16 @@ public abstract class AbstractJdbcInsert {
/** /**
* Constructor for sublasses to delegate to for setting the DataSource. * Constructor to be used when initializing using a {@link DataSource}.
* @param dataSource the DataSource to be used
*/ */
protected AbstractJdbcInsert(DataSource dataSource) { protected AbstractJdbcInsert(DataSource dataSource) {
this.jdbcTemplate = new JdbcTemplate(dataSource); this.jdbcTemplate = new JdbcTemplate(dataSource);
} }
/** /**
* Constructor for sublasses to delegate to for setting the JdbcTemplate. * Constructor to be used when initializing using a {@link JdbcTemplate}.
* @param jdbcTemplate the JdbcTemplate to use
*/ */
protected AbstractJdbcInsert(JdbcTemplate jdbcTemplate) { protected AbstractJdbcInsert(JdbcTemplate jdbcTemplate) {
Assert.notNull(jdbcTemplate, "JdbcTemplate must not be null"); Assert.notNull(jdbcTemplate, "JdbcTemplate must not be null");
@ -112,7 +113,7 @@ public abstract class AbstractJdbcInsert {
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
/** /**
* Get the {@link JdbcTemplate} that is configured to be used. * Get the configured {@link JdbcTemplate}.
*/ */
public JdbcTemplate getJdbcTemplate() { public JdbcTemplate getJdbcTemplate() {
return this.jdbcTemplate; return this.jdbcTemplate;
@ -271,8 +272,9 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method to perform the actual compilation. Subclasses can override this template method * Delegate method to perform the actual compilation.
* to perform their own compilation. Invoked after this base class's compilation is complete. * <p>Subclasses can override this template method to perform their own compilation.
* Invoked after this base class's compilation is complete.
*/ */
protected void compileInternal() { protected void compileInternal() {
this.tableMetaDataContext.processMetaData( this.tableMetaDataContext.processMetaData(
@ -287,7 +289,7 @@ public abstract class AbstractJdbcInsert {
/** /**
* Hook method that subclasses may override to react to compilation. * Hook method that subclasses may override to react to compilation.
* This implementation does nothing. * <p>This implementation is empty.
*/ */
protected void onCompileInternal() { protected void onCompileInternal() {
} }
@ -329,20 +331,20 @@ public abstract class AbstractJdbcInsert {
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
/** /**
* Method that provides execution of the insert using the passed in Map of parameters * Delegate method that executes the insert using the passed-in Map of parameters.
* @param args Map with parameter names and values to be used in insert * @param args Map with parameter names and values to be used in insert
* @return number of rows affected * @return the number of rows affected
*/ */
protected int doExecute(Map<String, Object> args) { protected int doExecute(Map<String, ?> args) {
checkCompiled(); checkCompiled();
List<Object> values = matchInParameterValuesWithInsertColumns(args); List<Object> values = matchInParameterValuesWithInsertColumns(args);
return executeInsertInternal(values); return executeInsertInternal(values);
} }
/** /**
* Method that provides execution of the insert using the passed in {@link SqlParameterSource} * Delegate method that executes the insert using the passed-in {@link SqlParameterSource}.
* @param parameterSource parameter names and values to be used in insert * @param parameterSource parameter names and values to be used in insert
* @return number of rows affected * @return the number of rows affected
*/ */
protected int doExecute(SqlParameterSource parameterSource) { protected int doExecute(SqlParameterSource parameterSource) {
checkCompiled(); checkCompiled();
@ -351,9 +353,9 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method to execute the insert. * Delegate method to execute the insert.
*/ */
private int executeInsertInternal(List<Object> values) { private int executeInsertInternal(List<?> values) {
if (logger.isDebugEnabled()) { if (logger.isDebugEnabled()) {
logger.debug("The following parameters are used for insert " + getInsertString() + " with: " + values); logger.debug("The following parameters are used for insert " + getInsertString() + " with: " + values);
} }
@ -361,22 +363,20 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method that provides execution of the insert using the passed in Map of parameters * Method that provides execution of the insert using the passed-in
* and returning a generated key * Map of parameters and returning a generated key.
*
* @param args Map with parameter names and values to be used in insert * @param args Map with parameter names and values to be used in insert
* @return the key generated by the insert * @return the key generated by the insert
*/ */
protected Number doExecuteAndReturnKey(Map<String, Object> args) { protected Number doExecuteAndReturnKey(Map<String, ?> args) {
checkCompiled(); checkCompiled();
List<Object> values = matchInParameterValuesWithInsertColumns(args); List<Object> values = matchInParameterValuesWithInsertColumns(args);
return executeInsertAndReturnKeyInternal(values); return executeInsertAndReturnKeyInternal(values);
} }
/** /**
* Method that provides execution of the insert using the passed in {@link SqlParameterSource} * Method that provides execution of the insert using the passed-in
* and returning a generated key * {@link SqlParameterSource} and returning a generated key.
*
* @param parameterSource parameter names and values to be used in insert * @param parameterSource parameter names and values to be used in insert
* @return the key generated by the insert * @return the key generated by the insert
*/ */
@ -387,22 +387,20 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method that provides execution of the insert using the passed in Map of parameters * Method that provides execution of the insert using the passed-in
* and returning all generated keys * Map of parameters and returning all generated keys.
*
* @param args Map with parameter names and values to be used in insert * @param args Map with parameter names and values to be used in insert
* @return the KeyHolder containing keys generated by the insert * @return the KeyHolder containing keys generated by the insert
*/ */
protected KeyHolder doExecuteAndReturnKeyHolder(Map<String, Object> args) { protected KeyHolder doExecuteAndReturnKeyHolder(Map<String, ?> args) {
checkCompiled(); checkCompiled();
List<Object> values = matchInParameterValuesWithInsertColumns(args); List<Object> values = matchInParameterValuesWithInsertColumns(args);
return executeInsertAndReturnKeyHolderInternal(values); return executeInsertAndReturnKeyHolderInternal(values);
} }
/** /**
* Method that provides execution of the insert using the passed in {@link SqlParameterSource} * Method that provides execution of the insert using the passed-in
* and returning all generated keys * {@link SqlParameterSource} and returning all generated keys.
*
* @param parameterSource parameter names and values to be used in insert * @param parameterSource parameter names and values to be used in insert
* @return the KeyHolder containing keys generated by the insert * @return the KeyHolder containing keys generated by the insert
*/ */
@ -413,9 +411,9 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method to execute the insert generating single key * Delegate method to execute the insert, generating a single key.
*/ */
private Number executeInsertAndReturnKeyInternal(final List<Object> values) { private Number executeInsertAndReturnKeyInternal(final List<?> values) {
KeyHolder kh = executeInsertAndReturnKeyHolderInternal(values); KeyHolder kh = executeInsertAndReturnKeyHolderInternal(values);
if (kh != null && kh.getKey() != null) { if (kh != null && kh.getKey() != null) {
return kh.getKey(); return kh.getKey();
@ -427,9 +425,9 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method to execute the insert generating any number of keys * Delegate method to execute the insert, generating any number of keys.
*/ */
private KeyHolder executeInsertAndReturnKeyHolderInternal(final List<Object> values) { private KeyHolder executeInsertAndReturnKeyHolderInternal(final List<?> values) {
if (logger.isDebugEnabled()) { if (logger.isDebugEnabled()) {
logger.debug("The following parameters are used for call " + getInsertString() + " with: " + values); logger.debug("The following parameters are used for call " + getInsertString() + " with: " + values);
} }
@ -514,16 +512,14 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Create the PreparedStatement to be used for insert that have generated keys * Create a PreparedStatement to be used for an insert operation with generated keys.
* * @param con the Connection to use
* @param con the connection used * @return the PreparedStatement
* @return PreparedStatement to use
* @throws SQLException
*/ */
private PreparedStatement prepareStatementForGeneratedKeys(Connection con) throws SQLException { private PreparedStatement prepareStatementForGeneratedKeys(Connection con) throws SQLException {
if (getGeneratedKeyNames().length < 1) { if (getGeneratedKeyNames().length < 1) {
throw new InvalidDataAccessApiUsageException("Generated Key Name(s) not specificed. " + throw new InvalidDataAccessApiUsageException("Generated Key Name(s) not specified. " +
"Using the generated keys features requires specifying the name(s) of the generated column(s)"); "Using the generated keys features requires specifying the name(s) of the generated column(s).");
} }
PreparedStatement ps; PreparedStatement ps;
if (this.tableMetaDataContext.isGeneratedKeysColumnNameArraySupported()) { if (this.tableMetaDataContext.isGeneratedKeysColumnNameArraySupported()) {
@ -542,56 +538,49 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Method that provides execution of a batch insert using the passed in Maps of parameters. * Delegate method that executes a batch insert using the passed-in Maps of parameters.
* @param batch array of Maps with parameter names and values to be used in batch insert * @param batch array of Maps with parameter names and values to be used in batch insert
* @return array of number of rows affected * @return array of number of rows affected
*/ */
@SuppressWarnings({ "unchecked", "rawtypes" }) protected int[] doExecuteBatch(Map<String, ?>... batch) {
protected int[] doExecuteBatch(Map<String, Object>[] batch) {
checkCompiled(); checkCompiled();
List[] batchValues = new ArrayList[batch.length]; List<List<Object>> batchValues = new ArrayList<List<Object>>(batch.length);
int i = 0; for (Map<String, ?> args : batch) {
for (Map<String, Object> args : batch) { batchValues.add(matchInParameterValuesWithInsertColumns(args));
List<Object> values = matchInParameterValuesWithInsertColumns(args);
batchValues[i++] = values;
} }
return executeBatchInternal(batchValues); return executeBatchInternal(batchValues);
} }
/** /**
* Method that provides execution of a batch insert using the passed in array of {@link SqlParameterSource} * Delegate method that executes a batch insert using the passed-in {@link SqlParameterSource}s.
* @param batch array of SqlParameterSource with parameter names and values to be used in insert * @param batch array of SqlParameterSource with parameter names and values to be used in insert
* @return array of number of rows affected * @return array of number of rows affected
*/ */
@SuppressWarnings({ "unchecked", "rawtypes" }) protected int[] doExecuteBatch(SqlParameterSource... batch) {
protected int[] doExecuteBatch(SqlParameterSource[] batch) {
checkCompiled(); checkCompiled();
List[] batchValues = new ArrayList[batch.length]; List<List<Object>> batchValues = new ArrayList<List<Object>>(batch.length);
int i = 0;
for (SqlParameterSource parameterSource : batch) { for (SqlParameterSource parameterSource : batch) {
List<Object> values = matchInParameterValuesWithInsertColumns(parameterSource); batchValues.add(matchInParameterValuesWithInsertColumns(parameterSource));
batchValues[i++] = values;
} }
return executeBatchInternal(batchValues); return executeBatchInternal(batchValues);
} }
/** /**
* Method to execute the batch insert. * Delegate method to execute the batch insert.
*/ */
private int[] executeBatchInternal(final List<Object>[] batchValues) { private int[] executeBatchInternal(final List<List<Object>> batchValues) {
if (logger.isDebugEnabled()) { if (logger.isDebugEnabled()) {
logger.debug("Executing statement " + getInsertString() + " with batch of size: " + batchValues.length); logger.debug("Executing statement " + getInsertString() + " with batch of size: " + batchValues.size());
} }
return getJdbcTemplate().batchUpdate(getInsertString(), return getJdbcTemplate().batchUpdate(getInsertString(),
new BatchPreparedStatementSetter() { new BatchPreparedStatementSetter() {
@Override @Override
public void setValues(PreparedStatement ps, int i) throws SQLException { public void setValues(PreparedStatement ps, int i) throws SQLException {
List<Object> values = batchValues[i]; setParameterValues(ps, batchValues.get(i), getInsertTypes());
setParameterValues(ps, values, getInsertTypes());
} }
@Override @Override
public int getBatchSize() { public int getBatchSize() {
return batchValues.length; return batchValues.size();
} }
}); });
} }
@ -601,7 +590,7 @@ public abstract class AbstractJdbcInsert {
* @param preparedStatement the PreparedStatement * @param preparedStatement the PreparedStatement
* @param values the values to be set * @param values the values to be set
*/ */
private void setParameterValues(PreparedStatement preparedStatement, List<Object> values, int[] columnTypes) private void setParameterValues(PreparedStatement preparedStatement, List<?> values, int... columnTypes)
throws SQLException { throws SQLException {
int colIndex = 0; int colIndex = 0;
@ -617,8 +606,8 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Match the provided in parameter values with registered parameters and parameters defined * Match the provided in parameter values with registered parameters and parameters
* via metadata processing. * defined via metadata processing.
* @param parameterSource the parameter values provided as a {@link SqlParameterSource} * @param parameterSource the parameter values provided as a {@link SqlParameterSource}
* @return Map with parameter names and values * @return Map with parameter names and values
*/ */
@ -627,12 +616,12 @@ public abstract class AbstractJdbcInsert {
} }
/** /**
* Match the provided in parameter values with regitered parameters and parameters defined * Match the provided in parameter values with registered parameters and parameters
* via metadata processing. * defined via metadata processing.
* @param args the parameter values provided in a Map * @param args the parameter values provided in a Map
* @return Map with parameter names and values * @return Map with parameter names and values
*/ */
protected List<Object> matchInParameterValuesWithInsertColumns(Map<String, Object> args) { protected List<Object> matchInParameterValuesWithInsertColumns(Map<String, ?> args) {
return this.tableMetaDataContext.matchInParameterValuesWithInsertColumns(args); return this.tableMetaDataContext.matchInParameterValuesWithInsertColumns(args);
} }

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2013 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -17,7 +17,7 @@
package org.springframework.jdbc.core.simple; package org.springframework.jdbc.core.simple;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashSet; import java.util.LinkedHashSet;
import java.util.Map; import java.util.Map;
import javax.sql.DataSource; import javax.sql.DataSource;
@ -123,7 +123,7 @@ public class SimpleJdbcCall extends AbstractJdbcCall implements SimpleJdbcCallOp
@Override @Override
public SimpleJdbcCall useInParameterNames(String... inParameterNames) { public SimpleJdbcCall useInParameterNames(String... inParameterNames) {
setInParameterNames(new HashSet<String>(Arrays.asList(inParameterNames))); setInParameterNames(new LinkedHashSet<String>(Arrays.asList(inParameterNames)));
return this; return this;
} }

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2013 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -24,8 +24,8 @@ import org.springframework.jdbc.core.namedparam.SqlParameterSource;
/** /**
* Interface specifying the API for a Simple JDBC Call implemented by {@link SimpleJdbcCall}. * Interface specifying the API for a Simple JDBC Call implemented by {@link SimpleJdbcCall}.
* This interface is not often used directly, but provides the * This interface is not often used directly, but provides the option to enhance testability,
* option to enhance testability, as it can easily be mocked or stubbed. * as it can easily be mocked or stubbed.
* *
* @author Thomas Risberg * @author Thomas Risberg
* @since 2.5 * @since 2.5
@ -55,8 +55,8 @@ public interface SimpleJdbcCallOperations {
/** /**
* Optionally, specify the name of the catalog that contins the stored procedure. * Optionally, specify the name of the catalog that contins the stored procedure.
* To provide consistency with the Oracle DatabaseMetaData, this is used to specify the package name if * <p>To provide consistency with the Oracle DatabaseMetaData, this is used to specify the
* the procedure is declared as part of a package. * package name if the procedure is declared as part of a package.
* @param catalogName the catalog or package name * @param catalogName the catalog or package name
* @return the instance of this SimpleJdbcCall * @return the instance of this SimpleJdbcCall
*/ */
@ -69,12 +69,12 @@ public interface SimpleJdbcCallOperations {
SimpleJdbcCallOperations withReturnValue(); SimpleJdbcCallOperations withReturnValue();
/** /**
* Specify one or more parameters if desired. These parameters will be supplemented with any * Specify one or more parameters if desired. These parameters will be supplemented with
* parameter information retrieved from the database meta data. * any parameter information retrieved from the database meta data.
* Note that only parameters declared as {@code SqlParameter} and {@code SqlInOutParameter} * <p>Note that only parameters declared as {@code SqlParameter} and {@code SqlInOutParameter}
* will be used to provide input values. This is different from the {@code StoredProcedure} class * will be used to provide input values. This is different from the {@code StoredProcedure}
* which for backwards compatibility reasons allows input values to be provided for parameters declared * class which - for backwards compatibility reasons - allows input values to be provided
* as {@code SqlOutParameter}. * for parameters declared as {@code SqlOutParameter}.
* @param sqlParameters the parameters to use * @param sqlParameters the parameters to use
* @return the instance of this SimpleJdbcCall * @return the instance of this SimpleJdbcCall
*/ */
@ -84,11 +84,11 @@ public interface SimpleJdbcCallOperations {
SimpleJdbcCallOperations useInParameterNames(String... inParameterNames); SimpleJdbcCallOperations useInParameterNames(String... inParameterNames);
/** /**
* Used to specify when a ResultSet is returned by the stored procedure and you want it mapped * Used to specify when a ResultSet is returned by the stored procedure and you want it
* by a RowMapper. The results will be returned using the parameter name specified. Multiple * mapped by a {@link RowMapper}. The results will be returned using the parameter name
* ResultSets must be declared in the correct order. If the database you are using uses ref cursors * specified. Multiple ResultSets must be declared in the correct order.
* then the name specified must match the name of the parameter declared for the procedure in the * <p>If the database you are using uses ref cursors then the name specified must match
* database. * the name of the parameter declared for the procedure in the database.
* @param parameterName the name of the returned results and/or the name of the ref cursor parameter * @param parameterName the name of the returned results and/or the name of the ref cursor parameter
* @param rowMapper the RowMapper implementation that will map the data returned for each row * @param rowMapper the RowMapper implementation that will map the data returned for each row
* */ * */
@ -102,7 +102,8 @@ public interface SimpleJdbcCallOperations {
/** /**
* Execute the stored function and return the results obtained as an Object of the specified return type. * Execute the stored function and return the results obtained as an Object of the
* specified return type.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args optional array containing the in parameter values to be used in the call. * @param args optional array containing the in parameter values to be used in the call.
* Parameter values must be provided in the same order as the parameters are defined * Parameter values must be provided in the same order as the parameters are defined
@ -111,66 +112,73 @@ public interface SimpleJdbcCallOperations {
<T> T executeFunction(Class<T> returnType, Object... args); <T> T executeFunction(Class<T> returnType, Object... args);
/** /**
* Execute the stored function and return the results obtained as an Object of the specified return type. * Execute the stored function and return the results obtained as an Object of the
* specified return type.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args Map containing the parameter values to be used in the call. * @param args Map containing the parameter values to be used in the call
*/ */
<T> T executeFunction(Class<T> returnType, Map<String, ?> args); <T> T executeFunction(Class<T> returnType, Map<String, ?> args);
/** /**
* Execute the stored function and return the results obtained as an Object of the specified return type. * Execute the stored function and return the results obtained as an Object of the
* specified return type.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args MapSqlParameterSource containing the parameter values to be used in the call. * @param args MapSqlParameterSource containing the parameter values to be used in the call
*/ */
<T> T executeFunction(Class<T> returnType, SqlParameterSource args); <T> T executeFunction(Class<T> returnType, SqlParameterSource args);
/** /**
* Execute the stored procedure and return the single out parameter as an Object of the specified return type. * Execute the stored procedure and return the single out parameter as an Object
* In the case where there are multiple out parameters, the first one is returned and additional out parameters * of the specified return type. In the case where there are multiple out parameters,
* are ignored. * the first one is returned and additional out parameters are ignored.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args optional array containing the in parameter values to be used in the call. Parameter values must * @param args optional array containing the in parameter values to be used in the call.
* be provided in the same order as the parameters are defined for the stored procedure. * Parameter values must be provided in the same order as the parameters are defined for
* the stored procedure.
*/ */
<T> T executeObject(Class<T> returnType, Object... args); <T> T executeObject(Class<T> returnType, Object... args);
/** /**
* Execute the stored procedure and return the single out parameter as an Object of the specified return type. * Execute the stored procedure and return the single out parameter as an Object
* In the case where there are multiple out parameters, the first one is returned and additional out parameters * of the specified return type. In the case where there are multiple out parameters,
* are ignored. * the first one is returned and additional out parameters are ignored.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args Map containing the parameter values to be used in the call. * @param args Map containing the parameter values to be used in the call
*/ */
<T> T executeObject(Class<T> returnType, Map<String, ?> args); <T> T executeObject(Class<T> returnType, Map<String, ?> args);
/** /**
* Execute the stored procedure and return the single out parameter as an Object of the specified return type. * Execute the stored procedure and return the single out parameter as an Object
* In the case where there are multiple out parameters, the first one is returned and additional out parameters * of the specified return type. In the case where there are multiple out parameters,
* are ignored. * the first one is returned and additional out parameters are ignored.
* @param returnType the type of the value to return * @param returnType the type of the value to return
* @param args MapSqlParameterSource containing the parameter values to be used in the call. * @param args MapSqlParameterSource containing the parameter values to be used in the call
*/ */
<T> T executeObject(Class<T> returnType, SqlParameterSource args); <T> T executeObject(Class<T> returnType, SqlParameterSource args);
/** /**
* Execute the stored procedure and return a map of output params, keyed by name as in parameter declarations. * Execute the stored procedure and return a map of output params, keyed by name
* @param args optional array containing the in parameter values to be used in the call. Parameter values must * as in parameter declarations.
* be provided in the same order as the parameters are defined for the stored procedure. * @param args optional array containing the in parameter values to be used in the call.
* @return map of output params. * Parameter values must be provided in the same order as the parameters are defined for
* the stored procedure.
* @return Map of output params
*/ */
Map<String, Object> execute(Object... args); Map<String, Object> execute(Object... args);
/** /**
* Execute the stored procedure and return a map of output params, keyed by name as in parameter declarations.. * Execute the stored procedure and return a map of output params, keyed by name
* @param args Map containing the parameter values to be used in the call. * as in parameter declarations.
* @return map of output params. * @param args Map containing the parameter values to be used in the call
* @return Map of output params
*/ */
Map<String, Object> execute(Map<String, ?> args); Map<String, Object> execute(Map<String, ?> args);
/** /**
* Execute the stored procedure and return a map of output params, keyed by name as in parameter declarations.. * Execute the stored procedure and return a map of output params, keyed by name
* @param args SqlParameterSource containing the parameter values to be used in the call. * as in parameter declarations.
* @return map of output params. * @param args SqlParameterSource containing the parameter values to be used in the call
* @return Map of output params
*/ */
Map<String, Object> execute(SqlParameterSource args); Map<String, Object> execute(SqlParameterSource args);

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2013 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -118,7 +118,7 @@ public class SimpleJdbcInsert extends AbstractJdbcInsert implements SimpleJdbcIn
} }
@Override @Override
public int execute(Map<String, Object> args) { public int execute(Map<String, ?> args) {
return doExecute(args); return doExecute(args);
} }
@ -128,7 +128,7 @@ public class SimpleJdbcInsert extends AbstractJdbcInsert implements SimpleJdbcIn
} }
@Override @Override
public Number executeAndReturnKey(Map<String, Object> args) { public Number executeAndReturnKey(Map<String, ?> args) {
return doExecuteAndReturnKey(args); return doExecuteAndReturnKey(args);
} }
@ -138,7 +138,7 @@ public class SimpleJdbcInsert extends AbstractJdbcInsert implements SimpleJdbcIn
} }
@Override @Override
public KeyHolder executeAndReturnKeyHolder(Map<String, Object> args) { public KeyHolder executeAndReturnKeyHolder(Map<String, ?> args) {
return doExecuteAndReturnKeyHolder(args); return doExecuteAndReturnKeyHolder(args);
} }
@ -148,12 +148,12 @@ public class SimpleJdbcInsert extends AbstractJdbcInsert implements SimpleJdbcIn
} }
@Override @Override
public int[] executeBatch(Map<String, Object>[] batch) { public int[] executeBatch(Map<String, ?>... batch) {
return doExecuteBatch(batch); return doExecuteBatch(batch);
} }
@Override @Override
public int[] executeBatch(SqlParameterSource[] batch) { public int[] executeBatch(SqlParameterSource... batch) {
return doExecuteBatch(batch); return doExecuteBatch(batch);
} }

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2012 the original author or authors. * Copyright 2002-2014 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -24,8 +24,8 @@ import org.springframework.jdbc.support.nativejdbc.NativeJdbcExtractor;
/** /**
* Interface specifying the API for a Simple JDBC Insert implemented by {@link SimpleJdbcInsert}. * Interface specifying the API for a Simple JDBC Insert implemented by {@link SimpleJdbcInsert}.
* This interface is not often used directly, but provides the * This interface is not often used directly, but provides the option to enhance testability,
* option to enhance testability, as it can easily be mocked or stubbed. * as it can easily be mocked or stubbed.
* *
* @author Thomas Risberg * @author Thomas Risberg
* @since 2.5 * @since 2.5
@ -98,7 +98,7 @@ public interface SimpleJdbcInsertOperations {
* @param args Map containing column names and corresponding value * @param args Map containing column names and corresponding value
* @return the number of rows affected as returned by the JDBC driver * @return the number of rows affected as returned by the JDBC driver
*/ */
int execute(Map<String, Object> args); int execute(Map<String, ?> args);
/** /**
* Execute the insert using the values passed in. * Execute the insert using the values passed in.
@ -108,36 +108,40 @@ public interface SimpleJdbcInsertOperations {
int execute(SqlParameterSource parameterSource); int execute(SqlParameterSource parameterSource);
/** /**
* Execute the insert using the values passed in and return the generated key. This requires that * Execute the insert using the values passed in and return the generated key.
* the name of the columns with auto generated keys have been specified. This method will always * <p>This requires that the name of the columns with auto generated keys have been specified.
* return a key or throw an exception if a key was not returned. * This method will always return a KeyHolder but the caller must verify that it actually
* contains the generated keys.
* @param args Map containing column names and corresponding value * @param args Map containing column names and corresponding value
* @return the generated key value * @return the generated key value
*/ */
Number executeAndReturnKey(Map<String, Object> args); Number executeAndReturnKey(Map<String, ?> args);
/** /**
* Execute the insert using the values passed in and return the generated key. This requires that * Execute the insert using the values passed in and return the generated key.
* the name of the columns with auto generated keys have been specified. This method will always * <p>This requires that the name of the columns with auto generated keys have been specified.
* return a key or throw an exception if a key was not returned. * This method will always return a KeyHolder but the caller must verify that it actually
* contains the generated keys.
* @param parameterSource SqlParameterSource containing values to use for insert * @param parameterSource SqlParameterSource containing values to use for insert
* @return the generated key value. * @return the generated key value.
*/ */
Number executeAndReturnKey(SqlParameterSource parameterSource); Number executeAndReturnKey(SqlParameterSource parameterSource);
/** /**
* Execute the insert using the values passed in and return the generated keys. This requires that * Execute the insert using the values passed in and return the generated keys.
* the name of the columns with auto generated keys have been specified. This method will always return * <p>This requires that the name of the columns with auto generated keys have been specified.
* a KeyHolder but the caller must verify that it actually contains the generated keys. * This method will always return a KeyHolder but the caller must verify that it actually
* contains the generated keys.
* @param args Map containing column names and corresponding value * @param args Map containing column names and corresponding value
* @return the KeyHolder containing all generated keys * @return the KeyHolder containing all generated keys
*/ */
KeyHolder executeAndReturnKeyHolder(Map<String, Object> args); KeyHolder executeAndReturnKeyHolder(Map<String, ?> args);
/** /**
* Execute the insert using the values passed in and return the generated keys. This requires that * Execute the insert using the values passed in and return the generated keys.
* the name of the columns with auto generated keys have been specified. This method will always return * <p>This requires that the name of the columns with auto generated keys have been specified.
* a KeyHolder but the caller must verify that it actually contains the generated keys. * This method will always return a KeyHolder but the caller must verify that it actually
* contains the generated keys.
* @param parameterSource SqlParameterSource containing values to use for insert * @param parameterSource SqlParameterSource containing values to use for insert
* @return the KeyHolder containing all generated keys * @return the KeyHolder containing all generated keys
*/ */
@ -148,13 +152,13 @@ public interface SimpleJdbcInsertOperations {
* @param batch an array of Maps containing a batch of column names and corresponding value * @param batch an array of Maps containing a batch of column names and corresponding value
* @return the array of number of rows affected as returned by the JDBC driver * @return the array of number of rows affected as returned by the JDBC driver
*/ */
int[] executeBatch(Map<String, Object>[] batch); int[] executeBatch(Map<String, ?>... batch);
/** /**
* Execute a batch insert using the batch of values passed in. * Execute a batch insert using the batch of values passed in.
* @param batch an array of SqlParameterSource containing values for the batch * @param batch an array of SqlParameterSource containing values for the batch
* @return the array of number of rows affected as returned by the JDBC driver * @return the array of number of rows affected as returned by the JDBC driver
*/ */
int[] executeBatch(SqlParameterSource[] batch); int[] executeBatch(SqlParameterSource... batch);
} }