Stop referring to JDO and outdated JDBC versions in documentation

Closes gh-31183
This commit is contained in:
Sam Brannen 2023-09-07 13:14:20 +02:00
parent 05790e36db
commit e42902b742
19 changed files with 65 additions and 61 deletions

View File

@ -2,30 +2,26 @@
= Choosing an Approach for JDBC Database Access
You can choose among several approaches to form the basis for your JDBC database access.
In addition to three flavors of `JdbcTemplate`, a new `SimpleJdbcInsert` and
`SimpleJdbcCall` approach optimizes database metadata, and the RDBMS Object style takes a
more object-oriented approach similar to that of JDO Query design. Once you start using
one of these approaches, you can still mix and match to include a feature from a
different approach. All approaches require a JDBC 2.0-compliant driver, and some
advanced features require a JDBC 3.0 driver.
In addition to three flavors of `JdbcTemplate`, a `SimpleJdbcInsert` and `SimpleJdbcCall`
approach optimizes database metadata, and the RDBMS Object style results in a more
object-oriented approach. Once you start using one of these approaches, you can still mix
and match to include a feature from a different approach.
* `JdbcTemplate` is the classic and most popular Spring JDBC approach. This
"`lowest-level`" approach and all others use a JdbcTemplate under the covers.
"`lowest-level`" approach and all others use a `JdbcTemplate` under the covers.
* `NamedParameterJdbcTemplate` wraps a `JdbcTemplate` to provide named parameters
instead of the traditional JDBC `?` placeholders. This approach provides better
documentation and ease of use when you have multiple parameters for an SQL statement.
* `SimpleJdbcInsert` and `SimpleJdbcCall` optimize database metadata to limit the amount
of necessary configuration. This approach simplifies coding so that you need to
provide only the name of the table or procedure and provide a map of parameters matching
the column names. This works only if the database provides adequate metadata. If the
database does not provide this metadata, you have to provide explicit
configuration of the parameters.
of necessary configuration. This approach simplifies coding so that you only need to
provide the name of the table or procedure and a map of parameters matching the column
names. This works only if the database provides adequate metadata. If the database does
not provide this metadata, you have to provide explicit configuration of the parameters.
* RDBMS objects — including `MappingSqlQuery`, `SqlUpdate`, and `StoredProcedure` —
require you to create reusable and thread-safe objects during initialization of your
data-access layer. This approach is modeled after JDO Query, wherein you define your
query string, declare parameters, and compile the query. Once you do that,
`execute(...)`, `update(...)`, and `findObject(...)` methods can be called multiple
times with various parameter values.
data-access layer. This approach allows you to define your query string, declare
parameters, and compile the query. Once you do that, `execute(...)`, `update(...)`, and
`findObject(...)` methods can be called multiple times with various parameter values.

View File

@ -20,9 +20,10 @@ xref:data-access/jdbc/connections.adoc[Controlling Database Connections] and xre
* `object`: The `org.springframework.jdbc.object` package contains classes that represent
RDBMS queries, updates, and stored procedures as thread-safe, reusable objects. See
xref:data-access/jdbc/object.adoc[Modeling JDBC Operations as Java Objects]. This approach is modeled by JDO, although objects returned by queries
are naturally disconnected from the database. This higher-level of JDBC abstraction
depends on the lower-level abstraction in the `org.springframework.jdbc.core` package.
xref:data-access/jdbc/object.adoc[Modeling JDBC Operations as Java Objects]. This style
results in a more object-oriented approach, although objects returned by queries are
naturally disconnected from the database. This higher-level of JDBC abstraction depends
on the lower-level abstraction in the `org.springframework.jdbc.core` package.
* `support`: The `org.springframework.jdbc.support` package provides `SQLException`
translation functionality and some utility classes. Exceptions thrown during JDBC processing

View File

