From 13a5cda68d5cbfe39272fea34a1dcf28a50fe0b2 Mon Sep 17 00:00:00 2001 From: Michael McMahon <53276266+Michael-A-McMahon@users.noreply.github.com> Date: Mon, 20 Dec 2021 18:09:32 -0800 Subject: [PATCH] Update README.md Update for the 0.4.0 release --- README.md | 122 ++++++++++++++++++++++++++++++------------------------ 1 file changed, 67 insertions(+), 55 deletions(-) diff --git a/README.md b/README.md index b0d3275..f886a06 100644 --- a/README.md +++ b/README.md @@ -8,9 +8,9 @@ Oracle R2DBC implements the R2DBC Service Provider Interface (SPI) as specified ### Learn More About R2DBC: [R2DBC Project Home Page](https://r2dbc.io) -[R2DBC Javadocs v0.9.0.M2](https://r2dbc.io/spec/0.9.0.M2/api/) +[R2DBC Javadocs v0.9.0.RELEASE](https://r2dbc.io/spec/0.9.0.RELEASE/api/) -[R2DBC Specification v0.9.0.M2](https://r2dbc.io/spec/0.9.0.M2/spec/html/) +[R2DBC Specification v0.9.0.RELEASE](https://r2dbc.io/spec/0.9.0.RELEASE/spec/html/) ### Learn More About Reactive Streams: [Reactive Streams Project Home Page](http://www.reactive-streams.org) @@ -19,18 +19,22 @@ Oracle R2DBC implements the R2DBC Service Provider Interface (SPI) as specified [Reactive Streams Specification v1.0.3](https://github.com/reactive-streams/reactive-streams-jvm/blob/v1.0.3/README.md) # About This Version -The 0.3.0 release Oracle R2DBC implements version 0.9.0.M2 of the R2DBC SPI. -The 0.9.0.M2 SPI update introduces support for consuming a `Result` as a - stream of `Segment` objects, configuring statement execution timeouts, and - managing pooled `Connection`s with the `LifeCycle` interface. - -The 0.3.0 release updates the Oracle JDBC dependency to 21.3. The 21.3 release - introduces several improvements for the Reactive Extensions: - - Substantial reduction in object allocation costs. - - Row mapping functions will no longer contend with other threads for - access to the JDBC connection. - - Blocking database calls are no longer required for PreparedStatements - returning values generated by DML. +The 0.4.0 release Oracle R2DBC implements version 0.9.0.RELEASE of the R2DBC SPI. + +Bug fixes included in this release: +- Resolved a stack overflow that occcured when reading JSON columns +- Using asynchronous lock acquisition to avoid contention for JDBC's lock + +Functionality added in this release: +- Support for SERIALIZABLE transaction isolation +- Support for transaction savepoints +- Support for R2dbcException.getSql() + +API changes in this release: +- Addition of oracle.r2dbc.OracleR2dbcOptions, a class that declares Oracle R2DBC's extended Options +- Addition of oracle.r2dbc.OracleR2dbcOptions.EXECUTOR, an Option for configuring a non-default Executor +- Renamed the "oracleNetDescriptor" Option to "oracle.r2dbc.descriptor" +- Statement.add() results in an IllegalStateException if bind values are not set afterwards ### Spring Integration Use the 0.1.0 version of Oracle R2DBC if you are programming with Spring. @@ -60,12 +64,12 @@ Artifacts can also be found on Maven Central. com.oracle.database.r2dbc oracle-r2dbc - 0.3.0 + 0.4.0 ``` Oracle R2DBC is compatible with JDK 11 (or newer), and has the following runtime dependencies: -- R2DBC SPI 0.9.0.M2 +- R2DBC SPI 0.9.0.RELEASE - Reactive Streams 1.0.3 - Project Reactor 3.3.0.RELEASE - Oracle JDBC 21.3.0.0 for JDK 11 (ojdbc11.jar) @@ -142,9 +146,9 @@ This document specifies the behavior of the R2DBC SPI implemented for the Oracle Database. This SPI implementation is referred to as the "Oracle R2DBC Driver" or "Oracle R2DBC" throughout the remainder of this document. -The Oracle R2DBC Driver implements behavior specified by the R2DBC 0.9.0.M2 -[Specification](https://r2dbc.io/spec/0.9.0.M2/spec/html/) -and [Javadoc](https://r2dbc.io/spec/0.8.3.RELEASE/api/) +The Oracle R2DBC Driver implements behavior specified by the R2DBC 0.9.0.RELEASE +[Specification](https://r2dbc.io/spec/0.9.0.RELEASE/spec/html/) +and [Javadoc](https://r2dbc.io/spec/0.9.0.RELEASE/api/) Publisher objects created by Oracle R2DBC implement behavior specified by the Reactive Streams 1.0.3 [Specification](https://github.com/reactive-streams/reactive-streams-jvm/blob/v1.0.3/README.md) @@ -160,13 +164,13 @@ implements a ConnectionFactoryProvider located by an R2DBC URL identifing "oracle" as a driver, or by a DRIVER ConnectionFactoryOption with the value of "oracle". - The following well-known ConnectionFactory Options are supported: -DRIVER, USER, PASSWORD, HOST, PORT, DATABASE, SSL, -CONNECT_TIMEOUT, STATEMENT_TIMEOUT. -- The DATABASE ConnectionFactoryOption is interpreted as the +`DRIVER`, `USER`, `PASSWORD`, `HOST`, `PORT`, `DATABASE`, `SSL`, +`CONNECT_TIMEOUT`, `STATEMENT_TIMEOUT`. +- The `DATABASE` `ConnectionFactoryOption` is interpreted as the [service name](https://docs.oracle.com/en/database/oracle/oracle-database/21/netag/identifying-and-accessing-database.html#GUID-153861C1-16AD-41EC-A179-074146B722E6) of an Oracle Database instance. System Identifiers (SID) are not recognized. - A subset of Oracle JDBC's connection properties are supported as extended -Options. For Options having any of the following names, a CharSequence value may be specified: +options. Extended options that configure Oracle JDBC connection properties are declared in `oracle.r2dbc.OracleR2dbcOptions`. These options all have the same name as their corresponding Oracle JDBC connection property, and will accept a `CharSequence` value: - [oracle.net.tns_admin](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_TNS_ADMIN) - [oracle.net.wallet_location](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_WALLET_LOCATION) - [oracle.net.wallet_password](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_WALLET_PASSWORD) @@ -189,27 +193,35 @@ Options. For Options having any of the following names, a CharSequence value may - [oracle.jdbc.implicitStatementCacheSize](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_IMPLICIT_STATEMENT_CACHE_SIZE) - [oracle.jdbc.defaultLobPrefetchSize](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_DEFAULT_LOB_PREFETCH_SIZE) - [oracle.net.disableOob](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_THIN_NET_DISABLE_OUT_OF_BAND_BREAK) - - Out of band (OOB) breaks effect statement timeouts. Set this to "true" - if statement timeouts are not working correctly. + - Out of band (OOB) breaks effect statement timeouts. Set this to "true" if statement timeouts are not working correctly. - [oracle.jdbc.enableQueryResultCache](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html#CONNECTION_PROPERTY_ENABLE_QUERY_RESULT_CACHE) - Cached query results can cause phantom reads even if the serializable transaction isolation level is set. Set this to "false" if using the serializable isolation level. -- Oracle Net Descriptors of the form ```(DESCRIPTION=...)``` may be specified as an io.r2dbc.spi.Option having the name `oracleNetDescriptor`. - - If `oracleNetDescriptor` is specified, then it is invalid to specify any other options that might conflict with information in the descriptor, such as: `HOST`, `PORT`, `DATABASE`, and `SSL`. - - The `oracleNetDescriptor` option may appear in the query section of an R2DBC URL: `r2dbc:oracle://?oracleNetDescriptor=(DESCRIPTION=...)` - - The `oracleNetDescriptor` option may be provided programatically: `ConnectionFactoryOptions.builder().option(Option.valueOf("oracleNetDescriptor"), "(DESCRIPTION=...)")` - - The `oracleNetDescriptor` option may be set as the alias of a descriptor in a tnsnames.ora file. The directory of tnsnames.ora may be set using an io.r2dbc.spi.Option having the name `TNS_ADMIN`: `r2dbc:oracle://?oracleNetDescriptor=myAlias&TNS_ADMIN=/path/to/tnsnames/` - +- Oracle Net Descriptors of the form ```(DESCRIPTION=...)``` may be specified using `oracle.r2dbc.OracleR2dbcOptions.DESCRIPTOR`. + - If a descriptor is specified, then it is invalid to specify any other options that might conflict with information in the descriptor, such as: `HOST`, `PORT`, `DATABASE`, and `SSL`. + - The `DESCRIPTOR` option has the name `oracle.r2dbc.descriptor`, and this may appear in the query section of an R2DBC URL: `r2dbc:oracle://?oracle.r2dbc.descriptor=(DESCRIPTION=...)` + - The `DESCRIPTOR` option may be provided programmatically: + ```java + ConnectionFactoryOptions.builder().option(OracleR2dbcOptions.DESCRIPTOR, "(DESCRIPTION=...)") + ``` + - The `DESCRIPTOR` option may be set to an aliased entry of a tnsnames.ora file. The directory of tnsnames.ora may be set using an option with the name `TNS_ADMIN`: `r2dbc:oracle://?oracle.r2dbc.descriptor=myAlias&TNS_ADMIN=/path/to/tnsnames/` +- A `java.util.concurrent.Executor` to use for executing asynchronous callbacks may specified using `oracle.r2dbc.OracleR2dbcOptions.EXECUTOR`. + - The `EXECUTOR` option can only be set programmatically, it can not be set in the query section of an R2DBC URL: + ```java + Executor myExecutor = getMyExecutor(); + ConnectionFactoryOptions options = ConnectionFactoryOptions.builder() + .option(ConnectionFactoryOptions.DRIVER, "oracle") + .option(OracleR2dbcOptions.EXECUTOR, myExecutor) + ... + .build(); + ``` ### Thread Safety and Parallel Execution -- Oracle R2DBC's ConnectionFactory and ConnectionFactoryProvider are thread safe. +- Oracle R2DBC's `ConnectionFactory` and `ConnectionFactoryProvider` are thread safe. - All other SPI implementations are not thread safe. -- Executing parallel database calls is not supported over a single Connection. -If a thread attempts to initiate a parallel call, that thread is blocked until -the connection is no longer executing any other call. This is a -limitation of the Oracle Database, which does not support parallel calls -within a single session. +- Executing parallel database calls is not supported over a single `Connection`. +If a thread attempts to initiate a parallel call, that call will be enqueued. The enqueued call will not be executed until the connection is no longer executing any other call. This is a limitation of the Oracle Database, which does not support parallel calls within a single session. ### Reactive Streams - The Oracle R2DBC javadoc of every method that returns a Publisher specifies the @@ -228,7 +240,7 @@ or Oracle JDBC Driver error message](https://docs.oracle.com/en/database/oracle/ - READ COMMITTED is the default transaction isolation level - SERIALIZABLE is the only isolation level, besides READ COMMITED, that Oracle Database supports. -- Transaction savepoints are not supported in this release. + - To avoid phantom reads, configure `oracle.r2dbc.OracleR2dbcOptions.ENABLE_QUERY_RESULT_CACHE` as `false` when using SERIALIZABLE isolation. - Oracle Database does not support a lock wait timeout that is configurable within the scope of a transaction or session. SPI methods that configure a lock wait timeout throw ```UnsupportedOperationException``` @@ -287,35 +299,35 @@ of each row affected by an INSERT or UPDATE. ```Result``` for each returned cursor. ### Type Mappings -- javax.json.JsonObject and oracle.sql.json.OracleJsonObject are supported as -Java type mappings for JSON column values. -- java.time.Duration is supported as a Java type mapping for INTERVAL DAY TO SECOND +- `javax.json.JsonObject` and `oracle.sql.json.OracleJsonObject` are supported as +Java type mappings for `JSON` column values. +- `java.time.Duration` is supported as a Java type mapping for `INTERVAL DAY TO SECOND` column values. -- java.time.Period is supported as a Java type mapping for INTERVAL YEAR TO MONTH +- `java.time.Period` is supported as a Java type mapping for `INTERVAL YEAR TO MONTH` column values. -- java.time.LocalDateTime is supported as a Java type mapping for DATE column values. -The Oracle Database type named "DATE" stores the same information as a LocalDateTime: -year, month, day, hour, minute, and second. +- `java.time.LocalDateTime` is supported as a Java type mapping for `DATE` column values. +The Oracle Database type named "DATE" stores the same information as a `LocalDateTime`: +year, month, day, hour, minute, and second. ### BLOB, CLOB, and NCLOB When a SQL query returns a LOB value, a portion of that value is prefetched from the database and the remaining portion must be fetched with additional database calls. The number of prefetched -bytes is configured by an ```Option``` named [oracle.jdbc.defaultLobPrefetchSize](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_DEFAULT_LOB_PREFETCH_SIZE) -. The default value of this ```Option``` is 1 GB. +bytes is configured by an `Option` named [oracle.jdbc.defaultLobPrefetchSize](https://docs.oracle.com/en/database/oracle/oracle-database/21/jajdb/oracle/jdbc/OracleConnection.html?is-external=true#CONNECTION_PROPERTY_DEFAULT_LOB_PREFETCH_SIZE) +. The default value of this `Option` is 1 GB. -The ```Row.get(...)``` method allows LOB values to be mapped into materialized -types like ```ByteBuffer``` and ```String```. If the prefetch size is large -enough to have fetched the entire LOB value, then ```Row.get(...)``` can -return a ```ByteBuffer/String``` without any additional database calls. +The `Row.get(...)` method allows LOB values to be mapped into materialized +types like `ByteBuffer` and `String`. If the prefetch size is large +enough to have fetched the entire LOB value, then `Row.get(...)` can +return a `ByteBuffer/String` without any additional database calls. Otherwise, if the LOB value is larger than the prefetch size, then -```Row.get(...)``` must execute a **blocking database call** to fetch the +`Row.get(...)` must execute a **blocking database call** to fetch the remainder of that value. For systems in which LOB values are too large to be prefetched, a smaller -prefetch size can be configured, and LOB values may be mapped into ```Blob``` -or ```Clob``` objects rather than ```ByteBuffer``` or ```String```. ```Blob``` -and ```Clob``` objects allow the LOB value to be streamed using non-blocking +prefetch size can be configured, and LOB values may be mapped into `Blob` +or `Clob` objects rather than `ByteBuffer` or `String`. `Blob` +and `Clob` objects allow the LOB value to be streamed using non-blocking database calls. # Secure Programming Guidelines