diff --git a/CHANGELOG.md b/CHANGELOG.md
index c35a1760e5..287ca0c2a3 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -3,6 +3,25 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](http://keepachangelog.com/)
+## [6.3.2] Preview Release
+### Added
+- Added new connection property: sslProtocol [#422](https://github.com/Microsoft/mssql-jdbc/pull/422)
+- Added "slow" tag to long running tests [#461](https://github.com/Microsoft/mssql-jdbc/pull/461)
+
+### Fixed Issues
+- Fixed some error messages [#452](https://github.com/Microsoft/mssql-jdbc/pull/452) & [#459](https://github.com/Microsoft/mssql-jdbc/pull/459)
+- Fixed statement leaks [#455](https://github.com/Microsoft/mssql-jdbc/pull/455)
+- Fixed an issue regarding to loginTimeout with TLS [#456](https://github.com/Microsoft/mssql-jdbc/pull/456)
+- Fixed sql_variant issue with String type [#442](https://github.com/Microsoft/mssql-jdbc/pull/442)
+- Fixed issue with throwing error message for unsupported datatype [#450](https://github.com/Microsoft/mssql-jdbc/pull/450)
+- Fixed issue that initial batchException was not thrown [#458](https://github.com/Microsoft/mssql-jdbc/pull/458)
+
+### Changed
+- Changed sendStringParameterAsUnicode to impact set/update null [#445](https://github.com/Microsoft/mssql-jdbc/pull/445)
+- Removed connection property: fipsProvider [#460](https://github.com/Microsoft/mssql-jdbc/pull/460)
+- Replaced for and while loops with foeach loops [#421](https://github.com/Microsoft/mssql-jdbc/pull/421)
+- Replaced explicit types with the diamond operator [#468](https://github.com/Microsoft/mssql-jdbc/pull/468) & [#420](https://github.com/Microsoft/mssql-jdbc/pull/420)
+
## [6.3.1] Preview Release
### Added
- Added support for datetime/smallDatetime in TVP [#435](https://github.com/Microsoft/mssql-jdbc/pull/435)
diff --git a/README.md b/README.md
index 54810ab678..5fd1154ac9 100644
--- a/README.md
+++ b/README.md
@@ -90,7 +90,7 @@ To get the latest preview version of the driver, add the following to your POM f
com.microsoft.sqlservermssql-jdbc
- 6.3.1.jre8-preview-v2
+ 6.3.2.jre8-preview
```
@@ -120,7 +120,7 @@ Projects that require either of the two features need to explicitly declare the
com.microsoft.sqlservermssql-jdbc
- 6.3.1.jre8-preview-v2
+ 6.3.2.jre8-previewcompile
diff --git a/pom.xml b/pom.xml
index f5498d940c..9324600566 100644
--- a/pom.xml
+++ b/pom.xml
@@ -4,7 +4,7 @@
com.microsoft.sqlservermssql-jdbc
- 6.3.2-SNAPSHOT
+ 6.3.2jar
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/AE.java b/src/main/java/com/microsoft/sqlserver/jdbc/AE.java
index c6345d25b5..1b5b2543fa 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/AE.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/AE.java
@@ -88,7 +88,7 @@ byte[] getCekMdVersion() {
cekId = 0;
cekVersion = 0;
cekMdVersion = null;
- columnEncryptionKeyValues = new ArrayList();
+ columnEncryptionKeyValues = new ArrayList<>();
}
int getSize() {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Column.java b/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
index a9c09e3305..d6d8017bfc 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
@@ -337,7 +337,7 @@ else if (jdbcType.isBinary()) {
// to the server as Unicode rather than MBCS. This is accomplished here by re-tagging
// the value with the appropriate corresponding Unicode type.
if ((null != cryptoMetadata) && (con.sendStringParametersAsUnicode())
- && (JavaType.STRING == javaType || JavaType.READER == javaType || JavaType.CLOB == javaType)) {
+ && (JavaType.STRING == javaType || JavaType.READER == javaType || JavaType.CLOB == javaType || JavaType.OBJECT == javaType)) {
jdbcType = getSSPAUJDBCType(jdbcType);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java b/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
index 562b958c8d..c42dae2869 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
@@ -922,7 +922,8 @@ static final Object convertTemporalToObject(JDBCType jdbcType,
}
// Convert the calendar value (in local time) to the desired Java object type.
switch (jdbcType.category) {
- case BINARY: {
+ case BINARY:
+ case SQL_VARIANT: {
switch (ssType) {
case DATE: {
// Per JDBC spec, the time part of java.sql.Date values is initialized to midnight
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java b/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
index 914e382a29..3f6ebdbea5 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
@@ -382,7 +382,7 @@ private GetterConversion(SSType.Category from,
this.to = to;
}
- private static final EnumMap> conversionMap = new EnumMap>(
+ private static final EnumMap> conversionMap = new EnumMap<>(
SSType.Category.class);
static {
@@ -776,7 +776,7 @@ private SetterConversionAE(JavaType from,
this.to = to;
}
- private static final EnumMap> setterConversionAEMap = new EnumMap>(JavaType.class);
+ private static final EnumMap> setterConversionAEMap = new EnumMap<>(JavaType.class);
static {
for (JavaType javaType : JavaType.values())
@@ -1086,7 +1086,7 @@ private SetterConversion(JDBCType.Category from,
this.to = to;
}
- private static final EnumMap> conversionMap = new EnumMap>(
+ private static final EnumMap> conversionMap = new EnumMap<>(
JDBCType.Category.class);
static {
@@ -1305,7 +1305,7 @@ private UpdaterConversion(JDBCType.Category from,
this.to = to;
}
- private static final EnumMap> conversionMap = new EnumMap>(
+ private static final EnumMap> conversionMap = new EnumMap<>(
JDBCType.Category.class);
static {
@@ -1616,7 +1616,7 @@ private NormalizationAE(JDBCType from,
this.to = to;
}
- private static final EnumMap> normalizationMapAE = new EnumMap>(JDBCType.class);
+ private static final EnumMap> normalizationMapAE = new EnumMap<>(JDBCType.class);
static {
for (JDBCType jdbcType : JDBCType.values())
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java b/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
index f3146d926e..8bebf1f0e9 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
@@ -13,7 +13,7 @@
final class FailoverMapSingleton {
private static int INITIALHASHMAPSIZE = 5;
- private static HashMap failoverMap = new HashMap(INITIALHASHMAPSIZE);
+ private static HashMap failoverMap = new HashMap<>(INITIALHASHMAPSIZE);
private FailoverMapSingleton() {
/* hide the constructor to stop the instantiation of this class. */}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java b/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
index e70f04bbff..a9af8068bf 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
@@ -1579,7 +1579,7 @@ void enableSSL(String host,
boolean isFips = false;
String trustStoreType = null;
- String fipsProvider = null;
+ String sslProtocol = null;
// If anything in here fails, terminate the connection and throw an exception
try {
@@ -1597,11 +1597,11 @@ void enableSSL(String host,
trustStoreType = SQLServerDriverStringProperty.TRUST_STORE_TYPE.getDefaultValue();
}
- fipsProvider = con.activeConnectionProperties.getProperty(SQLServerDriverStringProperty.FIPS_PROVIDER.toString());
isFips = Boolean.valueOf(con.activeConnectionProperties.getProperty(SQLServerDriverBooleanProperty.FIPS.toString()));
+ sslProtocol = con.activeConnectionProperties.getProperty(SQLServerDriverStringProperty.SSL_PROTOCOL.toString());
if (isFips) {
- validateFips(fipsProvider, trustStoreType, trustStoreFileName);
+ validateFips(trustStoreType, trustStoreFileName);
}
assert TDS.ENCRYPT_OFF == con.getRequestedEncryptionLevel() || // Login only SSL
@@ -1647,12 +1647,8 @@ void enableSSL(String host,
if (logger.isLoggable(Level.FINEST))
logger.finest(toString() + " Finding key store interface");
- if (isFips) {
- ks = KeyStore.getInstance(trustStoreType, fipsProvider);
- }
- else {
- ks = KeyStore.getInstance(trustStoreType);
- }
+
+ ks = KeyStore.getInstance(trustStoreType);
ksProvider = ks.getProvider();
// Next, load up the trust store file from the specified location.
@@ -1728,7 +1724,7 @@ void enableSSL(String host,
if (logger.isLoggable(Level.FINEST))
logger.finest(toString() + " Getting TLS or better SSL context");
- sslContext = SSLContext.getInstance("TLS");
+ sslContext = SSLContext.getInstance(sslProtocol);
sslContextProvider = sslContext.getProvider();
if (logger.isLoggable(Level.FINEST))
@@ -1745,8 +1741,7 @@ void enableSSL(String host,
logger.finest(toString() + " Creating SSL socket");
sslSocket = (SSLSocket) sslContext.getSocketFactory().createSocket(proxySocket, host, port, false); // don't close proxy when SSL socket
- // is closed
-
+ // is closed
// At long last, start the SSL handshake ...
if (logger.isLoggable(Level.FINER))
logger.finer(toString() + " Starting SSL handshake");
@@ -1827,57 +1822,40 @@ void enableSSL(String host,
* Valid FIPS settings:
*
Encrypt should be true
*
trustServerCertificate should be false
- *
if certificate is not installed FIPSProvider & TrustStoreType should be present.
+ *
if certificate is not installed TrustStoreType should be present.
*
- * @param fipsProvider
- * FIPS Provider
* @param trustStoreType
* @param trustStoreFileName
* @throws SQLServerException
* @since 6.1.4
*/
- private void validateFips(final String fipsProvider,
- final String trustStoreType,
+ private void validateFips(final String trustStoreType,
final String trustStoreFileName) throws SQLServerException {
boolean isValid = false;
boolean isEncryptOn;
boolean isValidTrustStoreType;
boolean isValidTrustStore;
boolean isTrustServerCertificate;
- boolean isValidFipsProvider;
String strError = SQLServerException.getErrString("R_invalidFipsConfig");
isEncryptOn = (TDS.ENCRYPT_ON == con.getRequestedEncryptionLevel());
- // Here different FIPS provider supports different KeyStore type along with different JVM Implementation.
- isValidFipsProvider = !StringUtils.isEmpty(fipsProvider);
isValidTrustStoreType = !StringUtils.isEmpty(trustStoreType);
isValidTrustStore = !StringUtils.isEmpty(trustStoreFileName);
isTrustServerCertificate = con.trustServerCertificate();
- if (isEncryptOn && !isTrustServerCertificate) {
- if (logger.isLoggable(Level.FINER))
- logger.finer(toString() + " Found parameters are encrypt is true & trustServerCertificate false");
-
+ if (isEncryptOn && !isTrustServerCertificate) {
isValid = true;
-
if (isValidTrustStore) {
- // In case of valid trust store we need to check fipsProvider and TrustStoreType.
- if (!isValidFipsProvider || !isValidTrustStoreType) {
- isValid = false;
- strError = SQLServerException.getErrString("R_invalidFipsProviderConfig");
-
+ // In case of valid trust store we need to check TrustStoreType.
+ if (!isValidTrustStoreType) {
+ isValid = false;
if (logger.isLoggable(Level.FINER))
- logger.finer(toString() + " FIPS provider & TrustStoreType should pass with TrustStore.");
+ logger.finer(toString() + "TrustStoreType is required alongside with TrustStore.");
}
- if (logger.isLoggable(Level.FINER))
- logger.finer(toString() + " Found FIPS parameters seems to be valid.");
}
}
- else {
- strError = SQLServerException.getErrString("R_invalidFipsEncryptConfig");
- }
if (!isValid) {
throw new SQLServerException(strError, null, 0, null);
@@ -2338,8 +2316,8 @@ else if (!useTnir) {
findSocketUsingJavaNIO(inetAddrs, portNumber, timeoutInMilliSeconds);
}
else {
- LinkedList inet4Addrs = new LinkedList();
- LinkedList inet6Addrs = new LinkedList();
+ LinkedList inet4Addrs = new LinkedList<>();
+ LinkedList inet6Addrs = new LinkedList<>();
for (InetAddress inetAddr : inetAddrs) {
if (inetAddr instanceof Inet4Address) {
@@ -2467,13 +2445,13 @@ private void findSocketUsingJavaNIO(InetAddress[] inetAddrs,
assert inetAddrs.length != 0 : "Number of inetAddresses should not be zero in this function";
Selector selector = null;
- LinkedList socketChannels = new LinkedList();
+ LinkedList socketChannels = new LinkedList<>();
SocketChannel selectedChannel = null;
try {
selector = Selector.open();
- for (int i = 0; i < inetAddrs.length; i++) {
+ for (InetAddress inetAddr : inetAddrs) {
SocketChannel sChannel = SocketChannel.open();
socketChannels.add(sChannel);
@@ -2484,10 +2462,10 @@ private void findSocketUsingJavaNIO(InetAddress[] inetAddrs,
int ops = SelectionKey.OP_CONNECT;
SelectionKey key = sChannel.register(selector, ops);
- sChannel.connect(new InetSocketAddress(inetAddrs[i], portNumber));
+ sChannel.connect(new InetSocketAddress(inetAddr, portNumber));
if (logger.isLoggable(Level.FINER))
- logger.finer(this.toString() + " initiated connection to address: " + inetAddrs[i] + ", portNumber: " + portNumber);
+ logger.finer(this.toString() + " initiated connection to address: " + inetAddr + ", portNumber: " + portNumber);
}
long timerNow = System.currentTimeMillis();
@@ -2646,8 +2624,8 @@ private void findSocketUsingThreading(LinkedList inetAddrs,
assert inetAddrs.isEmpty() == false : "Number of inetAddresses should not be zero in this function";
- LinkedList sockets = new LinkedList();
- LinkedList socketConnectors = new LinkedList();
+ LinkedList sockets = new LinkedList<>();
+ LinkedList socketConnectors = new LinkedList<>();
try {
@@ -5037,13 +5015,11 @@ void writeTVPColumnMetaData(TVP value) throws SQLServerException {
writeShort((short) value.getTVPColumnCount());
Map columnMetadata = value.getColumnMetadata();
- Iterator> columnsIterator = columnMetadata.entrySet().iterator();
/*
* TypeColumnMetaData = UserType Flags TYPE_INFO ColName ;
*/
- while (columnsIterator.hasNext()) {
- Map.Entry pair = columnsIterator.next();
+ for (Entry pair : columnMetadata.entrySet()) {
JDBCType jdbcType = JDBCType.of(pair.getValue().javaSqlType);
boolean useServerDefault = pair.getValue().useServerDefault;
// ULONG ; UserType of column
@@ -5118,13 +5094,12 @@ void writeTVPColumnMetaData(TVP value) throws SQLServerException {
writeByte(TDSType.NVARCHAR.byteValue());
isShortValue = (2L * pair.getValue().precision) <= DataTypes.SHORT_VARTYPE_MAX_BYTES;
// Use PLP encoding on Yukon and later with long values
- if (!isShortValue) // PLP
+ if (!isShortValue) // PLP
{
// Handle Yukon v*max type header here.
writeShort((short) 0xFFFF);
con.getDatabaseCollation().writeCollation(this);
- }
- else // non PLP
+ } else // non PLP
{
writeShort((short) DataTypes.SHORT_VARTYPE_MAX_BYTES);
con.getDatabaseCollation().writeCollation(this);
@@ -5138,16 +5113,16 @@ void writeTVPColumnMetaData(TVP value) throws SQLServerException {
writeByte(TDSType.BIGVARBINARY.byteValue());
isShortValue = pair.getValue().precision <= DataTypes.SHORT_VARTYPE_MAX_BYTES;
// Use PLP encoding on Yukon and later with long values
- if (!isShortValue) // PLP
+ if (!isShortValue) // PLP
// Handle Yukon v*max type header here.
writeShort((short) 0xFFFF);
- else // non PLP
+ else // non PLP
writeShort((short) DataTypes.SHORT_VARTYPE_MAX_BYTES);
break;
case SQL_VARIANT:
writeByte(TDSType.SQL_VARIANT.byteValue());
writeInt(TDS.SQL_VARIANT_LENGTH);// write length of sql variant 8009
-
+
break;
default:
@@ -5168,7 +5143,7 @@ void writeTvpOrderUnique(TVP value) throws SQLServerException {
Map columnMetadata = value.getColumnMetadata();
Iterator> columnsIterator = columnMetadata.entrySet().iterator();
- LinkedList columnList = new LinkedList();
+ LinkedList columnList = new LinkedList<>();
while (columnsIterator.hasNext()) {
byte flags = 0;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/JaasConfiguration.java b/src/main/java/com/microsoft/sqlserver/jdbc/JaasConfiguration.java
index f080ae14e5..6443724fd4 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/JaasConfiguration.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/JaasConfiguration.java
@@ -23,9 +23,9 @@ public class JaasConfiguration extends Configuration {
private static AppConfigurationEntry[] generateDefaultConfiguration() {
if (Util.isIBM()) {
- Map confDetailsWithoutPassword = new HashMap();
+ Map confDetailsWithoutPassword = new HashMap<>();
confDetailsWithoutPassword.put("useDefaultCcache", "true");
- Map confDetailsWithPassword = new HashMap();
+ Map confDetailsWithPassword = new HashMap<>();
// We generated a two configurations fallback that is suitable for password and password-less authentication
// See https://www.ibm.com/support/knowledgecenter/SSYKE2_8.0.0/com.ibm.java.security.component.80.doc/security-component/jgssDocs/jaas_login_user.html
final String ibmLoginModule = "com.ibm.security.auth.module.Krb5LoginModule";
@@ -34,7 +34,7 @@ private static AppConfigurationEntry[] generateDefaultConfiguration() {
new AppConfigurationEntry(ibmLoginModule, AppConfigurationEntry.LoginModuleControlFlag.SUFFICIENT, confDetailsWithPassword)};
}
else {
- Map confDetails = new HashMap();
+ Map confDetails = new HashMap<>();
confDetails.put("useTicketCache", "true");
return new AppConfigurationEntry[] {new AppConfigurationEntry("com.sun.security.auth.module.Krb5LoginModule",
AppConfigurationEntry.LoginModuleControlFlag.REQUIRED, confDetails)};
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/KerbCallback.java b/src/main/java/com/microsoft/sqlserver/jdbc/KerbCallback.java
index 8cdc4cca96..6f861c4bbd 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/KerbCallback.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/KerbCallback.java
@@ -42,18 +42,15 @@ public String getUsernameRequested() {
@Override
public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
- for (int i = 0; i < callbacks.length; i++) {
- Callback callback = callbacks[i];
+ for (Callback callback : callbacks) {
if (callback instanceof NameCallback) {
usernameRequested = getAnyOf(callback, con.activeConnectionProperties, "user", SQLServerDriverStringProperty.USER.name());
((NameCallback) callback).setName(usernameRequested);
- }
- else if (callback instanceof PasswordCallback) {
+ } else if (callback instanceof PasswordCallback) {
String password = getAnyOf(callback, con.activeConnectionProperties, "password", SQLServerDriverStringProperty.PASSWORD.name());
- ((PasswordCallback) callbacks[i]).setPassword(password.toCharArray());
+ ((PasswordCallback) callback).setPassword(password.toCharArray());
- }
- else {
+ } else {
throw new UnsupportedCallbackException(callback, "Unrecognized Callback type: " + callback.getClass());
}
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java b/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
index afb71cd7fa..d08264c421 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
@@ -375,7 +375,9 @@ else if (value instanceof ISQLServerDataRecord) {
// If set to true, this connection property tells the driver to send textual parameters
// to the server as Unicode rather than MBCS. This is accomplished here by re-tagging
// the value with the appropriate corresponding Unicode type.
- if (con.sendStringParametersAsUnicode() && (JavaType.STRING == javaType || JavaType.READER == javaType || JavaType.CLOB == javaType)) {
+ // JavaType.OBJECT == javaType when calling setNull()
+ if (con.sendStringParametersAsUnicode()
+ && (JavaType.STRING == javaType || JavaType.READER == javaType || JavaType.CLOB == javaType || JavaType.OBJECT == javaType)) {
jdbcType = getSSPAUJDBCType(jdbcType);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLCollation.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLCollation.java
index 7a47b6fecd..d89a95e111 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLCollation.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLCollation.java
@@ -530,11 +530,11 @@ private Encoding encodingFromSortId() throws UnsupportedEncodingException {
static {
// Populate the windows locale and sort order indices
- localeIndex = new HashMap();
+ localeIndex = new HashMap<>();
for (WindowsLocale locale : EnumSet.allOf(WindowsLocale.class))
localeIndex.put(locale.langID, locale);
- sortOrderIndex = new HashMap();
+ sortOrderIndex = new HashMap<>();
for (SortOrder sortOrder : EnumSet.allOf(SortOrder.class))
sortOrderIndex.put(sortOrder.sortId, sortOrder);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
index 26b631b2d0..e7f5bccf71 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
@@ -11,6 +11,6 @@
final class SQLJdbcVersion {
static final int major = 6;
static final int minor = 3;
- static final int patch = 1;
+ static final int patch = 2;
static final int build = 0;
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerAeadAes256CbcHmac256Factory.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerAeadAes256CbcHmac256Factory.java
index 13c8dc3fb3..8f71ec6b61 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerAeadAes256CbcHmac256Factory.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerAeadAes256CbcHmac256Factory.java
@@ -21,7 +21,7 @@
class SQLServerAeadAes256CbcHmac256Factory extends SQLServerEncryptionAlgorithmFactory {
// In future we can have more
private byte algorithmVersion = 0x1;
- private ConcurrentHashMap encryptionAlgorithms = new ConcurrentHashMap();
+ private ConcurrentHashMap encryptionAlgorithms = new ConcurrentHashMap<>();
@Override
SQLServerEncryptionAlgorithm create(SQLServerSymmetricKey columnEncryptionKey,
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBlob.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBlob.java
index ef74f5c488..47927d6a68 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBlob.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBlob.java
@@ -40,7 +40,7 @@ public final class SQLServerBlob implements java.sql.Blob, java.io.Serializable
// Initial size of the array is based on an assumption that a Blob object is
// typically used either for input or output, and then only once. The array size
// grows automatically if multiple streams are used.
- ArrayList activeStreams = new ArrayList(1);
+ ArrayList activeStreams = new ArrayList<>(1);
static private final Logger logger = Logger.getLogger("com.microsoft.sqlserver.jdbc.internals.SQLServerBlob");
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCSVFileRecord.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCSVFileRecord.java
index f208f7656a..4ff063dab2 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCSVFileRecord.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCSVFileRecord.java
@@ -16,6 +16,7 @@
import java.io.UnsupportedEncodingException;
import java.math.BigDecimal;
import java.math.RoundingMode;
+import java.sql.Types;
import java.text.DecimalFormat;
import java.text.MessageFormat;
import java.time.OffsetDateTime;
@@ -158,7 +159,7 @@ else if (null == delimiter) {
catch (Exception e) {
throw new SQLServerException(null, e.getMessage(), null, 0, false);
}
- columnMetadata = new HashMap();
+ columnMetadata = new HashMap<>();
loggerExternal.exiting(loggerClassName, "SQLServerBulkCSVFileRecord");
}
@@ -215,7 +216,7 @@ else if (null == delimiter) {
catch (Exception e) {
throw new SQLServerException(null, e.getMessage(), null, 0, false);
}
- columnMetadata = new HashMap();
+ columnMetadata = new HashMap<>();
loggerExternal.exiting(loggerClassName, "SQLServerBulkCSVFileRecord");
}
@@ -525,9 +526,7 @@ public Object[] getRowData() throws SQLServerException {
// Cannot go directly from String[] to Object[] and expect it to act as an array.
Object[] dataRow = new Object[data.length];
- Iterator> it = columnMetadata.entrySet().iterator();
- while (it.hasNext()) {
- Entry pair = it.next();
+ for (Entry pair : columnMetadata.entrySet()) {
ColumnMetadata cm = pair.getValue();
// Reading a column not available in csv
@@ -556,7 +555,7 @@ public Object[] getRowData() throws SQLServerException {
* Both BCP and BULK INSERT considers double quotes as part of the data and throws error if any data (say "10") is to be
* inserted into an numeric column. Our implementation does the same.
*/
- case java.sql.Types.INTEGER: {
+ case Types.INTEGER: {
// Formatter to remove the decimal part as SQL Server floors the decimal in integer types
DecimalFormat decimalFormatter = new DecimalFormat("#");
String formatedfInput = decimalFormatter.format(Double.parseDouble(data[pair.getKey() - 1]));
@@ -564,8 +563,8 @@ public Object[] getRowData() throws SQLServerException {
break;
}
- case java.sql.Types.TINYINT:
- case java.sql.Types.SMALLINT: {
+ case Types.TINYINT:
+ case Types.SMALLINT: {
// Formatter to remove the decimal part as SQL Server floors the decimal in integer types
DecimalFormat decimalFormatter = new DecimalFormat("#");
String formatedfInput = decimalFormatter.format(Double.parseDouble(data[pair.getKey() - 1]));
@@ -573,52 +572,50 @@ public Object[] getRowData() throws SQLServerException {
break;
}
- case java.sql.Types.BIGINT: {
+ case Types.BIGINT: {
BigDecimal bd = new BigDecimal(data[pair.getKey() - 1].trim());
try {
dataRow[pair.getKey() - 1] = bd.setScale(0, BigDecimal.ROUND_DOWN).longValueExact();
- }
- catch (ArithmeticException ex) {
+ } catch (ArithmeticException ex) {
String value = "'" + data[pair.getKey() - 1] + "'";
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_errorConvertingValue"));
- throw new SQLServerException(form.format(new Object[] {value, JDBCType.of(cm.columnType)}), null, 0, ex);
+ throw new SQLServerException(form.format(new Object[]{value, JDBCType.of(cm.columnType)}), null, 0, ex);
}
break;
}
- case java.sql.Types.DECIMAL:
- case java.sql.Types.NUMERIC: {
+ case Types.DECIMAL:
+ case Types.NUMERIC: {
BigDecimal bd = new BigDecimal(data[pair.getKey() - 1].trim());
dataRow[pair.getKey() - 1] = bd.setScale(cm.scale, RoundingMode.HALF_UP);
break;
}
- case java.sql.Types.BIT: {
+ case Types.BIT: {
// "true" => 1, "false" => 0
// Any non-zero value (integer/double) => 1, 0/0.0 => 0
try {
dataRow[pair.getKey() - 1] = (0 == Double.parseDouble(data[pair.getKey() - 1])) ? Boolean.FALSE : Boolean.TRUE;
- }
- catch (NumberFormatException e) {
+ } catch (NumberFormatException e) {
dataRow[pair.getKey() - 1] = Boolean.parseBoolean(data[pair.getKey() - 1]);
}
break;
}
- case java.sql.Types.REAL: {
+ case Types.REAL: {
dataRow[pair.getKey() - 1] = Float.parseFloat(data[pair.getKey() - 1]);
break;
}
- case java.sql.Types.DOUBLE: {
+ case Types.DOUBLE: {
dataRow[pair.getKey() - 1] = Double.parseDouble(data[pair.getKey() - 1]);
break;
}
- case java.sql.Types.BINARY:
- case java.sql.Types.VARBINARY:
- case java.sql.Types.LONGVARBINARY:
- case java.sql.Types.BLOB: {
+ case Types.BINARY:
+ case Types.VARBINARY:
+ case Types.LONGVARBINARY:
+ case Types.BLOB: {
/*
* For binary data, the value in file may or may not have the '0x' prefix. We will try to match our implementation with
* 'BULK INSERT' except that we will allow 0x prefix whereas 'BULK INSERT' command does not allow 0x prefix. A BULK INSERT
@@ -630,14 +627,13 @@ public Object[] getRowData() throws SQLServerException {
String binData = data[pair.getKey() - 1].trim();
if (binData.startsWith("0x") || binData.startsWith("0X")) {
dataRow[pair.getKey() - 1] = binData.substring(2);
- }
- else {
+ } else {
dataRow[pair.getKey() - 1] = binData;
}
break;
}
- case 2013: // java.sql.Types.TIME_WITH_TIMEZONE
+ case 2013: // java.sql.Types.TIME_WITH_TIMEZONE
{
DriverJDBCVersion.checkSupportsJDBC42();
OffsetTime offsetTimeValue;
@@ -671,19 +667,19 @@ else if (dateTimeFormatter != null)
break;
}
- case java.sql.Types.NULL: {
+ case Types.NULL: {
dataRow[pair.getKey() - 1] = null;
break;
}
- case java.sql.Types.DATE:
- case java.sql.Types.CHAR:
- case java.sql.Types.NCHAR:
- case java.sql.Types.VARCHAR:
- case java.sql.Types.NVARCHAR:
- case java.sql.Types.LONGVARCHAR:
- case java.sql.Types.LONGNVARCHAR:
- case java.sql.Types.CLOB:
+ case Types.DATE:
+ case Types.CHAR:
+ case Types.NCHAR:
+ case Types.VARCHAR:
+ case Types.NVARCHAR:
+ case Types.LONGVARCHAR:
+ case Types.LONGNVARCHAR:
+ case Types.CLOB:
default: {
// The string is copied as is.
/*
@@ -702,13 +698,11 @@ else if (dateTimeFormatter != null)
break;
}
}
- }
- catch (IllegalArgumentException e) {
+ } catch (IllegalArgumentException e) {
String value = "'" + data[pair.getKey() - 1] + "'";
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_errorConvertingValue"));
- throw new SQLServerException(form.format(new Object[] {value, JDBCType.of(cm.columnType)}), null, 0, e);
- }
- catch (ArrayIndexOutOfBoundsException e) {
+ throw new SQLServerException(form.format(new Object[]{value, JDBCType.of(cm.columnType)}), null, 0, e);
+ } catch (ArrayIndexOutOfBoundsException e) {
throw new SQLServerException(SQLServerException.getErrString("R_CSVDataSchemaMismatch"), e);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
index 3076c90177..6e13ad187d 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
@@ -675,7 +675,7 @@ public void writeToServer(ISQLServerBulkRecord sourceData) throws SQLServerExcep
* Initializes the defaults for member variables that require it.
*/
private void initializeDefaults() {
- columnMappings = new LinkedList();
+ columnMappings = new LinkedList<>();
destinationTableName = null;
sourceBulkRecord = null;
sourceResultSet = null;
@@ -1471,7 +1471,7 @@ private String getDestTypeFromSrcType(int srcColIndx,
private String createInsertBulkCommand(TDSWriter tdsWriter) throws SQLServerException {
StringBuilder bulkCmd = new StringBuilder();
- List bulkOptions = new ArrayList();
+ List bulkOptions = new ArrayList<>();
String endColumn = " , ";
bulkCmd.append("INSERT BULK " + destinationTableName + " (");
@@ -1747,7 +1747,7 @@ private void getDestinationMetadata() throws SQLServerException {
.executeQueryInternal("SET FMTONLY ON SELECT * FROM " + destinationTableName + " SET FMTONLY OFF ");
destColumnCount = rs.getMetaData().getColumnCount();
- destColumnMetadata = new HashMap();
+ destColumnMetadata = new HashMap<>();
destCekTable = rs.getCekTable();
if (!connection.getServerSupportsColumnEncryption()) {
@@ -1793,7 +1793,7 @@ private void getDestinationMetadata() throws SQLServerException {
* source metadata from the same place for both ResultSet and File.
*/
private void getSourceMetadata() throws SQLServerException {
- srcColumnMetadata = new HashMap();
+ srcColumnMetadata = new HashMap<>();
int currentColumn;
if (null != sourceResultSet) {
try {
@@ -1818,9 +1818,8 @@ else if (null != sourceBulkRecord) {
}
else {
srcColumnCount = columnOrdinals.size();
- Iterator columnsIterator = columnOrdinals.iterator();
- while (columnsIterator.hasNext()) {
- currentColumn = columnsIterator.next();
+ for (Integer columnOrdinal : columnOrdinals) {
+ currentColumn = columnOrdinal;
srcColumnMetadata.put(currentColumn,
new BulkColumnMetaData(sourceBulkRecord.getColumnName(currentColumn), true, sourceBulkRecord.getPrecision(currentColumn),
sourceBulkRecord.getScale(currentColumn), sourceBulkRecord.getColumnType(currentColumn),
@@ -1944,9 +1943,7 @@ else if (0 > cm.destinationColumnOrdinal || destColumnCount < cm.destinationColu
}
else {
Set columnOrdinals = sourceBulkRecord.getColumnOrdinals();
- Iterator columnsIterator = columnOrdinals.iterator();
- while (columnsIterator.hasNext()) {
- int currentColumn = columnsIterator.next();
+ for (Integer currentColumn : columnOrdinals) {
if (sourceBulkRecord.getColumnName(currentColumn).equals(cm.sourceColumnName)) {
foundColumn = true;
cm.sourceColumnOrdinal = currentColumn;
@@ -3535,13 +3532,13 @@ private boolean writeBatchData(TDSWriter tdsWriter,
if (null != sourceResultSet) {
// Loop for each destination column. The mappings is a many to one mapping
// where multiple source columns can be mapped to one destination column.
- for (int i = 0; i < mappingColumnCount; ++i) {
- writeColumn(tdsWriter, columnMappings.get(i).sourceColumnOrdinal, columnMappings.get(i).destinationColumnOrdinal, null // cell
- // value is
- // retrieved
- // inside
- // writeRowData()
- // method.
+ for (ColumnMapping columnMapping : columnMappings) {
+ writeColumn(tdsWriter, columnMapping.sourceColumnOrdinal, columnMapping.destinationColumnOrdinal, null // cell
+ // value is
+ // retrieved
+ // inside
+ // writeRowData()
+ // method.
);
}
}
@@ -3558,11 +3555,11 @@ private boolean writeBatchData(TDSWriter tdsWriter,
throw new SQLServerException(SQLServerException.getErrString("R_unableRetrieveSourceData"), ex);
}
- for (int i = 0; i < mappingColumnCount; ++i) {
+ for (ColumnMapping columnMapping : columnMappings) {
// If the SQLServerBulkCSVRecord does not have metadata for columns, it returns strings in the object array.
// COnvert the strings using destination table types.
- writeColumn(tdsWriter, columnMappings.get(i).sourceColumnOrdinal, columnMappings.get(i).destinationColumnOrdinal,
- rowObjects[columnMappings.get(i).sourceColumnOrdinal - 1]);
+ writeColumn(tdsWriter, columnMapping.sourceColumnOrdinal, columnMapping.destinationColumnOrdinal,
+ rowObjects[columnMapping.sourceColumnOrdinal - 1]);
}
}
row++;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopyOptions.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopyOptions.java
index 774cd39cbf..c247b1c285 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopyOptions.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopyOptions.java
@@ -139,7 +139,7 @@ public int getBulkCopyTimeout() {
* @param timeout
* Number of seconds before operation times out.
* @throws SQLServerException
- * If the batchSize being set is invalid.
+ * If the timeout being set is invalid.
*/
public void setBulkCopyTimeout(int timeout) throws SQLServerException {
if (timeout >= 0) {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerCallableStatement.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerCallableStatement.java
index e5eaa7ccf5..40a77be153 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerCallableStatement.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerCallableStatement.java
@@ -1399,11 +1399,12 @@ public NClob getNClob(String parameterName) throws SQLException {
*/
/* L3 */ private int findColumn(String columnName) throws SQLServerException {
if (paramNames == null) {
+ SQLServerStatement s = null;
try {
// Note we are concatenating the information from the passed in sql, not any arguments provided by the user
// if the user can execute the sql, any fragments of it is potentially executed via the meta data call through injection
// is not a security issue.
- SQLServerStatement s = (SQLServerStatement) connection.createStatement();
+ s = (SQLServerStatement) connection.createStatement();
ThreePartName threePartName = ThreePartName.parse(procedureName);
StringBuilder metaQuery = new StringBuilder("exec sp_sproc_columns ");
if (null != threePartName.getDatabasePart()) {
@@ -1431,7 +1432,7 @@ public NClob getNClob(String parameterName) throws SQLException {
}
ResultSet rs = s.executeQueryInternal(metaQuery.toString());
- paramNames = new ArrayList();
+ paramNames = new ArrayList<>();
while (rs.next()) {
String sCol = rs.getString(4);
paramNames.add(sCol.trim());
@@ -1440,6 +1441,10 @@ public NClob getNClob(String parameterName) throws SQLException {
catch (SQLException e) {
SQLServerException.makeFromDriverError(connection, this, e.toString(), null, false);
}
+ finally {
+ if (null != s)
+ s.close();
+ }
}
int l = 0;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerClob.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerClob.java
index f933727cfe..a9556baf31 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerClob.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerClob.java
@@ -88,7 +88,7 @@ abstract class SQLServerClobBase implements Serializable {
// Initial size of the array is based on an assumption that a Clob/NClob object is
// typically used either for input or output, and then only once. The array size
// grows automatically if multiple streams are used.
- private ArrayList activeStreams = new ArrayList(1);
+ private ArrayList activeStreams = new ArrayList<>(1);
transient SQLServerConnection con;
private static Logger logger;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
index 487c99c389..42c050ab62 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
@@ -100,7 +100,7 @@ public class SQLServerConnection implements ISQLServerConnection {
private Boolean enablePrepareOnFirstPreparedStatementCall = null; // Current limit for this particular connection.
// Handle the actual queue of discarded prepared statements.
- private ConcurrentLinkedQueue discardedPreparedStatementHandles = new ConcurrentLinkedQueue();
+ private ConcurrentLinkedQueue discardedPreparedStatementHandles = new ConcurrentLinkedQueue<>();
private AtomicInteger discardedPreparedStatementHandleCount = new AtomicInteger(0);
private boolean fedAuthRequiredByUser = false;
@@ -525,7 +525,7 @@ boolean getServerSupportsColumnEncryption() {
}
static boolean isWindows;
- static Map globalSystemColumnEncryptionKeyStoreProviders = new HashMap();
+ static Map globalSystemColumnEncryptionKeyStoreProviders = new HashMap<>();
static {
if (System.getProperty("os.name").toLowerCase(Locale.ENGLISH).startsWith("windows")) {
isWindows = true;
@@ -538,7 +538,7 @@ boolean getServerSupportsColumnEncryption() {
}
static Map globalCustomColumnEncryptionKeyStoreProviders = null;
// This is a per-connection store provider. It can be JKS or AKV.
- Map systemColumnEncryptionKeyStoreProvider = new HashMap();
+ Map systemColumnEncryptionKeyStoreProvider = new HashMap<>();
/**
* Registers key store providers in the globalCustomColumnEncryptionKeyStoreProviders.
@@ -561,7 +561,7 @@ public static synchronized void registerColumnEncryptionKeyStoreProviders(
throw new SQLServerException(null, SQLServerException.getErrString("R_CustomKeyStoreProviderSetOnce"), null, 0, false);
}
- globalCustomColumnEncryptionKeyStoreProviders = new HashMap();
+ globalCustomColumnEncryptionKeyStoreProviders = new HashMap<>();
for (Map.Entry entry : clientKeyStoreProviders.entrySet()) {
String providerName = entry.getKey();
@@ -625,7 +625,7 @@ synchronized SQLServerColumnEncryptionKeyStoreProvider getSystemColumnEncryption
}
private String trustedServerNameAE = null;
- private static Map> columnEncryptionTrustedMasterKeyPaths = new HashMap>();
+ private static Map> columnEncryptionTrustedMasterKeyPaths = new HashMap<>();
/**
* Sets Trusted Master Key Paths in the columnEncryptionTrustedMasterKeyPaths.
@@ -691,7 +691,7 @@ public static synchronized void removeColumnEncryptionTrustedMasterKeyPaths(Stri
public static synchronized Map> getColumnEncryptionTrustedMasterKeyPaths() {
loggerExternal.entering(SQLServerConnection.class.getName(), "getColumnEncryptionTrustedMasterKeyPaths", "Getting Trusted Master Key Paths");
- Map> masterKeyPathCopy = new HashMap>();
+ Map> masterKeyPathCopy = new HashMap<>();
for (Map.Entry> entry : columnEncryptionTrustedMasterKeyPaths.entrySet()) {
masterKeyPathCopy.put(entry.getKey(), entry.getValue());
@@ -1079,7 +1079,10 @@ Connection connect(Properties propsIn,
// timeout, default is 15 per spec
String sPropValue = propsIn.getProperty(SQLServerDriverIntProperty.LOGIN_TIMEOUT.toString());
if (null != sPropValue && sPropValue.length() > 0) {
- loginTimeoutSeconds = Integer.parseInt(sPropValue);
+ int sPropValueInt = Integer.parseInt(sPropValue);
+ if (0 != sPropValueInt) { // Use the default timeout in case of a zero value
+ loginTimeoutSeconds = sPropValueInt;
+ }
}
}
@@ -1694,6 +1697,16 @@ else if (0 == requestedPacketSize)
setEnablePrepareOnFirstPreparedStatementCall(booleanPropertyOn(sPropKey, sPropValue));
}
+ sPropKey = SQLServerDriverStringProperty.SSL_PROTOCOL.toString();
+ sPropValue = activeConnectionProperties.getProperty(sPropKey);
+ if (null == sPropValue) {
+ sPropValue = SQLServerDriverStringProperty.SSL_PROTOCOL.getDefaultValue().toString();
+ activeConnectionProperties.setProperty(sPropKey, sPropValue);
+ }
+ else {
+ activeConnectionProperties.setProperty(sPropKey, SSLProtocol.valueOfString(sPropValue).toString());
+ }
+
FailoverInfo fo = null;
String databaseNameProperty = SQLServerDriverStringProperty.DATABASE_NAME.toString();
String serverNameProperty = SQLServerDriverStringProperty.SERVER_NAME.toString();
@@ -3217,7 +3230,7 @@ public CallableStatement prepareCall(String sql,
public java.util.Map> getTypeMap() throws SQLServerException {
loggerExternal.entering(getClassNameLogging(), "getTypeMap");
checkClosed();
- java.util.Map> mp = new java.util.HashMap>();
+ java.util.Map> mp = new java.util.HashMap<>();
loggerExternal.exiting(getClassNameLogging(), "getTypeMap", mp);
return mp;
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
index 25c269f83c..16891f3f0b 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
@@ -585,13 +585,14 @@ public boolean getFIPS() {
return getBooleanProperty(connectionProps, SQLServerDriverBooleanProperty.FIPS.toString(),
SQLServerDriverBooleanProperty.FIPS.getDefaultValue());
}
-
- public void setFIPSProvider(String fipsProvider) {
- setStringProperty(connectionProps, SQLServerDriverStringProperty.FIPS_PROVIDER.toString(), fipsProvider);
+
+ public void setSSLProtocol(String sslProtocol) {
+ setStringProperty(connectionProps, SQLServerDriverStringProperty.SSL_PROTOCOL.toString(), sslProtocol);
}
- public String getFIPSProvider() {
- return getStringProperty(connectionProps, SQLServerDriverStringProperty.FIPS_PROVIDER.toString(), null);
+ public String getSSLProtocol() {
+ return getStringProperty(connectionProps, SQLServerDriverStringProperty.SSL_PROTOCOL.toString(),
+ SQLServerDriverStringProperty.SSL_PROTOCOL.getDefaultValue());
}
// The URL property is exposed for backwards compatibility reasons. Also, several
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataTable.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataTable.java
index 53284f3722..d69d3e2744 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataTable.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataTable.java
@@ -36,8 +36,8 @@ public final class SQLServerDataTable {
*/
// Name used in CREATE TYPE
public SQLServerDataTable() throws SQLServerException {
- columnMetadata = new LinkedHashMap();
- rows = new HashMap();
+ columnMetadata = new LinkedHashMap<>();
+ rows = new HashMap<>();
}
/**
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
index 25e7a7c146..06fbab5277 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
@@ -89,7 +89,7 @@ final void close() throws SQLServerException {
}
}
- EnumMap handleMap = new EnumMap(CallableHandles.class);
+ EnumMap handleMap = new EnumMap<>(CallableHandles.class);
// Returns unique id for each instance.
private static int nextInstanceID() {
@@ -244,7 +244,6 @@ private SQLServerResultSet getResultSetFromInternalQueries(String catalog,
SQLServerResultSet rs = null;
try {
rs = ((SQLServerStatement) connection.createStatement()).executeQueryInternal(query);
-
}
finally {
if (null != orgCat) {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDriver.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDriver.java
index bfe9612202..307e0fb12c 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDriver.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDriver.java
@@ -117,6 +117,46 @@ else if (value.toLowerCase(Locale.US).equalsIgnoreCase(ColumnEncryptionSetting.D
}
}
+enum SSLProtocol {
+ TLS("TLS"),
+ TLS_V10("TLSv1"),
+ TLS_V11("TLSv1.1"),
+ TLS_V12("TLSv1.2"),;
+
+ private final String name;
+
+ private SSLProtocol(String name) {
+ this.name = name;
+ }
+
+ public String toString() {
+ return name;
+ }
+
+ static SSLProtocol valueOfString(String value) throws SQLServerException {
+ SSLProtocol protocol = null;
+
+ if (value.toLowerCase(Locale.ENGLISH).equalsIgnoreCase(SSLProtocol.TLS.toString())) {
+ protocol = SSLProtocol.TLS;
+ }
+ else if (value.toLowerCase(Locale.ENGLISH).equalsIgnoreCase(SSLProtocol.TLS_V10.toString())) {
+ protocol = SSLProtocol.TLS_V10;
+ }
+ else if (value.toLowerCase(Locale.ENGLISH).equalsIgnoreCase(SSLProtocol.TLS_V11.toString())) {
+ protocol = SSLProtocol.TLS_V11;
+ }
+ else if (value.toLowerCase(Locale.ENGLISH).equalsIgnoreCase(SSLProtocol.TLS_V12.toString())) {
+ protocol = SSLProtocol.TLS_V12;
+ }
+ else {
+ MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_invalidSSLProtocol"));
+ Object[] msgArgs = {value};
+ throw new SQLServerException(null, form.format(msgArgs), null, 0, false);
+ }
+ return protocol;
+ }
+}
+
enum KeyStoreAuthentication {
JavaKeyStorePassword;
@@ -246,7 +286,7 @@ enum SQLServerDriverStringProperty
KEY_STORE_AUTHENTICATION ("keyStoreAuthentication", ""),
KEY_STORE_SECRET ("keyStoreSecret", ""),
KEY_STORE_LOCATION ("keyStoreLocation", ""),
- FIPS_PROVIDER ("fipsProvider", ""),
+ SSL_PROTOCOL ("sslProtocol", SSLProtocol.TLS.toString()),
;
private final String name;
@@ -377,13 +417,13 @@ public final class SQLServerDriver implements java.sql.Driver {
new SQLServerDriverPropertyInfo(SQLServerDriverBooleanProperty.XOPEN_STATES.toString(), Boolean.toString(SQLServerDriverBooleanProperty.XOPEN_STATES.getDefaultValue()), false, TRUE_FALSE),
new SQLServerDriverPropertyInfo(SQLServerDriverStringProperty.AUTHENTICATION_SCHEME.toString(), SQLServerDriverStringProperty.AUTHENTICATION_SCHEME.getDefaultValue(), false, new String[] {AuthenticationScheme.javaKerberos.toString(),AuthenticationScheme.nativeAuthentication.toString()}),
new SQLServerDriverPropertyInfo(SQLServerDriverStringProperty.AUTHENTICATION.toString(), SQLServerDriverStringProperty.AUTHENTICATION.getDefaultValue(), false, new String[] {SqlAuthentication.NotSpecified.toString(),SqlAuthentication.SqlPassword.toString(),SqlAuthentication.ActiveDirectoryPassword.toString(),SqlAuthentication.ActiveDirectoryIntegrated.toString()}),
- new SQLServerDriverPropertyInfo(SQLServerDriverStringProperty.FIPS_PROVIDER.toString(), SQLServerDriverStringProperty.FIPS_PROVIDER.getDefaultValue(), false, null),
new SQLServerDriverPropertyInfo(SQLServerDriverIntProperty.SOCKET_TIMEOUT.toString(), Integer.toString(SQLServerDriverIntProperty.SOCKET_TIMEOUT.getDefaultValue()), false, null),
new SQLServerDriverPropertyInfo(SQLServerDriverBooleanProperty.FIPS.toString(), Boolean.toString(SQLServerDriverBooleanProperty.FIPS.getDefaultValue()), false, TRUE_FALSE),
new SQLServerDriverPropertyInfo(SQLServerDriverBooleanProperty.ENABLE_PREPARE_ON_FIRST_PREPARED_STATEMENT.toString(), Boolean.toString(SQLServerDriverBooleanProperty.ENABLE_PREPARE_ON_FIRST_PREPARED_STATEMENT.getDefaultValue()), false,TRUE_FALSE),
new SQLServerDriverPropertyInfo(SQLServerDriverIntProperty.SERVER_PREPARED_STATEMENT_DISCARD_THRESHOLD.toString(), Integer.toString(SQLServerDriverIntProperty.SERVER_PREPARED_STATEMENT_DISCARD_THRESHOLD.getDefaultValue()), false, null),
new SQLServerDriverPropertyInfo(SQLServerDriverIntProperty.STATEMENT_POOLING_CACHE_SIZE.toString(), Integer.toString(SQLServerDriverIntProperty.STATEMENT_POOLING_CACHE_SIZE.getDefaultValue()), false, null),
new SQLServerDriverPropertyInfo(SQLServerDriverStringProperty.JAAS_CONFIG_NAME.toString(), SQLServerDriverStringProperty.JAAS_CONFIG_NAME.getDefaultValue(), false, null),
+ new SQLServerDriverPropertyInfo(SQLServerDriverStringProperty.SSL_PROTOCOL.toString(), SQLServerDriverStringProperty.SSL_PROTOCOL.getDefaultValue(), false, new String[] {SSLProtocol.TLS.toString(), SSLProtocol.TLS_V10.toString(), SSLProtocol.TLS_V11.toString(), SSLProtocol.TLS_V12.toString()}),
};
// Properties that can only be set by using Properties.
@@ -485,8 +525,8 @@ static Properties mergeURLAndSuppliedProperties(Properties urlProps,
return urlProps;
Properties suppliedPropertiesFixed = fixupProperties(suppliedProperties);
// Merge URL properties and supplied properties.
- for (int i = 0; i < DRIVER_PROPERTIES.length; i++) {
- String sProp = DRIVER_PROPERTIES[i].getName();
+ for (SQLServerDriverPropertyInfo DRIVER_PROPERTY : DRIVER_PROPERTIES) {
+ String sProp = DRIVER_PROPERTY.getName();
String sPropVal = suppliedPropertiesFixed.getProperty(sProp); // supplied properties have precedence
if (null != sPropVal) {
// overwrite the property in urlprops if already exists. supp prop has more precedence
@@ -495,8 +535,8 @@ static Properties mergeURLAndSuppliedProperties(Properties urlProps,
}
// Merge URL properties with property-only properties
- for (int i = 0; i < DRIVER_PROPERTIES_PROPERTY_ONLY.length; i++) {
- String sProp = DRIVER_PROPERTIES_PROPERTY_ONLY[i].getName();
+ for (SQLServerDriverPropertyInfo aDRIVER_PROPERTIES_PROPERTY_ONLY : DRIVER_PROPERTIES_PROPERTY_ONLY) {
+ String sProp = aDRIVER_PROPERTIES_PROPERTY_ONLY.getName();
Object oPropVal = suppliedPropertiesFixed.get(sProp); // supplied properties have precedence
if (null != oPropVal) {
// overwrite the property in urlprops if already exists. supp prop has more precedence
@@ -520,14 +560,14 @@ static String getNormalizedPropertyName(String name,
if (null == name)
return name;
- for (int i = 0; i < driverPropertiesSynonyms.length; i++) {
- if (driverPropertiesSynonyms[i][0].equalsIgnoreCase(name)) {
- return driverPropertiesSynonyms[i][1];
+ for (String[] driverPropertiesSynonym : driverPropertiesSynonyms) {
+ if (driverPropertiesSynonym[0].equalsIgnoreCase(name)) {
+ return driverPropertiesSynonym[1];
}
}
- for (int i = 0; i < DRIVER_PROPERTIES.length; i++) {
- if (DRIVER_PROPERTIES[i].getName().equalsIgnoreCase(name)) {
- return DRIVER_PROPERTIES[i].getName();
+ for (SQLServerDriverPropertyInfo DRIVER_PROPERTY : DRIVER_PROPERTIES) {
+ if (DRIVER_PROPERTY.getName().equalsIgnoreCase(name)) {
+ return DRIVER_PROPERTY.getName();
}
}
@@ -549,9 +589,9 @@ static String getPropertyOnlyName(String name,
if (null == name)
return name;
- for (int i = 0; i < DRIVER_PROPERTIES_PROPERTY_ONLY.length; i++) {
- if (DRIVER_PROPERTIES_PROPERTY_ONLY[i].getName().equalsIgnoreCase(name)) {
- return DRIVER_PROPERTIES_PROPERTY_ONLY[i].getName();
+ for (SQLServerDriverPropertyInfo aDRIVER_PROPERTIES_PROPERTY_ONLY : DRIVER_PROPERTIES_PROPERTY_ONLY) {
+ if (aDRIVER_PROPERTIES_PROPERTY_ONLY.getName().equalsIgnoreCase(name)) {
+ return aDRIVER_PROPERTIES_PROPERTY_ONLY.getName();
}
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerEncryptionAlgorithmFactoryList.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerEncryptionAlgorithmFactoryList.java
index 91c9a3973d..a7eb1c0ded 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerEncryptionAlgorithmFactoryList.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerEncryptionAlgorithmFactoryList.java
@@ -21,7 +21,7 @@ final class SQLServerEncryptionAlgorithmFactoryList {
private static final SQLServerEncryptionAlgorithmFactoryList instance = new SQLServerEncryptionAlgorithmFactoryList();
private SQLServerEncryptionAlgorithmFactoryList() {
- encryptionAlgoFactoryMap = new ConcurrentHashMap();
+ encryptionAlgoFactoryMap = new ConcurrentHashMap<>();
encryptionAlgoFactoryMap.putIfAbsent(SQLServerAeadAes256CbcHmac256Algorithm.algorithmName, new SQLServerAeadAes256CbcHmac256Factory());
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
index 2f4dfd06ca..e8ed55d5ab 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
@@ -103,14 +103,12 @@ final void setDriverErrorCode(int value) {
if (exLogger.isLoggable(Level.FINE)) {
StringBuilder sb = new StringBuilder(100);
StackTraceElement st[] = this.getStackTrace();
- for (int i = 0; i < st.length; i++)
- sb.append(st[i].toString());
+ for (StackTraceElement aSt : st) sb.append(aSt.toString());
Throwable t = this.getCause();
if (t != null) {
sb.append("\n caused by " + t + "\n");
StackTraceElement tst[] = t.getStackTrace();
- for (int i = 0; i < tst.length; i++)
- sb.append(tst[i].toString());
+ for (StackTraceElement aTst : tst) sb.append(aTst.toString());
}
exLogger.fine(sb.toString());
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
index 04df112ea8..1d11e61afd 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
@@ -563,6 +563,8 @@ private void checkClosed() throws SQLServerException {
assert null != st;
stmtParent = st;
con = st.connection;
+ SQLServerStatement s = null;
+ SQLServerStatement stmt = null;
if (logger.isLoggable(java.util.logging.Level.FINE)) {
logger.fine(toString() + " created by (" + st.toString() + ")");
}
@@ -571,7 +573,7 @@ private void checkClosed() throws SQLServerException {
// If the CallableStatement/PreparedStatement is a stored procedure call
// then we can extract metadata using sp_sproc_columns
if (null != st.procedureName) {
- SQLServerStatement s = (SQLServerStatement) con.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
+ s = (SQLServerStatement) con.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
String sProc = parseProcIdentifier(st.procedureName);
if (con.isKatmaiOrLater())
rsProcedureMeta = s.executeQueryInternal("exec sp_sproc_columns_100 " + sProc + ", @ODBCVer=3");
@@ -601,7 +603,7 @@ private void checkClosed() throws SQLServerException {
// procedure "sp_describe_undeclared_parameters" to retrieve parameter meta data
// if SQL server version is 2008, then use FMTONLY
else {
- queryMetaMap = new HashMap();
+ queryMetaMap = new HashMap<>();
if (con.getServerMajorVersion() >= SQL_SERVER_2012_VERSION) {
// new implementation for SQL verser 2012 and above
@@ -616,7 +618,7 @@ private void checkClosed() throws SQLServerException {
else {
// old implementation for SQL server 2008
stringToParse = sProcString;
- ArrayList metaInfoList = new ArrayList();
+ ArrayList metaInfoList = new ArrayList<>();
while (stringToParse.length() > 0) {
MetaInfo metaInfo = parseStatement(stringToParse);
@@ -659,13 +661,11 @@ private void checkClosed() throws SQLServerException {
String tablesAndJoins = sbTablesAndJoins.toString();
- Statement stmt = con.createStatement();
+ stmt = (SQLServerStatement) con.createStatement();
String sCom = "sp_executesql N'SET FMTONLY ON SELECT " + columns + " FROM " + tablesAndJoins + " '";
ResultSet rs = stmt.executeQuery(sCom);
parseQueryMetaFor2008(rs);
- stmt.close();
- rs.close();
}
}
}
@@ -679,6 +679,10 @@ private void checkClosed() throws SQLServerException {
catch(StringIndexOutOfBoundsException e){
SQLServerException.makeFromDriverError(con, stmtParent, e.toString(), null, false);
}
+ finally {
+ if (null != stmt)
+ stmt.close();
+ }
}
public boolean isWrapperFor(Class> iface) throws SQLException {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPooledConnection.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPooledConnection.java
index f407dff112..cc059434d8 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPooledConnection.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPooledConnection.java
@@ -38,7 +38,7 @@ public class SQLServerPooledConnection implements PooledConnection {
SQLServerPooledConnection(SQLServerDataSource ds,
String user,
String password) throws SQLException {
- listeners = new Vector();
+ listeners = new Vector<>();
// Piggyback SQLServerDataSource logger for now.
pcLogger = SQLServerDataSource.dsLogger;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
index 2b9350e490..1ba3c62e8d 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
@@ -98,6 +98,9 @@ public class SQLServerPreparedStatement extends SQLServerStatement implements IS
/** The prepared statement handle returned by the server */
private int prepStmtHandle = 0;
+
+ /** Statement used for getMetadata(). Declared as a field to facilitate closing the statement. */
+ private SQLServerStatement internalStmt = null;
private void setPreparedStatementHandle(int handle) {
this.prepStmtHandle = handle;
@@ -271,6 +274,18 @@ final void closeInternal() {
// If we have a prepared statement handle, close it.
closePreparedHandle();
+
+ // Close the statement that was used to generate empty statement from getMetadata().
+ try {
+ if (null != internalStmt)
+ internalStmt.close();
+ } catch (SQLServerException e) {
+ if (loggerExternal.isLoggable(java.util.logging.Level.FINER))
+ loggerExternal.finer("Ignored error closing internal statement: " + e.getErrorCode() + " " + e.getMessage());
+ }
+ finally {
+ internalStmt = null;
+ }
// Clean up client-side state
batchParamValues = null;
@@ -338,7 +353,7 @@ private String buildParamTypeDefinitions(Parameter[] params,
StringBuilder sb = new StringBuilder();
int nCols = params.length;
char cParamName[] = new char[10];
- parameterNames = new ArrayList();
+ parameterNames = new ArrayList<>();
for (int i = 0; i < nCols; i++) {
if (i > 0)
@@ -795,7 +810,7 @@ private void getParameterEncryptionMetadata(Parameter[] params) throws SQLServer
return;
}
- Map cekList = new HashMap();
+ Map cekList = new HashMap<>();
CekTableEntry cekEntry = null;
try {
while (rs.next()) {
@@ -1023,8 +1038,8 @@ else if (resultSet != null) {
ResultSet emptyResultSet = null;
try {
fmtSQL = replaceMarkerWithNull(fmtSQL);
- SQLServerStatement stmt = (SQLServerStatement) connection.createStatement();
- emptyResultSet = stmt.executeQueryInternal("set fmtonly on " + fmtSQL + "\nset fmtonly off");
+ internalStmt = (SQLServerStatement) connection.createStatement();
+ emptyResultSet = internalStmt.executeQueryInternal("set fmtonly on " + fmtSQL + "\nset fmtonly off");
}
catch (SQLException sqle) {
if (false == sqle.getMessage().equals(SQLServerException.getErrString("R_noResultset"))) {
@@ -2376,7 +2391,7 @@ public final void addBatch() throws SQLServerException {
// Create the list of batch parameter values first time through
if (batchParamValues == null)
- batchParamValues = new ArrayList();
+ batchParamValues = new ArrayList<>();
final int numParams = inOutParam.length;
Parameter paramValues[] = new Parameter[numParams];
@@ -2417,10 +2432,9 @@ public int[] executeBatch() throws SQLServerException, BatchUpdateException {
//
// OUT and INOUT parameter checking is done here, before executing the batch. If any
// OUT or INOUT are present, the entire batch fails.
- for (int batch = 0; batch < batchParamValues.size(); ++batch) {
- Parameter paramValues[] = batchParamValues.get(batch);
- for (int param = 0; param < paramValues.length; ++param) {
- if (paramValues[param].isOutput()) {
+ for (Parameter[] paramValues : batchParamValues) {
+ for (Parameter paramValue : paramValues) {
+ if (paramValue.isOutput()) {
throw new BatchUpdateException(SQLServerException.getErrString("R_outParamsNotPermittedinBatch"), null, 0, null);
}
}
@@ -2475,10 +2489,9 @@ public long[] executeLargeBatch() throws SQLServerException, BatchUpdateExceptio
//
// OUT and INOUT parameter checking is done here, before executing the batch. If any
// OUT or INOUT are present, the entire batch fails.
- for (int batch = 0; batch < batchParamValues.size(); ++batch) {
- Parameter paramValues[] = batchParamValues.get(batch);
- for (int param = 0; param < paramValues.length; ++param) {
- if (paramValues[param].isOutput()) {
+ for (Parameter[] paramValues : batchParamValues) {
+ for (Parameter paramValue : paramValues) {
+ if (paramValue.isOutput()) {
throw new BatchUpdateException(SQLServerException.getErrString("R_outParamsNotPermittedinBatch"), null, 0, null);
}
}
@@ -2538,7 +2551,7 @@ final void doExecutePreparedStatementBatch(PrepStmtBatchExecCmd batchCommand) th
int numBatchesPrepared = 0;
int numBatchesExecuted = 0;
- Vector cryptoMetaBatch = new Vector();
+ Vector cryptoMetaBatch = new Vector<>();
if (isSelect(userSQL)) {
SQLServerException.makeFromDriverError(connection, this, SQLServerException.getErrString("R_selectNotPermittedinBatch"), null, true);
@@ -2573,8 +2586,8 @@ final void doExecutePreparedStatementBatch(PrepStmtBatchExecCmd batchCommand) th
buildPreparedStrings(batchParam, true);
// Save the crypto metadata retrieved for the first batch. We will re-use these for the rest of the batches.
- for (int i = 0; i < batchParam.length; i++) {
- cryptoMetaBatch.add(batchParam[i].cryptoMeta);
+ for (Parameter aBatchParam : batchParam) {
+ cryptoMetaBatch.add(aBatchParam.cryptoMeta);
}
}
@@ -2683,10 +2696,17 @@ final void doExecutePreparedStatementBatch(PrepStmtBatchExecCmd batchCommand) th
numBatchesPrepared = numBatchesExecuted;
continue;
}
- else
+ else if (null != batchCommand.batchException) {
+ // if batch exception occurred, loop out to throw the initial batchException
+ numBatchesExecuted = numBatchesPrepared;
+ attempt++;
+ continue;
+ }
+ else {
throw e;
+ }
}
- break;
+ break;
}
}
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResource.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResource.java
index 3945a2096c..0276af73b8 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResource.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResource.java
@@ -38,7 +38,7 @@ protected Object[][] getContents() {
{"R_invalidLength", "The length {0} is not valid."},
{"R_unknownSSType", "Invalid SQL Server data type {0}."},
{"R_unknownJDBCType", "Invalid JDBC data type {0}."},
- {"R_notSQLServer", "The driver received an unexpected pre-login response. Verify the connection properties and check that an instance of SQL Server is running on the host and accepting TCP/IP connections at the port. This driver can be used only with SQL Server 2000 or later."},
+ {"R_notSQLServer", "The driver received an unexpected pre-login response. Verify the connection properties and check that an instance of SQL Server is running on the host and accepting TCP/IP connections at the port. This driver can be used only with SQL Server 2005 or later."},
{"R_tcpOpenFailed", "{0}. Verify the connection properties. Make sure that an instance of SQL Server is running on the host and accepting TCP/IP connections at the port. Make sure that TCP connections to the port are not blocked by a firewall."},
{"R_unsupportedJREVersion", "Java Runtime Environment (JRE) version {0} is not supported by this driver. Use the sqljdbc4.jar class library, which provides support for JDBC 4.0."},
{"R_unsupportedServerVersion", "SQL Server version {0} is not supported by this driver."},
@@ -180,8 +180,8 @@ protected Object[][] getContents() {
{"R_packetSizePropertyDescription", "The network packet size used to communicate with SQL Server."},
{"R_encryptPropertyDescription", "Determines if Secure Sockets Layer (SSL) encryption should be used between the client and the server."},
{"R_trustServerCertificatePropertyDescription", "Determines if the driver should validate the SQL Server Secure Sockets Layer (SSL) certificate."},
- {"R_trustStoreTypePropertyDescription", "Type of trust store type like JKS / PKCS12 or any FIPS Provider KeyStore implementation Type."},
- {"R_trustStorePropertyDescription", "The path to the certificate trust store file."},
+ {"R_trustStoreTypePropertyDescription", "KeyStore type."},
+ {"R_trustStorePropertyDescription", "The path to the certificate TrustStore file."},
{"R_trustStorePasswordPropertyDescription", "The password used to check the integrity of the trust store data."},
{"R_hostNameInCertificatePropertyDescription", "The host name to be used when validating the SQL Server Secure Sockets Layer (SSL) certificate."},
{"R_sendTimeAsDatetimePropertyDescription", "Determines whether to use the SQL Server datetime data type to send java.sql.Time values to the database."},
@@ -190,7 +190,7 @@ protected Object[][] getContents() {
{"R_socketTimeoutPropertyDescription", "The number of milliseconds to wait before the java.net.SocketTimeoutException is raised."},
{"R_serverPreparedStatementDiscardThresholdPropertyDescription", "The threshold for when to close discarded prepare statements on the server (calling a batch of sp_unprepares). A value of 1 or less will cause sp_unprepare to be called immediately on PreparedStatment close."},
{"R_enablePrepareOnFirstPreparedStatementCallPropertyDescription", "This setting specifies whether a prepared statement is prepared (sp_prepexec) on first use (property=true) or on second after first calling sp_executesql (property=false)."},
- {"R_statementPoolingCacheSizePropertyDescription", "This setting specifies the size of the prepared statement cache for a conection. A value less than 1 means no cache."},
+ {"R_statementPoolingCacheSizePropertyDescription", "This setting specifies the size of the prepared statement cache for a connection. A value less than 1 means no cache."},
{"R_gsscredentialPropertyDescription", "Impersonated GSS Credential to access SQL Server."},
{"R_noParserSupport", "An error occurred while instantiating the required parser. Error: \"{0}\""},
{"R_writeOnlyXML", "Cannot read from this SQLXML instance. This instance is for writing data only."},
@@ -222,7 +222,7 @@ protected Object[][] getContents() {
{"R_unableRetrieveSourceData", "Unable to retrieve data from the source."},
{"R_ParsingError", "Failed to parse data for the {0} type."},
{"R_BulkTypeNotSupported", "Data type {0} is not supported in bulk copy."},
- {"R_invalidTransactionOption", "UseInternalTransaction option can not be set to TRUE when used with a Connection object."},
+ {"R_invalidTransactionOption", "UseInternalTransaction option cannot be set to TRUE when used with a Connection object."},
{"R_invalidNegativeArg", "The {0} argument cannot be negative."},
{"R_BulkColumnMappingsIsEmpty", "Cannot perform bulk copy operation if the only mapping is an identity column and KeepIdentity is set to false."},
{"R_CSVDataSchemaMismatch", "Source data does not match source schema."},
@@ -260,7 +260,7 @@ protected Object[][] getContents() {
{"R_CertificateError", "Error occurred while retrieving certificate \"{0}\" from keystore \"{1}\"."},
{"R_ByteToShortConversion", "Error occurred while decrypting column encryption key."},
{"R_InvalidCertificateSignature", "The specified encrypted column encryption key signature does not match the signature computed with the column master key (certificate) in \"{0}\". The encrypted column encryption key may be corrupt, or the specified path may be incorrect."},
- {"R_CEKDecryptionFailed", "Exception while decryption of encrypted column encryption key : {0} "},
+ {"R_CEKDecryptionFailed", "Exception while decryption of encrypted column encryption key: {0} "},
{"R_NullKeyEncryptionAlgorithm", "Key encryption algorithm cannot be null."},
{"R_NullKeyEncryptionAlgorithmInternal", "Internal error. Key encryption algorithm cannot be null."},
{"R_InvalidKeyEncryptionAlgorithm", "Invalid key encryption algorithm specified: {0}. Expected value: {1}."},
@@ -268,7 +268,7 @@ protected Object[][] getContents() {
{"R_NullColumnEncryptionKey", "Column encryption key cannot be null."},
{"R_EmptyColumnEncryptionKey", "Empty column encryption key specified."},
{"R_CertificateNotFoundForAlias", "Certificate with alias {0} not found in the store provided by {1}. Verify the certificate has been imported correctly into the certificate location/store."},
- {"R_UnrecoverableKeyAE", "Cannot recover private key from keystore with certificate details {0}. Verify that imported AE certificate contains private key and password provided for certificate is correct."},
+ {"R_UnrecoverableKeyAE", "Cannot recover private key from keystore with certificate details {0}. Verify that imported certificate for Always Encrypted contains private key and password provided for certificate is correct."},
{"R_KeyStoreNotFound", "System cannot find the key store file at the specified path. Verify that the path is correct and you have proper permissions to access it."},
{"R_CustomKeyStoreProviderMapNull", "Column encryption key store provider map cannot be null. Expecting a non-null value."},
{"R_EmptyCustomKeyStoreProviderName", "Invalid key store provider name specified. Key store provider names cannot be null or empty."},
@@ -306,7 +306,7 @@ protected Object[][] getContents() {
{"R_ForceEncryptionTrue_HonorAETrue_UnencryptedColumnRS", "Cannot execute update because Force Encryption was set as true for parameter {0} and the database expects this parameter to be sent as plaintext. This may be due to a configuration error."},
{"R_NullValue","{0} cannot be null."},
{"R_AKVPathNull", "Azure Key Vault key path cannot be null." },
- {"R_AKVURLInvalid", "Invalid url specified: {0}." },
+ {"R_AKVURLInvalid", "Invalid URL specified: {0}." },
{"R_AKVMasterKeyPathInvalid", "Invalid Azure Key Vault key path specified: {0}."},
{"R_EmptyCEK","Empty column encryption key specified."},
{"R_EncryptedCEKNull","Encrypted column encryption key cannot be null."},
@@ -320,8 +320,8 @@ protected Object[][] getContents() {
{"R_NoSHA256Algorithm","SHA-256 Algorithm is not supported."},
{"R_VerifySignature","Unable to verify signature of the column encryption key."},
{"R_CEKSignatureNotMatchCMK","The specified encrypted column encryption key signature does not match the signature computed with the column master key (Asymmetric key in Azure Key Vault) in {0}. The encrypted column encryption key may be corrupt, or the specified path may be incorrect."},
- {"R_DecryptCEKError","Unable to decrypt CEK using specified Azure Key Vault key."},
- {"R_EncryptCEKError","Unable to encrypt CEK using specified Azure Key Vault key."},
+ {"R_DecryptCEKError","Unable to decrypt column encryption key using specified Azure Key Vault key."},
+ {"R_EncryptCEKError","Unable to encrypt column encryption key using specified Azure Key Vault key."},
{"R_CipherTextLengthNotMatchRSASize","CipherText length does not match the RSA key size."},
{"R_GenerateSignature","Unable to generate signature using a specified Azure Key Vault Key URL."},
{"R_SignedHashLengthError","Signed hash length does not match the RSA key size."},
@@ -363,8 +363,7 @@ protected Object[][] getContents() {
{"R_keyStoreAuthenticationPropertyDescription", "The name that identifies a key store."},
{"R_keyStoreSecretPropertyDescription", "The authentication secret or information needed to locate the secret."},
{"R_keyStoreLocationPropertyDescription", "The key store location."},
- {"R_fipsProviderPropertyDescription", "FIPS Provider."},
- {"R_keyStoreAuthenticationNotSet", "\"keyStoreAuthentication\" connection string keyword must be specified, if \"{0}\" is specified."},
+ {"R_keyStoreAuthenticationNotSet", "\"keyStoreAuthentication\" connection string keyword must be specified, if \"{0}\" is specified."},
{"R_keyStoreSecretOrLocationNotSet", "Both \"keyStoreSecret\" and \"keyStoreLocation\" must be set, if \"keyStoreAuthentication=JavaKeyStorePassword\" has been specified in the connection string."},
{"R_certificateStoreInvalidKeyword", "Cannot set \"keyStoreSecret\", if \"keyStoreAuthentication=CertificateStore\" has been specified in the connection string."},
{"R_certificateStoreLocationNotSet", "\"keyStoreLocation\" must be specified, if \"keyStoreAuthentication=CertificateStore\" has been specified in the connection string."},
@@ -372,13 +371,11 @@ protected Object[][] getContents() {
{"R_invalidKeyStoreFile", "Cannot parse \"{0}\". Either the file format is not valid or the password is not correct."}, // for JKS/PKCS
{"R_invalidCEKCacheTtl", "Invalid column encryption key cache time-to-live specified. The columnEncryptionKeyCacheTtl value cannot be negative and timeUnit can only be DAYS, HOURS, MINUTES or SECONDS."},
{"R_sendTimeAsDateTimeForAE", "Use sendTimeAsDateTime=false with Always Encrypted."},
- {"R_TVPnotWorkWithSetObjectResultSet" , "setObject() with ResultSet is not supported for Table-Valued Parameter. Please use setStructured()."},
+ {"R_TVPnotWorkWithSetObjectResultSet", "setObject() with ResultSet is not supported for Table-Valued Parameter. Please use setStructured()."},
{"R_invalidQueryTimeout", "The queryTimeout {0} is not valid."},
{"R_invalidSocketTimeout", "The socketTimeout {0} is not valid."},
- {"R_fipsPropertyDescription", "Determines if enable FIPS compilant SSL connection between the client and the server."},
- {"R_invalidFipsConfig", "Could not enable FIPS."},
- {"R_invalidFipsEncryptConfig", "Could not enable FIPS due to either encrypt is not true or using trusted certificate settings."},
- {"R_invalidFipsProviderConfig", "Could not enable FIPS due to invalid FIPSProvider or TrustStoreType."},
+ {"R_fipsPropertyDescription", "Determines if FIPS mode is enabled."},
+ {"R_invalidFipsConfig", "Unable to verify FIPS mode settings."},
{"R_serverPreparedStatementDiscardThreshold", "The serverPreparedStatementDiscardThreshold {0} is not valid."},
{"R_statementPoolingCacheSize", "The statementPoolingCacheSize {0} is not valid."},
{"R_kerberosLoginFailedForUsername", "Cannot login with Kerberos principal {0}, check your credentials. {1}"},
@@ -386,9 +383,12 @@ protected Object[][] getContents() {
{"R_StoredProcedureNotFound", "Could not find stored procedure ''{0}''."},
{"R_jaasConfigurationNamePropertyDescription", "Login configuration file for Kerberos authentication."},
{"R_AKVKeyNotFound", "Key not found: {0}"},
- {"R_SQLVariantSupport", "SQL_VARIANT datatype is not supported in pre-SQL 2008 version."},
- {"R_invalidProbbytes", "SQL_VARIANT: invalid probBytes for {0} type."},
- {"R_invalidStringValue", "SQL_VARIANT does not support string values more than 8000 length."},
- {"R_invalidValueForTVPWithSQLVariant", "Inserting null value with column type sql_variant in TVP is not supported."},
+ {"R_SQLVariantSupport", "SQL_VARIANT is not supported in versions of SQL Server before 2008."},
+ {"R_invalidProbbytes", "SQL_VARIANT: invalid probBytes for {0} type."},
+ {"R_invalidStringValue", "SQL_VARIANT does not support string values of length greater than 8000."},
+ {"R_invalidValueForTVPWithSQLVariant", "Use of TVPs containing null sql_variant columns is not supported."},
+ {"R_invalidDataTypeSupportForSQLVariant", "Unexpected TDS type ' '{0}' ' in SQL_VARIANT."},
+ {"R_sslProtocolPropertyDescription", "SSL protocol label from TLS, TLSv1, TLSv1.1 & TLSv1.2. The default is TLS."},
+ {"R_invalidSSLProtocol", "SSL Protocol {0} label is not valid. Only TLS, TLSv1, TLSv1.1 & TLSv1.2 are supported."},
};
-}
+}
\ No newline at end of file
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
index 936e4727e4..e937b27c36 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
@@ -1796,8 +1796,7 @@ private void cancelInsert() {
/** Clear any updated column values for the current row in the result set. */
final void clearColumnsValues() {
int l = columns.length;
- for (int i = 0; i < l; i++)
- columns[i].cancelUpdates();
+ for (Column column : columns) column.cancelUpdates();
}
/* L0 */ public SQLWarning getWarnings() throws SQLServerException {
@@ -5684,14 +5683,14 @@ final boolean doExecute() throws SQLServerException {
// If no values were set for any columns and no columns are updatable,
// then the table name cannot be determined, so error.
Column tableColumn = null;
- for (int i = 0; i < columns.length; i++) {
- if (columns[i].hasUpdates()) {
- tableColumn = columns[i];
+ for (Column column : columns) {
+ if (column.hasUpdates()) {
+ tableColumn = column;
break;
}
- if (null == tableColumn && columns[i].isUpdatable())
- tableColumn = columns[i];
+ if (null == tableColumn && column.isUpdatable())
+ tableColumn = column;
}
if (null == tableColumn) {
@@ -5726,8 +5725,7 @@ private void doInsertRowRPC(TDSCommand command,
if (hasUpdatedColumns()) {
tdsWriter.writeRPCStringUnicode(tableName);
- for (int i = 0; i < columns.length; i++)
- columns[i].sendByRPC(tdsWriter, stmt.connection);
+ for (Column column : columns) column.sendByRPC(tdsWriter, stmt.connection);
}
else {
tdsWriter.writeRPCStringUnicode("");
@@ -5801,16 +5799,15 @@ private void doUpdateRowRPC(TDSCommand command) throws SQLServerException {
assert hasUpdatedColumns();
- for (int i = 0; i < columns.length; i++)
- columns[i].sendByRPC(tdsWriter, stmt.connection);
+ for (Column column : columns) column.sendByRPC(tdsWriter, stmt.connection);
TDSParser.parse(command.startResponse(), command.getLogContext());
}
/** Determines whether there are updated columns in this result set. */
final boolean hasUpdatedColumns() {
- for (int i = 0; i < columns.length; i++)
- if (columns[i].hasUpdates())
+ for (Column column : columns)
+ if (column.hasUpdates())
return true;
return false;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
index 632edf9e64..7f6d8e1d26 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
@@ -429,7 +429,7 @@ boolean onDone(TDSReader tdsReader) throws SQLServerException {
* The array of objects in a batched call. Applicable to statements and prepared statements When the iterativeBatching property is turned on.
*/
/** The buffer that accumulates batchable statements */
- private final ArrayList batchStatementBuffer = new ArrayList();
+ private final ArrayList batchStatementBuffer = new ArrayList<>();
/** logging init at the construction */
static final private java.util.logging.Logger stmtlogger = java.util.logging.Logger
@@ -1512,7 +1512,7 @@ boolean onInfo(TDSReader tdsReader) throws SQLServerException {
infoToken.msg.getErrorNumber());
if (sqlWarnings == null) {
- sqlWarnings = new Vector();
+ sqlWarnings = new Vector<>();
}
else {
int n = sqlWarnings.size();
@@ -2384,7 +2384,7 @@ int translateLimit(StringBuffer sql,
Matcher offsetMatcher = limitSyntaxWithOffset.matcher(sql);
int startIndx = indx;
- Stack topPosition = new Stack();
+ Stack topPosition = new Stack<>();
State nextState = State.START;
while (indx < sql.length()) {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
index 5799251d85..76b886786d 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
@@ -68,7 +68,7 @@ public Thread newThread(Runnable r) {
.getLogger("com.microsoft.sqlserver.jdbc.SQLServerSymmetricKeyCache");
private SQLServerSymmetricKeyCache() {
- cache = new ConcurrentHashMap();
+ cache = new ConcurrentHashMap<>();
}
static SQLServerSymmetricKeyCache getInstance() {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerXAResource.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerXAResource.java
index 60c710bcc1..8e72d0f35a 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerXAResource.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerXAResource.java
@@ -445,6 +445,7 @@ private String typeDisplay(int type) {
case XA_START:
if (!serverInfoRetrieved) {
+ Statement stmt = null;
try {
serverInfoRetrieved = true;
// data are converted to varchar as type variant returned by SERVERPROPERTY is not supported by driver
@@ -453,7 +454,7 @@ private String typeDisplay(int type) {
+ " convert(varchar(100), SERVERPROPERTY('ProductVersion')) as version,"
+ " SUBSTRING(@@VERSION, CHARINDEX('<', @@VERSION)+2, 2)";
- Statement stmt = controlConnection.createStatement();
+ stmt = controlConnection.createStatement();
ResultSet rs = stmt.executeQuery(query);
rs.next();
@@ -475,7 +476,6 @@ else if (-1 != version.indexOf('.')) {
ArchitectureOS = Integer.parseInt(rs.getString(4));
rs.close();
- stmt.close();
}
// Got caught in static analysis. Catch only the thrown exceptions, do not catch
// run time exceptions.
@@ -483,6 +483,16 @@ else if (-1 != version.indexOf('.')) {
if (xaLogger.isLoggable(Level.WARNING))
xaLogger.warning(toString() + " Cannot retrieve server information: :" + e.getMessage());
}
+ finally {
+ if (null != stmt)
+ try {
+ stmt.close();
+ }
+ catch (SQLException e) {
+ if (xaLogger.isLoggable(Level.FINER))
+ xaLogger.finer(toString());
+ }
+ }
}
sContext = "START:";
@@ -792,7 +802,7 @@ else if (-1 != version.indexOf('.')) {
/* L0 */ public Xid[] recover(int flags) throws XAException {
XAReturnValue r = DTC_XA_Interface(XA_RECOVER, null, flags | tightlyCoupled);
int offset = 0;
- ArrayList al = new ArrayList();
+ ArrayList al = new ArrayList<>();
// If no XID's found, return zero length XID array (don't return null).
//
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/StreamColInfo.java b/src/main/java/com/microsoft/sqlserver/jdbc/StreamColInfo.java
index a5fcc1b2ff..e0d7eaeb5c 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/StreamColInfo.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/StreamColInfo.java
@@ -36,9 +36,7 @@ int applyTo(Column[] columns) throws SQLServerException {
// Read and apply the column info for each column
TDSReaderMark currentMark = tdsReader.mark();
tdsReader.reset(colInfoMark);
- for (int i = 0; i < columns.length; i++) {
- Column col = columns[i];
-
+ for (Column col : columns) {
// Ignore the column number, per TDS spec.
// Column info is returned for each column, ascending by column index,
// so iterating through the column info is sufficient.
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/StreamTabName.java b/src/main/java/com/microsoft/sqlserver/jdbc/StreamTabName.java
index 1dc2a50851..6690990b1d 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/StreamTabName.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/StreamTabName.java
@@ -44,9 +44,7 @@ void applyTo(Column[] columns,
tableNames[i] = tdsReader.readSQLIdentifier();
// Apply the table names to their appropriate columns
- for (int i = 0; i < columns.length; i++) {
- Column col = columns[i];
-
+ for (Column col : columns) {
if (col.getTableNum() > 0)
col.setTableName(tableNames[col.getTableNum() - 1]);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java b/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
index 5113f1fc05..6f68d685a9 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
@@ -62,7 +62,7 @@ enum MPIState {
void initTVP(TVPType type,
String tvpPartName) throws SQLServerException {
tvpType = type;
- columnMetadata = new LinkedHashMap();
+ columnMetadata = new LinkedHashMap<>();
parseTypeName(tvpPartName);
}
@@ -157,9 +157,7 @@ void populateMetadataFromDataTable() throws SQLServerException {
if (null == dataTableMetaData || dataTableMetaData.isEmpty()) {
throw new SQLServerException(SQLServerException.getErrString("R_TVPEmptyMetadata"), null);
}
- Iterator> columnsIterator = dataTableMetaData.entrySet().iterator();
- while (columnsIterator.hasNext()) {
- Map.Entry pair = columnsIterator.next();
+ for (Entry pair : dataTableMetaData.entrySet()) {
// duplicate column names for the dataTable will be checked in the SQLServerDataTable.
columnMetadata.put(pair.getKey(),
new SQLServerMetaData(pair.getValue().columnName, pair.getValue().javaSqlType, pair.getValue().precision, pair.getValue().scale));
@@ -200,9 +198,7 @@ void validateOrderProperty() throws SQLServerException {
int maxSortOrdinal = -1;
int sortCount = 0;
- Iterator> columnsIterator = columnMetadata.entrySet().iterator();
- while (columnsIterator.hasNext()) {
- Map.Entry columnPair = columnsIterator.next();
+ for (Entry columnPair : columnMetadata.entrySet()) {
SQLServerSortOrder columnSortOrder = columnPair.getValue().sortOrder;
int columnSortOrdinal = columnPair.getValue().sortOrdinal;
@@ -210,13 +206,13 @@ void validateOrderProperty() throws SQLServerException {
// check if there's no way sort order could be monotonically increasing
if (columnCount <= columnSortOrdinal) {
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_TVPSortOrdinalGreaterThanFieldCount"));
- throw new SQLServerException(form.format(new Object[] {columnSortOrdinal, columnPair.getKey()}), null, 0, null);
+ throw new SQLServerException(form.format(new Object[]{columnSortOrdinal, columnPair.getKey()}), null, 0, null);
}
// Check to make sure we haven't seen this ordinal before
if (sortOrdinalSpecified[columnSortOrdinal]) {
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_TVPDuplicateSortOrdinal"));
- throw new SQLServerException(form.format(new Object[] {columnSortOrdinal}), null, 0, null);
+ throw new SQLServerException(form.format(new Object[]{columnSortOrdinal}), null, 0, null);
}
sortOrdinalSpecified[columnSortOrdinal] = true;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Util.java b/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
index d630d6e48a..db10ebce1e 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
@@ -626,8 +626,8 @@ static String byteToHexDisplayString(byte[] b) {
int hexVal;
StringBuilder sb = new StringBuilder(b.length * 2 + 2);
sb.append("0x");
- for (int i = 0; i < b.length; i++) {
- hexVal = b[i] & 0xFF;
+ for (byte aB : b) {
+ hexVal = aB & 0xFF;
sb.append(hexChars[(hexVal & 0xF0) >> 4]);
sb.append(hexChars[(hexVal & 0x0F)]);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/dns/DNSUtilities.java b/src/main/java/com/microsoft/sqlserver/jdbc/dns/DNSUtilities.java
index 3a91a3071e..483ad3635f 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/dns/DNSUtilities.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/dns/DNSUtilities.java
@@ -36,13 +36,13 @@ public class DNSUtilities {
* if DNS is not available
*/
public static Set findSrvRecords(final String dnsSrvRecordToFind) throws NamingException {
- Hashtable