@ -404,7 +404,7 @@ public class TableMetaDataContext {
/**
* Does this database support the JDBC 3.0 feature of retrieving generated keys?
* Does this database support the JDBC feature for retrieving generated keys?
* @see java.sql.DatabaseMetaData#supportsGetGeneratedKeys()
*/
public boolean isGetGeneratedKeysSupported() {
@ -412,16 +412,19 @@ public class TableMetaDataContext {
}
/**
* Does this database support a simple query to retrieve the generated key when
* the JDBC 3.0 feature of retrieving generated keys is not supported?
* Does this database support a simple query to retrieve generated keys when
* the JDBC feature for retrieving generated keys is not supported?
* @see #isGetGeneratedKeysSupported()
* @see #getSimpleQueryForGetGeneratedKey(String, String)
*/
public boolean isGetGeneratedKeysSimulated() {
return obtainMetaDataProvider().isGetGeneratedKeysSimulated();
}
/**
* Get the simple query to retrieve a generated key.
* Get the simple query to retrieve generated keys when the JDBC feature for
* retrieving generated keys is not supported.
* @see #isGetGeneratedKeysSimulated()
*/
@Nullable
public String getSimpleQueryForGetGeneratedKey(String tableName, String keyColumnName) {
@ -429,7 +432,8 @@ public class TableMetaDataContext {
}
/**
* Is a column name String array for retrieving generated keys supported?
* Does this database support a column name String array for retrieving generated
* keys?
* @see java.sql.Connection#createStruct(String, Object[])
*/
public boolean isGeneratedKeysColumnNameArraySupported() {

View File

@ -108,20 +108,23 @@ public interface TableMetaDataProvider {
boolean isTableColumnMetaDataUsed();
/**
* Does this database support the JDBC 3.0 feature of retrieving generated keys?
* Does this database support the JDBC feature for retrieving generated keys?
* @see java.sql.DatabaseMetaData#supportsGetGeneratedKeys()
*/
boolean isGetGeneratedKeysSupported();
/**
* Does this database support a simple query to retrieve the generated key when
* the JDBC 3.0 feature of retrieving generated keys is not supported?
* Does this database support a simple query to retrieve generated keys when
* the JDBC feature for retrieving generated keys is not supported?
* @see #isGetGeneratedKeysSupported()
* @see #getSimpleQueryForGetGeneratedKey(String, String)
*/
boolean isGetGeneratedKeysSimulated();
/**
* Get the simple query to retrieve a generated key.
* Get the simple query to retrieve generated keys when the JDBC feature for
* retrieving generated keys is not supported.
* @see #isGetGeneratedKeysSimulated()
*/
@Nullable
String getSimpleQueryForGetGeneratedKey(String tableName, String keyColumnName);

View File

@ -165,7 +165,7 @@ public class ConnectionHolder extends ResourceHolderSupport {
}
/**
* Return whether JDBC 3.0 Savepoints are supported.
* Return whether JDBC Savepoints are supported.
* Caches the flag for the lifetime of this ConnectionHolder.
* @throws SQLException if thrown by the JDBC driver
*/
@ -177,7 +177,7 @@ public class ConnectionHolder extends ResourceHolderSupport {
}
/**
* Create a new JDBC 3.0 Savepoint for the current Connection,
* Create a new JDBC Savepoint for the current Connection,
* using generated savepoint names that are unique for the Connection.
* @return the new Savepoint
* @throws SQLException if thrown by the JDBC driver

View File

@ -82,7 +82,7 @@ import org.springframework.util.Assert;
* until a {@code Statement} gets executed, lazily applying the specified transaction
* settings to the target {@code Connection}.
*
* <p>This transaction manager supports nested transactions via the JDBC 3.0
* <p>This transaction manager supports nested transactions via the JDBC
* {@link java.sql.Savepoint} mechanism. The
* {@link #setNestedTransactionAllowed "nestedTransactionAllowed"} flag defaults
* to "true", since nested transactions will work without restrictions on JDBC

View File

@ -137,7 +137,7 @@ public abstract class JdbcTransactionObjectSupport implements SavepointManager,
//---------------------------------------------------------------------
/**
* This implementation creates a JDBC 3.0 Savepoint and returns it.
* This implementation creates a JDBC Savepoint and returns it.
* @see java.sql.Connection#setSavepoint
*/
@Override
@ -160,7 +160,7 @@ public abstract class JdbcTransactionObjectSupport implements SavepointManager,
}
/**
* This implementation rolls back to the given JDBC 3.0 Savepoint.
* This implementation rolls back to the given JDBC Savepoint.
* @see java.sql.Connection#rollback(java.sql.Savepoint)
*/
@Override
@ -176,7 +176,7 @@ public abstract class JdbcTransactionObjectSupport implements SavepointManager,
}
/**
* This implementation releases the given JDBC 3.0 Savepoint.
* This implementation releases the given JDBC Savepoint.
* @see java.sql.Connection#releaseSavepoint
*/
@Override

View File

@ -415,14 +415,14 @@ public abstract class JdbcUtils {
}
/**
* Return whether the given JDBC driver supports JDBC 2.0 batch updates.
* Return whether the given JDBC driver supports JDBC batch updates.
* <p>Typically invoked right before execution of a given set of statements:
* to decide whether the set of SQL statements should be executed through
* the JDBC 2.0 batch mechanism or simply in a traditional one-by-one fashion.
* the JDBC batch mechanism or simply in a traditional one-by-one fashion.
* <p>Logs a warning if the "supportsBatchUpdates" methods throws an exception
* and simply returns {@code false} in that case.
* @param con the Connection to check
* @return whether JDBC 2.0 batch updates are supported
* @return whether JDBC batch updates are supported
* @see java.sql.DatabaseMetaData#supportsBatchUpdates()
*/
public static boolean supportsBatchUpdates(Connection con) {
@ -492,8 +492,8 @@ public abstract class JdbcUtils {
/**
* Determine the column name to use. The column name is determined based on a
* lookup using ResultSetMetaData.
* <p>This method implementation takes into account recent clarifications
* expressed in the JDBC 4.0 specification:
* <p>This method's implementation takes into account clarifications expressed
* in the JDBC 4.0 specification:
* <p><i>columnLabel - the label for the column specified with the SQL AS clause.
* If the SQL AS clause was not specified, then the label is the name of the column</i>.
* @param resultSetMetaData the current meta-data to use

View File

@ -41,9 +41,9 @@ import javax.sql.DataSource;
* is rolled back, the unused values will never be served. The maximum hole size in
* numbering is consequently the value of cacheSize.
*
* <b>HINT:</b> Since Derby supports the JDBC 3.0 {@code getGeneratedKeys} method,
* it is recommended to use IDENTITY columns directly in the tables and then utilizing
* a {@link org.springframework.jdbc.support.KeyHolder} when calling the with the
* <b>HINT:</b> Since Derby supports the JDBC {@code getGeneratedKeys} method,
* it is recommended to use IDENTITY columns directly in the tables and then utilize
* a {@link org.springframework.jdbc.support.KeyHolder} when calling the
* {@code update(PreparedStatementCreator psc, KeyHolder generatedKeyHolder)}
* method of the {@link org.springframework.jdbc.core.JdbcTemplate}.
*

View File

@ -39,10 +39,10 @@ import javax.sql.DataSource;
* is rolled back, the unused values will never be served. The maximum hole size in
* numbering is consequently the value of cacheSize.
*
* <b>HINT:</b> Since Microsoft SQL Server supports the JDBC 3.0 {@code getGeneratedKeys}
* method, it is recommended to use IDENTITY columns directly in the tables and then using a
* {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or utilizing
* a {@link org.springframework.jdbc.support.KeyHolder} when calling the with the
* <b>HINT:</b> Since Microsoft SQL Server supports the JDBC {@code getGeneratedKeys}
* method, it is recommended to use IDENTITY columns directly in the tables and then
* use a {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or a
* {@link org.springframework.jdbc.support.KeyHolder} when calling the
* {@code update(PreparedStatementCreator psc, KeyHolder generatedKeyHolder)}
* method of the {@link org.springframework.jdbc.core.JdbcTemplate}.
*

View File

@ -39,10 +39,10 @@ import javax.sql.DataSource;
* is rolled back, the unused values will never be served. The maximum hole size in
* numbering is consequently the value of cacheSize.
*
* <b>HINT:</b> Since Sybase Anywhere supports the JDBC 3.0 {@code getGeneratedKeys}
* <b>HINT:</b> Since Sybase Anywhere supports the JDBC {@code getGeneratedKeys}
* method, it is recommended to use IDENTITY columns directly in the tables and then
* using a {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or utilizing
* a {@link org.springframework.jdbc.support.KeyHolder} when calling the with the
* use a {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or use a
* {@link org.springframework.jdbc.support.KeyHolder} when calling the
* {@code update(PreparedStatementCreator psc, KeyHolder generatedKeyHolder)}
* method of the {@link org.springframework.jdbc.core.JdbcTemplate}.
*

View File

@ -39,10 +39,10 @@ import javax.sql.DataSource;
* is rolled back, the unused values will never be served. The maximum hole size in
* numbering is consequently the value of cacheSize.
*
* <b>HINT:</b> Since Sybase Adaptive Server supports the JDBC 3.0 {@code getGeneratedKeys}
* <b>HINT:</b> Since Sybase Adaptive Server supports the JDBC {@code getGeneratedKeys}
* method, it is recommended to use IDENTITY columns directly in the tables and then
* using a {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or utilizing
* a {@link org.springframework.jdbc.support.KeyHolder} when calling the with the
* use a {@link org.springframework.jdbc.core.simple.SimpleJdbcInsert} or use a
* {@link org.springframework.jdbc.support.KeyHolder} when calling the
* {@code update(PreparedStatementCreator psc, KeyHolder generatedKeyHolder)}
* method of the {@link org.springframework.jdbc.core.JdbcTemplate}.
*

View File

@ -33,8 +33,8 @@ import org.springframework.lang.Nullable;
* <p>The LOB creation part is where {@link LobHandler} implementations usually
* differ. Possible strategies include usage of
* {@code PreparedStatement.setBinaryStream/setCharacterStream} but also
* {@code PreparedStatement.setBlob/setClob} with either a stream argument
* (requires JDBC 4.0) or {@code java.sql.Blob/Clob} wrapper objects.
* {@code PreparedStatement.setBlob/setClob} with either a stream argument or
* {@code java.sql.Blob/Clob} wrapper objects.
*
* <p>A LobCreator represents a session for creating BLOBs: It is <i>not</i>
* thread-safe and needs to be instantiated for each statement execution or for

View File

@ -34,8 +34,8 @@ import org.springframework.lang.Nullable;
import org.springframework.util.FileCopyUtils;
/**
* {@link LobCreator} implementation based on temporary LOBs,
* using JDBC 4.0's {@link java.sql.Connection#createBlob()} /
* {@link LobCreator} implementation based on temporary LOBs, using JDBC's
* {@link java.sql.Connection#createBlob()} /
* {@link java.sql.Connection#createClob()} mechanism.
*
* <p>Used by DefaultLobHandler's {@link DefaultLobHandler#setCreateTemporaryLob} mode.

View File

@ -87,7 +87,7 @@ import org.springframework.util.Assert;
* transaction. The DataSource that Hibernate uses needs to be JTA-enabled in
* such a scenario (see container setup).
*
* <p>This transaction manager supports nested transactions via JDBC 3.0 Savepoints.
* <p>This transaction manager supports nested transactions via JDBC Savepoints.
* The {@link #setNestedTransactionAllowed} "nestedTransactionAllowed"} flag defaults
* to "false", though, as nested transactions will just apply to the JDBC Connection,
* not to the Hibernate Session and its cached entity objects and related context.

View File

@ -91,7 +91,7 @@ import org.springframework.util.CollectionUtils;
* used as the connection factory of the EntityManagerFactory, so you usually
* don't need to explicitly specify the "dataSource" property.
*
* <p>This transaction manager supports nested transactions via JDBC 3.0 Savepoints.
* <p>This transaction manager supports nested transactions via JDBC Savepoints.
* The {@link #setNestedTransactionAllowed "nestedTransactionAllowed"} flag defaults
* to {@code false} though, since nested transactions will just apply to the JDBC
* Connection, not to the JPA EntityManager and its cached entity objects and related

View File

@ -25,7 +25,7 @@ package org.springframework.transaction;
* Just use this programmatic savepoint handling for advanced needs;
* else, a subtransaction with PROPAGATION_NESTED is preferable.
*
* <p>This interface is inspired by JDBC 3.0's Savepoint mechanism
* <p>This interface is inspired by JDBC's Savepoint mechanism
* but is independent of any specific persistence technology.
*
* @author Juergen Hoeller

View File

@ -125,7 +125,7 @@ public interface TransactionDefinition {
* <p><b>NOTE:</b> Actual creation of a nested transaction will only work on
* specific transaction managers. Out of the box, this only applies to the JDBC
* {@link org.springframework.jdbc.datasource.DataSourceTransactionManager}
* when working on a JDBC 3.0 driver. Some JTA providers might support
* when working on a JDBC 3.0+ driver. Some JTA providers might support
* nested transactions as well.
* @see org.springframework.jdbc.datasource.DataSourceTransactionManager
*/

View File

@ -469,7 +469,7 @@ public abstract class AbstractPlatformTransactionManager
if (useSavepointForNestedTransaction()) {
// Create savepoint within existing Spring-managed transaction,
// through the SavepointManager API implemented by TransactionStatus.
// Usually uses JDBC 3.0 savepoints. Never activates Spring synchronization.
// Usually uses JDBC savepoints. Never activates Spring synchronization.
DefaultTransactionStatus status = newTransactionStatus(
definition, transaction, false, false, true, debugEnabled, null);
this.transactionExecutionListeners.forEach(listener -> listener.beforeBegin(status));