diff --git a/CHANGELOG.md b/CHANGELOG.md
index 081cb8281e..4e736de77b 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -3,21 +3,6 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](http://keepachangelog.com/)
-## [7.1.3] Preview Release
-### Added
-- Added a new SQLServerMetaData constructor for string values of length greater than 4000 [#876](https://github.com/Microsoft/mssql-jdbc/pull/876)
-
-### Fixed Issues
-- Fixed an issue with Geography.point() having coordinates reversed [#853](https://github.com/Microsoft/mssql-jdbc/pull/853)
-- Fixed intermittent test failures [#854](https://github.com/Microsoft/mssql-jdbc/pull/854) [#862](https://github.com/Microsoft/mssql-jdbc/pull/862) [#888](https://github.com/Microsoft/mssql-jdbc/pull/888)
-- Fixed an issue with setAutoCommit() leaving a transaction open when running against Azure SQL Data Warehouse [#881](https://github.com/Microsoft/mssql-jdbc/pull/881)
-
-### Changed
-- Changed query timeout logic to use a single thread [#842](https://github.com/Microsoft/mssql-jdbc/pull/842)
-- Code cleanup [#857](https://github.com/Microsoft/mssql-jdbc/pull/857) [#873](https://github.com/Microsoft/mssql-jdbc/pull/873)
-- Removed populating Lobs when calling ResultSet.wasNull() [#875](https://github.com/Microsoft/mssql-jdbc/pull/875)
-- Improved retry logic for intermittent TLS1.2 issue when establishing a connection [#882](https://github.com/Microsoft/mssql-jdbc/pull/882)
-
## [7.1.2] Preview Release
### Added
- Added support for JDK 11 [#824](https://github.com/Microsoft/mssql-jdbc/pull/824) [#837](https://github.com/Microsoft/mssql-jdbc/pull/837) [#807](https://github.com/Microsoft/mssql-jdbc/pull/807)
@@ -72,7 +57,7 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/)
- Added new test for validation of supported public APIs in request boundary declaration APIs [#746](https://github.com/Microsoft/mssql-jdbc/pull/746)
### Fixed Issues
-- Fixed policheck issue with a keyword [#745](https://github.com/Microsoft/mssql-jdbc/pull/745)
+- Fixed policheck issue with 'Country' keyword [#745](https://github.com/Microsoft/mssql-jdbc/pull/745)
- Fixed issues reported by static analysis tools (SonarQube, Fortify) [#747](https://github.com/Microsoft/mssql-jdbc/pull/747)
### Changed
diff --git a/README.md b/README.md
index 8fb19d3f95..51c931dd59 100644
--- a/README.md
+++ b/README.md
@@ -18,7 +18,7 @@ SQL Server Team
Let us know how you think we're doing.
-
+
## Status of Most Recent Builds
| AppVeyor (Windows) | Travis CI (Linux) |
@@ -90,7 +90,7 @@ To get the latest preview version of the driver, add the following to your POM f
com.microsoft.sqlserver
mssql-jdbc
- 7.1.3.jre11-preview
+ 7.1.2.jre11-preview
```
@@ -123,7 +123,7 @@ Projects that require either of the two features need to explicitly declare the
com.microsoft.sqlserver
mssql-jdbc
- 7.1.3.jre11-preview
+ 7.1.2.jre11-preview
compile
@@ -140,7 +140,7 @@ Projects that require either of the two features need to explicitly declare the
com.microsoft.sqlserver
mssql-jdbc
- 7.1.3.jre11-preview
+ 7.1.2.jre11-preview
compile
diff --git a/appveyor.yml b/appveyor.yml
index 4f1c4577fd..3e70b718ba 100644
--- a/appveyor.yml
+++ b/appveyor.yml
@@ -4,7 +4,7 @@ init:
- cmd: net start MSSQL$%SQL_Instance%
environment:
- JAVA_HOME: C:\Program Files\Java\jdk11
+ JAVA_HOME: C:\Program Files\Java\jdk10
mssql_jdbc_test_connection_properties: jdbc:sqlserver://localhost:1433;instanceName=%SQL_Instance%;databaseName=master;username=sa;password=Password12!;
matrix:
- SQL_Instance: SQL2008R2SP2
@@ -31,9 +31,9 @@ cache:
build_script:
- keytool -importkeystore -srckeystore cert.pfx -srcstoretype pkcs12 -destkeystore clientcert.jks -deststoretype JKS -srcstorepass password -deststorepass password
- keytool -list -v -keystore clientcert.jks -storepass "password" > JavaKeyStore.txt
- - cd..
- - mvn install -DskipTests=true -Dmaven.javadoc.skip=true -B -V -Pbuild43
- - mvn install -DskipTests=true -Dmaven.javadoc.skip=true -B -V -Pbuild42
-test_script:
- - mvn test -B -Pbuild43
- - mvn test -B -Pbuild42
+# - cd..
+# - mvn install -DskipTests=true -Dmaven.javadoc.skip=true -B -V -Pbuild43
+# - mvn install -DskipTests=true -Dmaven.javadoc.skip=true -B -V -Pbuild42
+# test_script:
+# - mvn test -B -Pbuild43
+# - mvn test -B -Pbuild42
diff --git a/build.gradle b/build.gradle
index d084185a8c..0688b4aedf 100644
--- a/build.gradle
+++ b/build.gradle
@@ -10,7 +10,7 @@
apply plugin: 'java'
-version = '7.1.3'
+version = '7.1.2'
def jreVersion = ""
def testOutputDir = file("build/classes/java/test")
def archivesBaseName = 'mssql-jdbc'
diff --git a/pom.xml b/pom.xml
index 7b8e944adc..9505b50557 100644
--- a/pom.xml
+++ b/pom.xml
@@ -6,7 +6,7 @@
com.microsoft.sqlserver
mssql-jdbc
- 7.1.3
+ 7.1.2
jar
Microsoft JDBC Driver for SQL Server
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Column.java b/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
index fdd71facbf..20453b2b7a 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Column.java
@@ -214,7 +214,7 @@ void updateValue(JDBCType jdbcType, Object value, JavaType javaType, StreamSette
if (JDBCType.TINYINT == cryptoMetadata.getBaseTypeInfo().getSSType().getJDBCType()
&& javaType == JavaType.SHORT) {
if (value instanceof Boolean) {
- if ((boolean) value) {
+ if (true == ((boolean) value)) {
value = 1;
} else {
value = 0;
@@ -251,7 +251,7 @@ else if (jdbcType.isBinary()) {
}
if (Util.shouldHonorAEForParameters(stmtColumnEncriptionSetting, con)) {
- if ((null == cryptoMetadata) && forceEncrypt) {
+ if ((null == cryptoMetadata) && true == forceEncrypt) {
MessageFormat form = new MessageFormat(
SQLServerException.getErrString("R_ForceEncryptionTrue_HonorAETrue_UnencryptedColumnRS"));
Object[] msgArgs = {parameterIndex};
@@ -273,7 +273,7 @@ else if (jdbcType.isBinary()) {
}
}
} else {
- if (forceEncrypt) {
+ if (true == forceEncrypt) {
MessageFormat form = new MessageFormat(
SQLServerException.getErrString("R_ForceEncryptionTrue_HonorAEFalseRS"));
Object[] msgArgs = {parameterIndex};
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java b/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
index 7e18aec104..845fe5b900 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/DDC.java
@@ -596,14 +596,8 @@ static final Object convertStreamToObject(BaseInputStream stream, TypeInfo typeI
if (JDBCType.GUID == jdbcType) {
return Util.readGUID(byteValue);
} else if (JDBCType.GEOMETRY == jdbcType) {
- if (!typeInfo.getSSTypeName().equalsIgnoreCase(jdbcType.toString())) {
- DataTypes.throwConversionError(typeInfo.getSSTypeName().toUpperCase(), jdbcType.toString());
- }
return Geometry.STGeomFromWKB(byteValue);
} else if (JDBCType.GEOGRAPHY == jdbcType) {
- if (!typeInfo.getSSTypeName().equalsIgnoreCase(jdbcType.toString())) {
- DataTypes.throwConversionError(typeInfo.getSSTypeName().toUpperCase(), jdbcType.toString());
- }
return Geography.STGeomFromWKB(byteValue);
} else {
String hexString = Util.bytesToHexString(byteValue, byteValue.length);
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java b/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
index a5970e6dce..66f71bac98 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/DataTypes.java
@@ -606,7 +606,7 @@ else if (!sendStringParametersAsUnicode && fromJavaType == JavaType.BYTEARRAY
return false;
return setterConversionAEMap.get(fromJavaType).contains(toJDBCType);
}
- }
+ };
}
@@ -799,7 +799,7 @@ private SetterConversion(JDBCType.Category from, EnumSet to)
static boolean converts(JDBCType fromJDBCType, JDBCType toJDBCType) {
return conversionMap.get(fromJDBCType.category).contains(toJDBCType.category);
}
- }
+ };
boolean convertsTo(JDBCType jdbcType) {
return SetterConversion.converts(this, jdbcType);
@@ -898,7 +898,7 @@ private UpdaterConversion(JDBCType.Category from, EnumSet to) {
static boolean converts(JDBCType fromJDBCType, SSType toSSType) {
return conversionMap.get(fromJDBCType.category).contains(toSSType.category);
}
- }
+ };
boolean convertsTo(SSType ssType) {
return UpdaterConversion.converts(this, ssType);
@@ -1076,7 +1076,7 @@ private NormalizationAE(JDBCType from, EnumSet to) {
static boolean converts(JDBCType fromJDBCType, SSType toSSType) {
return normalizationMapAE.get(fromJDBCType).contains(toSSType);
}
- }
+ };
boolean normalizationCheck(SSType ssType) {
return NormalizationAE.converts(this, ssType);
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java b/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
index c87beb042e..c0936b09c0 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/FailOverMapSingleton.java
@@ -31,7 +31,7 @@ private static String concatPrimaryDatabase(String primary, String instance, Str
static FailoverInfo getFailoverInfo(SQLServerConnection connection, String primaryServer, String instance,
String database) {
synchronized (FailoverMapSingleton.class) {
- if (failoverMap.isEmpty()) {
+ if (true == failoverMap.isEmpty()) {
return null;
} else {
String mapKey = concatPrimaryDatabase(primaryServer, instance, database);
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Geography.java b/src/main/java/com/microsoft/sqlserver/jdbc/Geography.java
index c572ad70bd..d8dd00929f 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Geography.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Geography.java
@@ -140,7 +140,7 @@ public static Geography parse(String wkt) throws SQLServerException {
* if an exception occurs
*/
public static Geography point(double lat, double lon, int srid) throws SQLServerException {
- return new Geography("POINT (" + lon + " " + lat + ")", srid);
+ return new Geography("POINT (" + lat + " " + lon + ")", srid);
}
/**
@@ -212,8 +212,8 @@ public boolean hasZ() {
* @return double value that represents the latitude.
*/
public Double getLatitude() {
- if (null != internalType && internalType == InternalSpatialDatatype.POINT && yValues.length == 1) {
- return yValues[0];
+ if (null != internalType && internalType == InternalSpatialDatatype.POINT && xValues.length == 1) {
+ return xValues[0];
}
return null;
}
@@ -224,8 +224,8 @@ public Double getLatitude() {
* @return double value that represents the longitude.
*/
public Double getLongitude() {
- if (null != internalType && internalType == InternalSpatialDatatype.POINT && xValues.length == 1) {
- return xValues[0];
+ if (null != internalType && internalType == InternalSpatialDatatype.POINT && yValues.length == 1) {
+ return yValues[0];
}
return null;
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java b/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
index 056cf721ff..0cabb29360 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/IOBuffer.java
@@ -52,10 +52,15 @@
import java.util.Set;
import java.util.SimpleTimeZone;
import java.util.TimeZone;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
import java.util.concurrent.SynchronousQueue;
+import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;
+import java.util.concurrent.atomic.AtomicReference;
import java.util.logging.Level;
import java.util.logging.Logger;
@@ -1362,7 +1367,7 @@ private final class HostNameOverrideX509TrustManager implements X509TrustManager
this.logContext = tdsChannel.toString() + " (HostNameOverrideX509TrustManager):";
defaultTrustManager = tm;
// canonical name is in lower case so convert this to lowercase too.
- this.hostName = hostName.toLowerCase(Locale.ENGLISH);
+ this.hostName = hostName.toLowerCase(Locale.ENGLISH);;
}
// Parse name in RFC 2253 format
@@ -1537,7 +1542,7 @@ enum SSLHandhsakeState {
SSL_HANDHSAKE_NOT_STARTED,
SSL_HANDHSAKE_STARTED,
SSL_HANDHSAKE_COMPLETE
- }
+ };
/**
* Enables SSL Handshake.
@@ -1794,40 +1799,31 @@ else if (con.getTrustManagerClass() != null) {
+ tmfDefaultAlgorithm + "\n") : "")
+ ((null != ksProvider) ? ("KeyStore provider info: " + ksProvider.getInfo() + "\n") : "")
+ "java.ext.dirs: " + System.getProperty("java.ext.dirs"));
- // Retrieve the localized error message if possible.
- String localizedMessage = e.getLocalizedMessage();
- String errMsg = (localizedMessage != null) ? localizedMessage : e.getMessage();
- /*
- * Retrieve the error message of the cause too because actual error message can be wrapped into a different
- * message when re-thrown from underlying InputStream.
- */
- String causeErrMsg = null;
- Throwable cause = e.getCause();
- if (cause != null) {
- String causeLocalizedMessage = cause.getLocalizedMessage();
- causeErrMsg = (causeLocalizedMessage != null) ? causeLocalizedMessage : cause.getMessage();
- }
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_sslFailed"));
- Object[] msgArgs = {errMsg};
-
- /*
- * The error message may have a connection id appended to it. Extract the message only for comparison. This
- * client connection id is appended in method checkAndAppendClientConnId().
- */
- if (errMsg != null && errMsg.contains(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX)) {
- errMsg = errMsg.substring(0, errMsg.indexOf(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX));
+ Object[] msgArgs = {e.getMessage()};
+
+ // It is important to get the localized message here, otherwise error messages won't match for different
+ // locales.
+ String errMsg = e.getLocalizedMessage();
+ // If the message is null replace it with the non-localized message or a dummy string. This can happen if a
+ // custom
+ // TrustManager implementation is specified that does not provide localized messages.
+ if (errMsg == null) {
+ errMsg = e.getMessage();
}
-
- if (causeErrMsg != null && causeErrMsg.contains(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX)) {
- causeErrMsg = causeErrMsg.substring(0,
- causeErrMsg.indexOf(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX));
+ if (errMsg == null) {
+ errMsg = "";
+ }
+ // The error message may have a connection id appended to it. Extract the message only for comparison.
+ // This client connection id is appended in method checkAndAppendClientConnId().
+ if (errMsg.contains(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX)) {
+ errMsg = errMsg.substring(0, errMsg.indexOf(SQLServerException.LOG_CLIENT_CONNECTION_ID_PREFIX));
}
// Isolate the TLS1.2 intermittent connection error.
if (e instanceof IOException && (SSLHandhsakeState.SSL_HANDHSAKE_STARTED == handshakeState)
- && (SQLServerException.getErrString("R_truncatedServerResponse").equals(errMsg)
- || SQLServerException.getErrString("R_truncatedServerResponse").equals(causeErrMsg))) {
+ && (errMsg.equals(SQLServerException.getErrString("R_truncatedServerResponse")))) {
con.terminate(SQLServerException.DRIVER_ERROR_INTERMITTENT_TLS_FAILED, form.format(msgArgs), e);
} else {
con.terminate(SQLServerException.DRIVER_ERROR_SSL_FAILED, form.format(msgArgs), e);
@@ -2112,8 +2108,8 @@ final void close() {
//
// Note: the log formatter itself timestamps what we write so we don't have
// to do it again here.
- logMsg.append(tcpSocket.getLocalAddress().toString()).append(":").append(tcpSocket.getLocalPort())
- .append(" SPID:").append(spid).append(" ").append(messageDetail).append("\r\n");
+ logMsg.append(tcpSocket.getLocalAddress().toString() + ":" + tcpSocket.getLocalPort() + " SPID:" + spid + " "
+ + messageDetail + "\r\n");
// Fill in the body of the log message, line by line, 16 bytes per line.
int nBytesLogged = 0;
@@ -2299,7 +2295,7 @@ Socket findSocket(String hostName, int portNumber, int timeoutInMilliSeconds, bo
loggingString.append(". They are: ");
for (InetAddress inetAddr : inetAddrs) {
- loggingString.append(inetAddr.toString()).append(";");
+ loggingString.append(inetAddr.toString() + ";");
}
logger.finer(loggingString.toString());
@@ -2477,7 +2473,7 @@ private void findSocketUsingJavaNIO(InetAddress[] inetAddrs, int portNumber,
// ch.finishConnect should either return true or throw an exception
// as we have subscribed for OP_CONNECT.
- assert connected : "finishConnect on channel:" + ch + " cannot be false";
+ assert connected == true : "finishConnect on channel:" + ch + " cannot be false";
selectedChannel = ch;
@@ -6167,7 +6163,7 @@ final public String toString() {
final boolean isEOM() {
return TDS.STATUS_BIT_EOM == (header[TDS.PACKET_HEADER_MESSAGE_STATUS] & TDS.STATUS_BIT_EOM);
}
-}
+};
/**
@@ -6196,7 +6192,7 @@ final class TDSReaderMark {
final class TDSReader {
private final static Logger logger = Logger.getLogger("com.microsoft.sqlserver.jdbc.internals.TDS.Reader");
final private String traceID;
- private TimeoutCommand timeoutCommand;
+ private TimeoutTimer tcpKeepAliveTimeoutTimer;
final public String toString() {
return traceID;
@@ -6240,6 +6236,17 @@ private static int nextReaderID() {
this.tdsChannel = tdsChannel;
this.con = con;
this.command = command; // may be null
+ if (null != command) {
+ // if cancelQueryTimeout is set, we should wait for the total amount of queryTimeout + cancelQueryTimeout to
+ // terminate the connection.
+ this.tcpKeepAliveTimeoutTimer = (command.getCancelQueryTimeoutSeconds() > 0
+ && command.getQueryTimeoutSeconds() > 0)
+ ? (new TimeoutTimer(
+ command.getCancelQueryTimeoutSeconds()
+ + command.getQueryTimeoutSeconds(),
+ null, con))
+ : null;
+ }
// if the logging level is not detailed than fine or more we will not have proper reader IDs.
if (logger.isLoggable(Level.FINE))
traceID = "TDSReader@" + nextReaderID() + " (" + con.toString() + ")";
@@ -6344,16 +6351,11 @@ synchronized final boolean readPacket() throws SQLServerException {
+ " should be less than numMsgsSent:" + tdsChannel.numMsgsSent;
TDSPacket newPacket = new TDSPacket(con.getTDSPacketSize());
- if (null != command) {
- // if cancelQueryTimeout is set, we should wait for the total amount of
- // queryTimeout + cancelQueryTimeout to
- // terminate the connection.
- if ((command.getCancelQueryTimeoutSeconds() > 0 && command.getQueryTimeoutSeconds() > 0)) {
- // if a timeout is configured with this object, add it to the timeout poller
- int timeout = command.getCancelQueryTimeoutSeconds() + command.getQueryTimeoutSeconds();
- this.timeoutCommand = new TdsTimeoutCommand(timeout, this.command, this.con);
- TimeoutPoller.getTimeoutPoller().addTimeoutCommand(this.timeoutCommand);
+ if (null != tcpKeepAliveTimeoutTimer) {
+ if (logger.isLoggable(Level.FINEST)) {
+ logger.finest(this.toString() + ": starting timer...");
}
+ tcpKeepAliveTimeoutTimer.start();
}
// First, read the packet header.
for (int headerBytesRead = 0; headerBytesRead < TDS.PACKET_HEADER_SIZE;) {
@@ -6373,8 +6375,11 @@ synchronized final boolean readPacket() throws SQLServerException {
}
// if execution was subject to timeout then stop timing
- if (this.timeoutCommand != null) {
- TimeoutPoller.getTimeoutPoller().remove(this.timeoutCommand);
+ if (null != tcpKeepAliveTimeoutTimer) {
+ if (logger.isLoggable(Level.FINEST)) {
+ logger.finest(this.toString() + ":stopping timer...");
+ }
+ tcpKeepAliveTimeoutTimer.stop();
}
// Header size is a 2 byte unsigned short integer in big-endian order.
int packetLength = Util.readUnsignedShortBigEndian(newPacket.header, TDS.PACKET_HEADER_MESSAGE_LENGTH);
@@ -6964,25 +6969,82 @@ final void trySetSensitivityClassification(SensitivityClassification sensitivity
/**
- * The tds default implementation of a timeout command
+ * Timer for use with Commands that support a timeout.
+ *
+ * Once started, the timer runs for the prescribed number of seconds unless stopped. If the timer runs out, it
+ * interrupts its associated Command with a reason like "timed out".
*/
-class TdsTimeoutCommand extends TimeoutCommand {
- public TdsTimeoutCommand(int timeout, TDSCommand command, SQLServerConnection sqlServerConnection) {
- super(timeout, command, sqlServerConnection);
+final class TimeoutTimer implements Runnable {
+ private static final String threadGroupName = "mssql-jdbc-TimeoutTimer";
+ private final int timeoutSeconds;
+ private final TDSCommand command;
+ private volatile Future> task;
+ private final SQLServerConnection con;
+
+ private static final ExecutorService executor = Executors.newCachedThreadPool(new ThreadFactory() {
+ private final AtomicReference tgr = new AtomicReference<>();
+ private final AtomicInteger threadNumber = new AtomicInteger(0);
+
+ @Override
+ public Thread newThread(Runnable r) {
+ ThreadGroup tg = tgr.get();
+
+ if (tg == null || tg.isDestroyed()) {
+ tg = new ThreadGroup(threadGroupName);
+ tgr.set(tg);
+ }
+
+ Thread t = new Thread(tg, r, tg.getName() + "-" + threadNumber.incrementAndGet());
+ t.setDaemon(true);
+ return t;
+ }
+ });
+
+ private volatile boolean canceled = false;
+
+ TimeoutTimer(int timeoutSeconds, TDSCommand command, SQLServerConnection con) {
+ assert timeoutSeconds > 0;
+
+ this.timeoutSeconds = timeoutSeconds;
+ this.command = command;
+ this.con = con;
}
- public void interrupt() {
- TDSCommand command = getCommand();
- SQLServerConnection sqlServerConnection = getSqlServerConnection();
+ final void start() {
+ task = executor.submit(this);
+ }
+
+ final void stop() {
+ task.cancel(true);
+ canceled = true;
+ }
+
+ public void run() {
+ int secondsRemaining = timeoutSeconds;
try {
- // If TCP Connection to server is silently dropped, exceeding the query timeout
- // on the same connection does
+ // Poll every second while time is left on the timer.
+ // Return if/when the timer is canceled.
+ do {
+ if (canceled)
+ return;
+
+ Thread.sleep(1000);
+ } while (--secondsRemaining > 0);
+ } catch (InterruptedException e) {
+ // re-interrupt the current thread, in order to restore the thread's interrupt status.
+ Thread.currentThread().interrupt();
+ return;
+ }
+
+ // If the timer wasn't canceled before it ran out of
+ // time then interrupt the registered command.
+ try {
+ // If TCP Connection to server is silently dropped, exceeding the query timeout on the same connection does
// not throw SQLTimeoutException
- // The application stops responding instead until SocketTimeoutException is
- // thrown. In this case, we must
+ // The application stops responding instead until SocketTimeoutException is thrown. In this case, we must
// manually terminate the connection.
- if (null == command && null != sqlServerConnection) {
- sqlServerConnection.terminate(SQLServerException.DRIVER_ERROR_IO_FAILED,
+ if (null == command && null != con) {
+ con.terminate(SQLServerException.DRIVER_ERROR_IO_FAILED,
SQLServerException.getErrString("R_connectionIsClosed"));
} else {
// If the timer wasn't canceled before it ran out of
@@ -6999,6 +7061,7 @@ public void interrupt() {
}
}
+
/**
* TDSCommand encapsulates an interruptable TDS conversation.
*
@@ -7032,6 +7095,10 @@ final void log(Level level, String message) {
logger.log(level, toString() + ": " + message);
}
+ // Optional timer that is set if the command was created with a non-zero timeout period.
+ // When the timer expires, the command is interrupted.
+ private final TimeoutTimer timeoutTimer;
+
// TDS channel accessors
// These are set/reset at command execution time.
// Volatile ensures visibility to execution thread and interrupt thread
@@ -7120,7 +7187,6 @@ protected void setProcessedResponse(boolean processedResponse) {
private volatile boolean readingResponse;
private int queryTimeoutSeconds;
private int cancelQueryTimeoutSeconds;
- private TdsTimeoutCommand timeoutCommand;
protected int getQueryTimeoutSeconds() {
return this.queryTimeoutSeconds;
@@ -7147,6 +7213,7 @@ final boolean readingResponse() {
this.logContext = logContext;
this.queryTimeoutSeconds = queryTimeoutSeconds;
this.cancelQueryTimeoutSeconds = cancelQueryTimeoutSeconds;
+ this.timeoutTimer = (queryTimeoutSeconds > 0) ? (new TimeoutTimer(queryTimeoutSeconds, this, null)) : null;
}
/**
@@ -7535,9 +7602,11 @@ final TDSReader startResponse(boolean isAdaptive) throws SQLServerException {
// If command execution is subject to timeout then start timing until
// the server returns the first response packet.
- if (queryTimeoutSeconds > 0) {
- this.timeoutCommand = new TdsTimeoutCommand(queryTimeoutSeconds, this, null);
- TimeoutPoller.getTimeoutPoller().addTimeoutCommand(this.timeoutCommand);
+ if (null != timeoutTimer) {
+ if (logger.isLoggable(Level.FINEST))
+ logger.finest(this.toString() + ": Starting timer...");
+
+ timeoutTimer.start();
}
if (logger.isLoggable(Level.FINEST))
@@ -7560,8 +7629,11 @@ final TDSReader startResponse(boolean isAdaptive) throws SQLServerException {
} finally {
// If command execution was subject to timeout then stop timing as soon
// as the server returns the first response packet or errors out.
- if (this.timeoutCommand != null) {
- TimeoutPoller.getTimeoutPoller().remove(this.timeoutCommand);
+ if (null != timeoutTimer) {
+ if (logger.isLoggable(Level.FINEST))
+ logger.finest(this.toString() + ": Stopping timer...");
+
+ timeoutTimer.stop();
}
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java b/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
index 7e94fe9e4c..6e8e0a2daa 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Parameter.java
@@ -296,7 +296,7 @@ void setValue(JDBCType jdbcType, Object value, JavaType javaType, StreamSetterAr
}
// forceEncryption is true, shouldhonorae is false
- if (forceEncrypt && !Util.shouldHonorAEForParameters(stmtColumnEncriptionSetting, con)) {
+ if ((true == forceEncrypt) && (false == Util.shouldHonorAEForParameters(stmtColumnEncriptionSetting, con))) {
MessageFormat form = new MessageFormat(
SQLServerException.getErrString("R_ForceEncryptionTrue_HonorAEFalse"));
@@ -603,9 +603,10 @@ private void setTypeDefinition(DTV dtv) {
*/
if (userProvidesScale) {
- param.typeDefinition = SSType.TIME.toString() + "(" + outScale + ")";
+ param.typeDefinition = (SSType.TIME.toString() + "(" + outScale + ")");
} else {
- param.typeDefinition = SSType.TIME.toString() + "(" + valueLength + ")";
+ param.typeDefinition = param.typeDefinition = SSType.TIME.toString() + "(" + valueLength
+ + ")";
}
} else {
param.typeDefinition = con.getSendTimeAsDatetime() ? SSType.DATETIME.toString()
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
index 05c10cbe1a..de354b40e4 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLJdbcVersion.java
@@ -8,6 +8,6 @@
final class SQLJdbcVersion {
static final int major = 7;
static final int minor = 1;
- static final int patch = 3;
+ static final int patch = 2;
static final int build = 0;
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
index 2df1e090a5..068e400117 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerBulkCopy.java
@@ -224,7 +224,7 @@ class BulkColumnMetaData {
this.jdbcType = bulkColumnMetaData.jdbcType;
this.cryptoMeta = cryptoMeta;
}
- }
+ };
/**
* A map to store the metadata information for the destination table.
@@ -247,16 +247,56 @@ class BulkColumnMetaData {
private int srcColumnCount;
/**
- * Timeout for the bulk copy command
+ * Timer for the bulk copy operation. The other timeout timers in the TDS layer only measure the response of the
+ * first packet from SQL Server.
*/
- private final class BulkTimeoutCommand extends TimeoutCommand {
- public BulkTimeoutCommand(int timeout, TDSCommand command, SQLServerConnection sqlServerConnection) {
- super(timeout, command, sqlServerConnection);
+ private final class BulkTimeoutTimer implements Runnable {
+ private final int timeoutSeconds;
+ private int secondsRemaining;
+ private final TDSCommand command;
+ private Thread timerThread;
+ private volatile boolean canceled = false;
+
+ BulkTimeoutTimer(int timeoutSeconds, TDSCommand command) {
+ assert timeoutSeconds > 0;
+ assert null != command;
+
+ this.timeoutSeconds = timeoutSeconds;
+ this.secondsRemaining = timeoutSeconds;
+ this.command = command;
+ }
+
+ final void start() {
+ timerThread = new Thread(this);
+ timerThread.setDaemon(true);
+ timerThread.start();
+ }
+
+ final void stop() {
+ canceled = true;
+ timerThread.interrupt();
}
- @Override
- public void interrupt() {
- TDSCommand command = getCommand();
+ final boolean expired() {
+ return (secondsRemaining <= 0);
+ }
+
+ public void run() {
+ try {
+ // Poll every second while time is left on the timer.
+ // Return if/when the timer is canceled.
+ do {
+ if (canceled)
+ return;
+
+ Thread.sleep(1000);
+ } while (--secondsRemaining > 0);
+ } catch (InterruptedException e) {
+ // re-interrupt the current thread, in order to restore the thread's interrupt status.
+ Thread.currentThread().interrupt();
+ return;
+ }
+
// If the timer wasn't canceled before it ran out of
// time then interrupt the registered command.
try {
@@ -270,7 +310,7 @@ public void interrupt() {
}
}
- private BulkTimeoutCommand timeoutCommand;
+ private BulkTimeoutTimer timeoutTimer = null;
/**
* The maximum temporal precision we can send when using varchar(precision) in bulkcommand, to send a
@@ -647,15 +687,15 @@ final class InsertBulk extends TDSCommand {
InsertBulk() {
super("InsertBulk", 0, 0);
int timeoutSeconds = copyOptions.getBulkCopyTimeout();
- timeoutCommand = timeoutSeconds > 0 ? new BulkTimeoutCommand(timeoutSeconds, this, null) : null;
+ timeoutTimer = (timeoutSeconds > 0) ? (new BulkTimeoutTimer(timeoutSeconds, this)) : null;
}
final boolean doExecute() throws SQLServerException {
- if (null != timeoutCommand) {
+ if (null != timeoutTimer) {
if (logger.isLoggable(Level.FINEST))
logger.finest(this.toString() + ": Starting bulk timer...");
- TimeoutPoller.getTimeoutPoller().addTimeoutCommand(timeoutCommand);
+ timeoutTimer.start();
}
// doInsertBulk inserts the rows in one batch. It returns true if there are more rows in
@@ -672,18 +712,18 @@ final boolean doExecute() throws SQLServerException {
// Check whether it is a timeout exception.
if (rootCause instanceof SQLException) {
- checkForTimeoutException((SQLException) rootCause, timeoutCommand);
+ checkForTimeoutException((SQLException) rootCause, timeoutTimer);
}
// It is not a timeout exception. Re-throw.
throw topLevelException;
}
- if (null != timeoutCommand) {
+ if (null != timeoutTimer) {
if (logger.isLoggable(Level.FINEST))
logger.finest(this.toString() + ": Stopping bulk timer...");
- TimeoutPoller.getTimeoutPoller().remove(timeoutCommand);
+ timeoutTimer.stop();
}
return true;
@@ -730,7 +770,7 @@ private void writeColumnMetaDataColumnData(TDSWriter tdsWriter, int idx) throws
// the driver will not sent AE information, so, we need to set Encryption bit flag to 0.
if (null == srcColumnMetadata.get(srcColumnIndex).cryptoMeta
&& null == destColumnMetadata.get(destColumnIndex).cryptoMeta
- && copyOptions.isAllowEncryptedValueModifications()) {
+ && true == copyOptions.isAllowEncryptedValueModifications()) {
// flags[1]>>3 & 0x01 is the encryption bit flag.
// it is the 4th least significant bit in this byte, so minus 8 to set it to 0.
@@ -1148,9 +1188,9 @@ private void writeColumnMetaData(TDSWriter tdsWriter) throws SQLServerException
/**
* Helper method that throws a timeout exception if the cause of the exception was that the query was cancelled
*/
- private void checkForTimeoutException(SQLException e, BulkTimeoutCommand timeoutCommand) throws SQLServerException {
+ private void checkForTimeoutException(SQLException e, BulkTimeoutTimer timeoutTimer) throws SQLServerException {
if ((null != e.getSQLState()) && (e.getSQLState().equals(SQLState.STATEMENT_CANCELED.getSQLStateCode()))
- && timeoutCommand.canTimeout()) {
+ && timeoutTimer.expired()) {
// If SQLServerBulkCopy is managing the transaction, a rollback is needed.
if (copyOptions.isUseInternalTransaction()) {
connection.rollback();
@@ -1410,7 +1450,7 @@ private String createInsertBulkCommand(TDSWriter tdsWriter) throws SQLServerExce
StringBuilder bulkCmd = new StringBuilder();
List bulkOptions = new ArrayList<>();
String endColumn = " , ";
- bulkCmd.append("INSERT BULK ").append(destinationTableName).append(" (");
+ bulkCmd.append("INSERT BULK " + destinationTableName + " (");
for (int i = 0; i < (columnMappings.size()); ++i) {
if (i == columnMappings.size() - 1) {
@@ -1431,23 +1471,21 @@ private String createInsertBulkCommand(TDSWriter tdsWriter) throws SQLServerExce
}
if (colMapping.destinationColumnName.contains("]")) {
String escapedColumnName = colMapping.destinationColumnName.replaceAll("]", "]]");
- bulkCmd.append("[").append(escapedColumnName).append("] ").append(destType).append(addCollate)
- .append(endColumn);
+ bulkCmd.append("[" + escapedColumnName + "] " + destType + addCollate + endColumn);
} else {
- bulkCmd.append("[").append(colMapping.destinationColumnName).append("] ").append(destType)
- .append(addCollate).append(endColumn);
+ bulkCmd.append("[" + colMapping.destinationColumnName + "] " + destType + addCollate + endColumn);
}
}
- if (copyOptions.isCheckConstraints()) {
+ if (true == copyOptions.isCheckConstraints()) {
bulkOptions.add("CHECK_CONSTRAINTS");
}
- if (copyOptions.isFireTriggers()) {
+ if (true == copyOptions.isFireTriggers()) {
bulkOptions.add("FIRE_TRIGGERS");
}
- if (copyOptions.isKeepNulls()) {
+ if (true == copyOptions.isKeepNulls()) {
bulkOptions.add("KEEP_NULLS");
}
@@ -1455,11 +1493,11 @@ private String createInsertBulkCommand(TDSWriter tdsWriter) throws SQLServerExce
bulkOptions.add("ROWS_PER_BATCH = " + copyOptions.getBatchSize());
}
- if (copyOptions.isTableLock()) {
+ if (true == copyOptions.isTableLock()) {
bulkOptions.add("TABLOCK");
}
- if (copyOptions.isAllowEncryptedValueModifications()) {
+ if (true == copyOptions.isAllowEncryptedValueModifications()) {
bulkOptions.add("ALLOW_ENCRYPTED_VALUE_MODIFICATIONS");
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
index 92355d90fe..0ba3f48d30 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerConnection.java
@@ -1324,7 +1324,7 @@ Connection connectInternal(Properties propsIn,
}
trustedServerNameAE = sPropValue;
- if (serverNameAsACE) {
+ if (true == serverNameAsACE) {
try {
sPropValue = java.net.IDN.toASCII(sPropValue);
} catch (IllegalArgumentException ex) {
@@ -1529,8 +1529,8 @@ Connection connectInternal(Properties propsIn,
}
authenticationString = SqlAuthentication.valueOfString(sPropValue).toString();
- if (integratedSecurity
- && !authenticationString.equalsIgnoreCase(SqlAuthentication.NotSpecified.toString())) {
+ if ((true == integratedSecurity)
+ && (!authenticationString.equalsIgnoreCase(SqlAuthentication.NotSpecified.toString()))) {
if (connectionlogger.isLoggable(Level.SEVERE)) {
connectionlogger.severe(toString() + " "
+ SQLServerException.getErrString("R_SetAuthenticationWhenIntegratedSecurityTrue"));
@@ -1591,7 +1591,7 @@ Connection connectInternal(Properties propsIn,
throw new SQLServerException(SQLServerException.getErrString("R_AccessTokenCannotBeEmpty"), null);
}
- if (integratedSecurity && (null != accessTokenInByte)) {
+ if ((true == integratedSecurity) && (null != accessTokenInByte)) {
if (connectionlogger.isLoggable(Level.SEVERE)) {
connectionlogger.severe(toString() + " "
+ SQLServerException.getErrString("R_SetAccesstokenWhenIntegratedSecurityTrue"));
@@ -2983,7 +2983,7 @@ String sqlStatementToSetTransactionIsolationLevel() throws SQLServerException {
* @return the required syntax
*/
static String sqlStatementToSetCommit(boolean autoCommit) {
- return autoCommit ? "set implicit_transactions off " : "set implicit_transactions on ";
+ return (true == autoCommit) ? "set implicit_transactions off " : "set implicit_transactions on ";
}
@Override
@@ -3033,7 +3033,7 @@ public void setAutoCommit(boolean newAutoCommitMode) throws SQLServerException {
// When changing to auto-commit from inside an existing transaction,
// commit that transaction first.
- if (newAutoCommitMode)
+ if (newAutoCommitMode == true)
commitPendingTransaction = "IF @@TRANCOUNT > 0 COMMIT TRAN ";
if (connectionlogger.isLoggable(Level.FINER)) {
@@ -3042,7 +3042,7 @@ public void setAutoCommit(boolean newAutoCommitMode) throws SQLServerException {
}
rolledBackTransaction = false;
- connectionCommand(sqlStatementToSetCommit(newAutoCommitMode) + commitPendingTransaction, "setAutoCommit");
+ connectionCommand(commitPendingTransaction + sqlStatementToSetCommit(newAutoCommitMode), "setAutoCommit");
databaseAutoCommitMode = newAutoCommitMode;
loggerExternal.exiting(getClassNameLogging(), "setAutoCommit");
}
@@ -3457,11 +3457,11 @@ int writeFedAuthFeatureRequest(boolean write, TDSWriter tdsWriter,
// set upper 7 bits of options to indicate fed auth library type
switch (fedAuthFeatureExtensionData.libraryType) {
case TDS.TDS_FEDAUTH_LIBRARY_ADAL:
- assert federatedAuthenticationInfoRequested;
+ assert federatedAuthenticationInfoRequested == true;
options |= TDS.TDS_FEDAUTH_LIBRARY_ADAL << 1;
break;
case TDS.TDS_FEDAUTH_LIBRARY_SECURITYTOKEN:
- assert federatedAuthenticationRequested;
+ assert federatedAuthenticationRequested == true;
options |= TDS.TDS_FEDAUTH_LIBRARY_SECURITYTOKEN << 1;
break;
default:
@@ -3469,7 +3469,7 @@ int writeFedAuthFeatureRequest(boolean write, TDSWriter tdsWriter,
break;
}
- options |= (byte) (fedAuthFeatureExtensionData.fedAuthRequiredPreLoginResponse ? 0x01 : 0x00);
+ options |= (byte) (fedAuthFeatureExtensionData.fedAuthRequiredPreLoginResponse == true ? 0x01 : 0x00);
// write FeatureDataLen
tdsWriter.writeInt(dataLen);
@@ -4279,7 +4279,7 @@ private void onFeatureExtAck(byte featureId, byte[] data) throws SQLServerExcept
}
byte enabled = data[1];
- serverSupportsDataClassification = enabled != 0;
+ serverSupportsDataClassification = (enabled == 0) ? false : true;
}
case TDS.TDS_FEATURE_EXT_UTF8SUPPORT: {
if (connectionlogger.isLoggable(Level.FINER)) {
@@ -4977,7 +4977,7 @@ public void releaseSavepoint(Savepoint savepoint) throws SQLException {
}
final private Savepoint setNamedSavepoint(String sName) throws SQLServerException {
- if (databaseAutoCommitMode) {
+ if (true == databaseAutoCommitMode) {
SQLServerException.makeFromDriverError(this, this, SQLServerException.getErrString("R_cantSetSavepoint"),
null, false);
}
@@ -5028,7 +5028,7 @@ public void rollback(Savepoint s) throws SQLServerException {
loggerExternal.finer(toString() + " ActivityId: " + ActivityCorrelator.getNext().toString());
}
checkClosed();
- if (databaseAutoCommitMode) {
+ if (true == databaseAutoCommitMode) {
SQLServerException.makeFromDriverError(this, this, SQLServerException.getErrString("R_cantInvokeRollback"),
null, false);
}
@@ -5971,7 +5971,7 @@ public void onEviction(CityHash128Key key, PreparedStatementHandle handle) {
boolean isAzureDW() throws SQLServerException, SQLException {
if (null == isAzureDW) {
try (Statement stmt = this.createStatement();
- ResultSet rs = stmt.executeQuery("SELECT CAST(SERVERPROPERTY('EngineEdition') as INT)")) {
+ ResultSet rs = stmt.executeQuery("SELECT CAST(SERVERPROPERTY('EngineEdition') as INT)");) {
// SERVERPROPERTY('EngineEdition') can be used to determine whether the db server is SQL Azure.
// It should return 6 for SQL Azure DW. This is more reliable than @@version or
// serverproperty('edition').
@@ -5988,7 +5988,7 @@ boolean isAzureDW() throws SQLServerException, SQLException {
// Base data type: int
final int ENGINE_EDITION_FOR_SQL_AZURE_DW = 6;
rs.next();
- isAzureDW = rs.getInt(1) == ENGINE_EDITION_FOR_SQL_AZURE_DW;
+ isAzureDW = (rs.getInt(1) == ENGINE_EDITION_FOR_SQL_AZURE_DW) ? true : false;
}
return isAzureDW;
} else {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
index e20b0a8e87..a0b32b32e8 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDataSource.java
@@ -1090,7 +1090,7 @@ Reference getReferenceInternal(String dataSourceClassString) {
if (propertyName.equals(SQLServerDriverStringProperty.TRUST_STORE_PASSWORD.toString())) {
// The property set and the variable set at the same time is not
// possible
- assert !trustStorePasswordStripped;
+ assert trustStorePasswordStripped == false;
ref.add(new StringRefAddr("trustStorePasswordStripped", "true"));
} else {
// do not add passwords to the collection. we have normal
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
index 51132018f7..91592c78b5 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerDatabaseMetaData.java
@@ -521,16 +521,17 @@ public java.sql.ResultSet getTables(String catalog, String schema, String table,
arguments[1] = schema;
arguments[2] = catalog;
+ String tableTypes = null;
if (types != null) {
- final StringBuilder tableTypes = new StringBuilder("'");
+ tableTypes = "'";
for (int i = 0; i < types.length; i++) {
if (i > 0)
- tableTypes.append(",");
- tableTypes.append("''").append(types[i]).append("''");
+ tableTypes += ",";
+ tableTypes += "''" + types[i] + "''";
}
- tableTypes.append("'");
- arguments[3] = tableTypes.toString();
+ tableTypes += "'";
}
+ arguments[3] = tableTypes;
return getResultSetWithProvidedColumnNames(catalog, CallableHandles.SP_TABLES, arguments, getTablesColumnNames);
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
index bdea428d6d..be19694f5e 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerException.java
@@ -118,7 +118,7 @@ private void logException(Object o, String errText, boolean bStack) {
sb.append(aSt.toString());
Throwable t = this.getCause();
if (t != null) {
- sb.append("\n caused by ").append(t).append("\n");
+ sb.append("\n caused by " + t + "\n");
StackTraceElement tst[] = t.getStackTrace();
for (StackTraceElement aTst : tst)
sb.append(aTst.toString());
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerMetaData.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerMetaData.java
index dfb43f7568..da9db54b7e 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerMetaData.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerMetaData.java
@@ -60,23 +60,6 @@ public SQLServerMetaData(String columnName, int sqlType, int precision, int scal
this.scale = scale;
}
- /**
- * Constructs a SQLServerMetaData with the column name, SQL type, and length (for String data).
- * The length is used to differentiate large strings from strings with length less than 4000 characters.
- *
- * @param columnName
- * the name of the column
- * @param sqlType
- * the SQL type of the column
- * @param length
- * the length of the string type
- */
- public SQLServerMetaData(String columnName, int sqlType, int length) {
- this.columnName = columnName;
- this.javaSqlType = sqlType;
- this.precision = length;
- }
-
/**
* Constructs a SQLServerMetaData.
*
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
index c2bea2755e..8ce79e106b 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerParameterMetaData.java
@@ -645,7 +645,7 @@ private void checkClosed() throws SQLServerException {
StringBuilder sbColumns = new StringBuilder();
for (MetaInfo mi : metaInfoList) {
- sbColumns = sbColumns.append(mi.fields).append(",");
+ sbColumns = sbColumns.append(mi.fields + ",");
}
sbColumns.deleteCharAt(sbColumns.length() - 1);
@@ -660,10 +660,9 @@ private void checkClosed() throws SQLServerException {
&& metaInfoList.get(i).fields.equals(metaInfoList.get(i - 1).fields)) {
continue;
}
- sbTablesAndJoins = sbTablesAndJoins.append(" LEFT JOIN ").append(metaInfoList.get(i).table)
- .append(" ON ").append(metaInfoList.get(i - 1).table).append(".")
- .append(metaInfoList.get(i - 1).fields).append("=")
- .append(metaInfoList.get(i).table).append(".").append(metaInfoList.get(i).fields);
+ sbTablesAndJoins = sbTablesAndJoins.append(" LEFT JOIN " + metaInfoList.get(i).table
+ + " ON " + metaInfoList.get(i - 1).table + "." + metaInfoList.get(i - 1).fields
+ + "=" + metaInfoList.get(i).table + "." + metaInfoList.get(i).fields);
}
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
index fea6c22e36..41844f8134 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerPreparedStatement.java
@@ -925,7 +925,7 @@ private void getParameterEncryptionMetadata(Parameter[] params) throws SQLServer
// Decrypt the symmetric key.(This will also validate and throw if needed).
SQLServerSecurityUtility.decryptSymmetricKey(params[paramIndex].cryptoMeta, connection);
} else {
- if (params[paramIndex].getForceEncryption()) {
+ if (true == params[paramIndex].getForceEncryption()) {
MessageFormat form = new MessageFormat(
SQLServerException.getErrString("R_ForceEncryptionTrue_HonorAETrue_UnencryptedColumn"));
Object[] msgArgs = {userSQL, paramIndex + 1};
@@ -1081,7 +1081,7 @@ private ResultSet buildExecuteMetaData() throws SQLServerException {
internalStmt = (SQLServerStatement) connection.createStatement();
emptyResultSet = internalStmt.executeQueryInternal("set fmtonly on " + fmtSQL + "\nset fmtonly off");
} catch (SQLException sqle) {
- if (!sqle.getMessage().equals(SQLServerException.getErrString("R_noResultset"))) {
+ if (false == sqle.getMessage().equals(SQLServerException.getErrString("R_noResultset"))) {
// if the error is not no resultset then throw a processings error.
MessageFormat form = new MessageFormat(SQLServerException.getErrString("R_processingError"));
Object[] msgArgs = {sqle.getMessage()};
@@ -1972,7 +1972,7 @@ public int[] executeBatch() throws SQLServerException, BatchUpdateException, SQL
stmtColumnEncriptionSetting);
SQLServerResultSet rs = stmt
.executeQueryInternal("sp_executesql N'SET FMTONLY ON SELECT * FROM "
- + Util.escapeSingleQuotes(tableName) + " '")) {
+ + Util.escapeSingleQuotes(tableName) + " '");) {
if (null != columnList && columnList.size() > 0) {
if (columnList.size() != valueList.size()) {
throw new IllegalArgumentException(
@@ -2129,7 +2129,7 @@ public long[] executeLargeBatch() throws SQLServerException, BatchUpdateExceptio
stmtColumnEncriptionSetting);
SQLServerResultSet rs = stmt
.executeQueryInternal("sp_executesql N'SET FMTONLY ON SELECT * FROM "
- + Util.escapeSingleQuotes(tableName) + " '")) {
+ + Util.escapeSingleQuotes(tableName) + " '");) {
if (null != columnList && columnList.size() > 0) {
if (columnList.size() != valueList.size()) {
throw new IllegalArgumentException(
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
index 8a6e3391c9..e163219e80 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerResultSet.java
@@ -1072,6 +1072,7 @@ public boolean next() throws SQLServerException {
public boolean wasNull() throws SQLServerException {
loggerExternal.entering(getClassNameLogging(), "wasNull");
checkClosed();
+ fillLOBs();
loggerExternal.exiting(getClassNameLogging(), "wasNull", lastValueWasNull);
return lastValueWasNull;
}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
index 7f166b0723..d0ae5e25b5 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerStatement.java
@@ -1012,28 +1012,29 @@ static String replaceParameterWithString(String str, char marker, String replace
*/
static String replaceMarkerWithNull(String sql) {
if (!sql.contains("'")) {
- return replaceParameterWithString(sql, '?', "null");
+ String retStr = replaceParameterWithString(sql, '?', "null");
+ return retStr;
} else {
StringTokenizer st = new StringTokenizer(sql, "'", true);
boolean beforeColon = true;
- final StringBuilder retSql = new StringBuilder();
+ String retSql = "";
while (st.hasMoreTokens()) {
String str = st.nextToken();
if (str.equals("'")) {
- retSql.append("'");
+ retSql += "'";
beforeColon = !beforeColon;
continue;
}
if (beforeColon) {
String repStr = replaceParameterWithString(str, '?', "null");
- retSql.append(repStr);
+ retSql += repStr;
continue;
} else {
- retSql.append(str);
+ retSql += str;
continue;
}
}
- return retSql.toString();
+ return retSql;
}
}
@@ -2411,7 +2412,7 @@ enum State {
OFFSET,
QUOTE,
PROCESS
- }
+ };
// This pattern matches the LIMIT syntax with an OFFSET clause. The driver does not support OFFSET expression in the
// LIMIT clause.
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
index bebb43e98b..80eb9a03ae 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SQLServerSymmetricKeyCache.java
@@ -14,7 +14,7 @@
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
-import java.util.concurrent.ThreadFactory;
+import java.util.concurrent.ThreadFactory;;
class CacheClear implements Runnable {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/SimpleInputStream.java b/src/main/java/com/microsoft/sqlserver/jdbc/SimpleInputStream.java
index 4586ef3895..fa22c96ca4 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/SimpleInputStream.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/SimpleInputStream.java
@@ -37,7 +37,7 @@ private static int nextLoggingID() {
}
static final java.util.logging.Logger logger = java.util.logging.Logger
- .getLogger("com.microsoft.sqlserver.jdbc.internals.InputStream");
+ .getLogger("com.microsoft.sqlserver.jdbc.internals.InputStream");;
private String traceID;
final public String toString() {
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java b/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
index abe9fe097e..92bf03d6c1 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/TVP.java
@@ -63,7 +63,7 @@ enum MPIState {
MPI_LookForNextCharOrSeparator,
MPI_ParseQuote,
MPI_RightQuote,
- }
+ };
void initTVP(TVPType type, String tvpPartName) throws SQLServerException {
tvpType = type;
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutCommand.java b/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutCommand.java
deleted file mode 100644
index 65b1f68b26..0000000000
--- a/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutCommand.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Microsoft JDBC Driver for SQL Server Copyright(c) Microsoft Corporation All rights reserved. This program is made
- * available under the terms of the MIT License. See the LICENSE file in the project root for more information.
- */
-
-package com.microsoft.sqlserver.jdbc;
-
-/**
- * Abstract implementation of a command that can be timed out using the {@link TimeoutPoller}
- */
-abstract class TimeoutCommand {
- private final long startTime;
- private final int timeout;
- private final T command;
- private final SQLServerConnection sqlServerConnection;
-
- TimeoutCommand(int timeout, T command, SQLServerConnection sqlServerConnection) {
- this.timeout = timeout;
- this.command = command;
- this.sqlServerConnection = sqlServerConnection;
- this.startTime = System.currentTimeMillis();
- }
-
- public boolean canTimeout() {
- long currentTime = System.currentTimeMillis();
- return ((currentTime - startTime) / 1000) >= timeout;
- }
-
- public T getCommand() {
- return command;
- }
-
- public SQLServerConnection getSqlServerConnection() {
- return sqlServerConnection;
- }
-
- /**
- * The implementation for interrupting this timeout command
- */
- public abstract void interrupt();
-}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutPoller.java b/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutPoller.java
deleted file mode 100644
index 6c53d4d744..0000000000
--- a/src/main/java/com/microsoft/sqlserver/jdbc/TimeoutPoller.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Microsoft JDBC Driver for SQL Server Copyright(c) Microsoft Corporation All rights reserved. This program is made
- * available under the terms of the MIT License. See the LICENSE file in the project root for more information.
- */
-
-package com.microsoft.sqlserver.jdbc;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.logging.Level;
-import java.util.logging.Logger;
-
-
-/**
- * Thread that runs in the background while the mssql driver is used that can timeout TDSCommands Checks all registered
- * commands every second to see if they can be interrupted
- */
-final class TimeoutPoller implements Runnable {
- private List> timeoutCommands = new ArrayList<>();
- final static Logger logger = Logger.getLogger("com.microsoft.sqlserver.jdbc.TimeoutPoller");
- private static volatile TimeoutPoller timeoutPoller = null;
-
- static TimeoutPoller getTimeoutPoller() {
- if (timeoutPoller == null) {
- synchronized (TimeoutPoller.class) {
- if (timeoutPoller == null) {
- // initialize the timeout poller thread once
- timeoutPoller = new TimeoutPoller();
- // start the timeout polling thread
- Thread pollerThread = new Thread(timeoutPoller, "mssql-jdbc-TimeoutPoller");
- pollerThread.setDaemon(true);
- pollerThread.start();
- }
- }
- }
- return timeoutPoller;
- }
-
- void addTimeoutCommand(TimeoutCommand timeoutCommand) {
- synchronized (timeoutCommands) {
- timeoutCommands.add(timeoutCommand);
- }
- }
-
- void remove(TimeoutCommand timeoutCommand) {
- synchronized (timeoutCommands) {
- timeoutCommands.remove(timeoutCommand);
- }
- }
-
- private TimeoutPoller() {}
-
- public void run() {
- try {
- // Poll every second checking for commands that have timed out and need
- // interruption
- while (true) {
- synchronized (timeoutCommands) {
- Iterator> timeoutCommandIterator = timeoutCommands.iterator();
- while (timeoutCommandIterator.hasNext()) {
- TimeoutCommand timeoutCommand = timeoutCommandIterator.next();
- try {
- if (timeoutCommand.canTimeout()) {
- try {
- timeoutCommand.interrupt();
- } finally {
- timeoutCommandIterator.remove();
- }
- }
- } catch (Exception e) {
- logger.log(Level.WARNING, "Could not timeout command", e);
- }
- }
- }
- Thread.sleep(1000);
- }
- } catch (Exception e) {
- logger.log(Level.SEVERE, "Error processing timeout commands", e);
- }
- }
-}
diff --git a/src/main/java/com/microsoft/sqlserver/jdbc/Util.java b/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
index 76617d31a0..087c2408b6 100644
--- a/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
+++ b/src/main/java/com/microsoft/sqlserver/jdbc/Util.java
@@ -380,7 +380,7 @@ else if (ch == ':')
name = SQLServerDriver.getNormalizedPropertyName(name, logger);
if (null != name) {
if (logger.isLoggable(Level.FINE)) {
- if (!name.equals(SQLServerDriverStringProperty.USER.toString())) {
+ if (false == name.equals(SQLServerDriverStringProperty.USER.toString())) {
if (!name.toLowerCase(Locale.ENGLISH).contains("password")
&& !name.toLowerCase(Locale.ENGLISH).contains("keystoresecret")) {
logger.fine("Property:" + name + " Value:" + value);
@@ -417,8 +417,8 @@ else if (ch == ':')
name = SQLServerDriver.getNormalizedPropertyName(name, logger);
if (null != name) {
if (logger.isLoggable(Level.FINE)) {
- if (!name.equals(SQLServerDriverStringProperty.USER.toString())
- && !name.equals(SQLServerDriverStringProperty.PASSWORD.toString()))
+ if ((false == name.equals(SQLServerDriverStringProperty.USER.toString()))
+ && (false == name.equals(SQLServerDriverStringProperty.PASSWORD.toString())))
logger.fine("Property:" + name + " Value:" + value);
}
p.put(name, value);
@@ -487,9 +487,9 @@ else if (ch == ':')
name = SQLServerDriver.getNormalizedPropertyName(name, logger);
if (null != name) {
if (logger.isLoggable(Level.FINE)) {
- if (!name.equals(SQLServerDriverStringProperty.USER.toString())
- && !name.equals(SQLServerDriverStringProperty.PASSWORD.toString())
- && !name.equals(SQLServerDriverStringProperty.KEY_STORE_SECRET.toString()))
+ if ((false == name.equals(SQLServerDriverStringProperty.USER.toString()))
+ && (false == name.equals(SQLServerDriverStringProperty.PASSWORD.toString()))
+ && (false == name.equals(SQLServerDriverStringProperty.KEY_STORE_SECRET.toString())))
logger.fine("Property:" + name + " Value:" + value);
}
p.put(name, value);
@@ -1044,19 +1044,19 @@ final String asEscapedString() {
StringBuilder fullName = new StringBuilder(256);
if (serverName.length() > 0)
- fullName.append("[").append(serverName).append("].");
+ fullName.append("[" + serverName + "].");
if (databaseName.length() > 0)
- fullName.append("[").append(databaseName).append("].");
+ fullName.append("[" + databaseName + "].");
else
assert 0 == serverName.length();
if (schemaName.length() > 0)
- fullName.append("[").append(schemaName).append("].");
+ fullName.append("[" + schemaName + "].");
else if (databaseName.length() > 0)
fullName.append('.');
- fullName.append("[").append(objectName).append("]");
+ fullName.append("[" + objectName + "]");
return fullName.toString();
}
diff --git a/src/samples/datatypes/src/main/java/SpatialDataTypes.java b/src/samples/datatypes/src/main/java/SpatialDataTypes.java
index 8a3d145fea..6a7aae6dc1 100644
--- a/src/samples/datatypes/src/main/java/SpatialDataTypes.java
+++ b/src/samples/datatypes/src/main/java/SpatialDataTypes.java
@@ -58,6 +58,7 @@ public static void main(String[] args) {
try (Connection con = ds.getConnection(); Statement stmt = con.createStatement();) {
dropAndCreateTable(stmt);
+ // TODO: Implement Sample code
String geoWKT = "POINT(3 40 5 6)";
Geometry geomWKT = Geometry.STGeomFromText(geoWKT, 0);
Geography geogWKT = Geography.STGeomFromText(geoWKT, 4326);
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyColumnMappingTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyColumnMappingTest.java
index e6b96f1833..0da47193c0 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyColumnMappingTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyColumnMappingTest.java
@@ -5,7 +5,6 @@
package com.microsoft.sqlserver.jdbc.bulkCopy;
import static org.junit.jupiter.api.Assertions.fail;
-import static org.junit.jupiter.api.Assertions.assertTrue;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
@@ -22,7 +21,6 @@
import com.microsoft.sqlserver.jdbc.ComparisonUtil;
import com.microsoft.sqlserver.jdbc.TestResource;
-import com.microsoft.sqlserver.jdbc.TestUtils;
import com.microsoft.sqlserver.testframework.DBConnection;
import com.microsoft.sqlserver.testframework.DBResultSet;
import com.microsoft.sqlserver.testframework.DBStatement;
@@ -387,10 +385,10 @@ private void validateValuesRepetitiveCM(DBConnection con, DBTable sourceTable,
int totalColumns = sourceMeta.getColumnCount();
// verify data from sourceType and resultSet
- int numRows = 0;
while (srcResultSet.next() && dstResultSet.next()) {
- numRows++;
for (int i = 1; i <= totalColumns; i++) {
+ // TODO: check row and column count in both the tables
+
Object srcValue, dstValue;
srcValue = srcResultSet.getObject(i);
dstValue = dstResultSet.getObject(i);
@@ -405,11 +403,6 @@ private void validateValuesRepetitiveCM(DBConnection con, DBTable sourceTable,
}
}
}
-
- // verify number of rows and columns
- assertTrue(((ResultSet) dstResultSet.product()).getMetaData().getColumnCount() == totalColumns + 1);
- assertTrue(sourceTable.getTotalRows() == numRows);
- assertTrue(destinationTable.getTotalRows() == numRows);
}
}
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyResultSetCursorTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyResultSetCursorTest.java
index 3ed177217e..3ce050a65e 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyResultSetCursorTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyResultSetCursorTest.java
@@ -70,7 +70,7 @@ private void serverCursorsTest(int resultSetType, int resultSetConcurrency) thro
try (Statement stmt2 = conn.createStatement(resultSetType, resultSetConcurrency);
ResultSet rs = stmt2
- .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable) + " ORDER BY id ASC");
+ .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable));
SQLServerBulkCopy bulkCopy = new SQLServerBulkCopy(conn)) {
bulkCopy.setDestinationTableName(AbstractSQLGenerator.escapeIdentifier(desTable));
bulkCopy.writeToServer(rs);
@@ -96,7 +96,7 @@ public void testSelectMethodSetToCursor() throws SQLException {
createTables(stmt);
populateSourceTable();
- try (ResultSet rs = stmt.executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable) + " ORDER BY id ASC");
+ try (ResultSet rs = stmt.executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable));
SQLServerBulkCopy bulkCopy = new SQLServerBulkCopy(conn)) {
bulkCopy.setDestinationTableName(AbstractSQLGenerator.escapeIdentifier(desTable));
@@ -122,7 +122,7 @@ public void testMultiplePreparedStatementAndResultSet() throws SQLException {
try (Statement stmt1 = conn.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE);
ResultSet rs = stmt1
- .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable) + " ORDER BY id ASC")) {
+ .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable))) {
try (SQLServerBulkCopy bulkCopy = new SQLServerBulkCopy(conn)) {
bulkCopy.setDestinationTableName(AbstractSQLGenerator.escapeIdentifier(desTable));
bulkCopy.writeToServer(rs);
@@ -158,7 +158,7 @@ public void testMultiplePreparedStatementAndResultSet() throws SQLException {
try (Statement stmt2 = conn.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE,
ResultSet.CONCUR_UPDATABLE);
ResultSet rs2 = stmt2
- .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable) + " ORDER BY id ASC");
+ .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(srcTable));
SQLServerBulkCopy bulkCopy3 = new SQLServerBulkCopy(conn)) {
bulkCopy3.setDestinationTableName(AbstractSQLGenerator.escapeIdentifier(desTable));
bulkCopy3.writeToServer(rs2);
@@ -170,20 +170,20 @@ public void testMultiplePreparedStatementAndResultSet() throws SQLException {
private static void verifyDestinationTableData(int expectedNumberOfRows) throws SQLException {
try (Connection conn = DriverManager.getConnection(connectionString); ResultSet rs = conn.createStatement()
- .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(desTable) + " ORDER BY id ASC")) {
+ .executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(desTable))) {
int expectedArrayLength = expectedBigDecimals.length;
int i = 0;
while (rs.next()) {
- assertTrue(rs.getString(2).equals(expectedBigDecimalStrings[i % expectedArrayLength]), "Expected Value:"
- + expectedBigDecimalStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(2));
- assertTrue(rs.getString(3).trim().equals(expectedStrings[i % expectedArrayLength]), "Expected Value:"
- + expectedStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(3));
- assertTrue(rs.getString(4).equals(expectedTimestampStrings[i % expectedArrayLength]), "Expected Value:"
- + expectedTimestampStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(4));
- assertTrue(rs.getString(5).trim().equals(expectedStrings[i % expectedArrayLength]), "Expected Value:"
- + expectedStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(5));
+ assertTrue(rs.getString(1).equals(expectedBigDecimalStrings[i % expectedArrayLength]), "Expected Value:"
+ + expectedBigDecimalStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(1));
+ assertTrue(rs.getString(2).trim().equals(expectedStrings[i % expectedArrayLength]), "Expected Value:"
+ + expectedStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(2));
+ assertTrue(rs.getString(3).equals(expectedTimestampStrings[i % expectedArrayLength]), "Expected Value:"
+ + expectedTimestampStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(3));
+ assertTrue(rs.getString(4).trim().equals(expectedStrings[i % expectedArrayLength]), "Expected Value:"
+ + expectedStrings[i % expectedArrayLength] + ", Actual Value: " + rs.getString(4));
i++;
}
@@ -196,7 +196,8 @@ private static void populateSourceTable() throws SQLException {
Calendar calGMT = Calendar.getInstance(TimeZone.getTimeZone("GMT"));
try (Connection conn = DriverManager.getConnection(connectionString);
- SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) conn.prepareStatement(sql)) {
+ SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) conn.prepareStatement(sql)) {
+
for (int i = 0; i < expectedBigDecimals.length; i++) {
pstmt.setBigDecimal(1, expectedBigDecimals[i]);
pstmt.setString(2, expectedStrings[i]);
@@ -218,10 +219,10 @@ private static void dropTables(Statement stmt) throws SQLException {
private static void createTables(Statement stmt) throws SQLException {
String sql = "create table " + AbstractSQLGenerator.escapeIdentifier(srcTable)
- + " (id INT NOT NULL IDENTITY PRIMARY KEY, c1 decimal(10,5) null, c2 nchar(50) null, c3 datetime2(7) null, c4 char(7000));";
+ + " (c1 decimal(10,5) null, c2 nchar(50) null, c3 datetime2(7) null, c4 char(7000));";
stmt.execute(sql);
sql = "create table " + AbstractSQLGenerator.escapeIdentifier(desTable)
- + " (id INT NOT NULL IDENTITY PRIMARY KEY, c1 decimal(10,5) null, c2 nchar(50) null, c3 datetime2(7) null, c4 char(7000));";
+ + " (c1 decimal(10,5) null, c2 nchar(50) null, c3 datetime2(7) null, c4 char(7000));";
stmt.execute(sql);
}
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTestUtil.java b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTestUtil.java
index 8a942a64ac..73e77c885f 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTestUtil.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTestUtil.java
@@ -4,7 +4,6 @@
*/
package com.microsoft.sqlserver.jdbc.bulkCopy;
-import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.junit.jupiter.api.Assertions.fail;
import java.sql.Connection;
@@ -281,10 +280,10 @@ static void validateValues(DBConnection con, DBTable sourceTable, DBTable destin
int totalColumns = destMeta.getColumnCount();
// verify data from sourceType and resultSet
- int numRows = 0;
while (srcResultSet.next() && dstResultSet.next()) {
- numRows++;
for (int i = 1; i <= totalColumns; i++) {
+ // TODO: check row and column count in both the tables
+
Object srcValue, dstValue;
srcValue = srcResultSet.getObject(i);
dstValue = dstResultSet.getObject(i);
@@ -292,14 +291,6 @@ static void validateValues(DBConnection con, DBTable sourceTable, DBTable destin
ComparisonUtil.compareExpectedAndActual(destMeta.getColumnType(i), srcValue, dstValue);
}
}
-
- // verify number of rows and columns
- assertTrue(((ResultSet) srcResultSet.product()).getMetaData().getColumnCount() == totalColumns);
-
- if (numRows > 0) {
- assertTrue(sourceTable.getTotalRows() == numRows);
- assertTrue(destinationTable.getTotalRows() == numRows);
- }
}
}
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTimeoutTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTimeoutTest.java
index 76688ca9e0..c3497adf8f 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTimeoutTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/bulkCopy/BulkCopyTimeoutTest.java
@@ -47,13 +47,13 @@ public void testZeroTimeOut() throws SQLException {
*/
@Test
@DisplayName("BulkCopy:test negative timeout")
- public void testNegativeTimeOut() {
+ public void testNegativeTimeOut() throws SQLException {
assertThrows(SQLException.class, new org.junit.jupiter.api.function.Executable() {
@Override
public void execute() throws SQLException {
testBulkCopyWithTimeout(-1);
}
- }, "The timeout argument cannot be negative.");
+ });
}
private void testBulkCopyWithTimeout(int timeout) throws SQLException {
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/databasemetadata/DatabaseMetaDataTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/databasemetadata/DatabaseMetaDataTest.java
index 3a4a054e28..07485bb8aa 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/databasemetadata/DatabaseMetaDataTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/databasemetadata/DatabaseMetaDataTest.java
@@ -419,7 +419,9 @@ public void testGetColumnPrivileges() throws SQLException {
}
/**
- * Testing {@link SQLServerDatabaseMetaData#getFunctions(String, String, String)} with sending wrong catalog.
+ * TODO: Check JDBC Specs: Can we have any tables/functions without category?
+ *
+ * Testing {@link SQLServerDatabaseMetaData#getFunctions(String, String, String)} with sending wrong category.
*
* @throws SQLException
*/
@@ -428,7 +430,9 @@ public void testGetFunctionsWithWrongParams() throws SQLException {
try (Connection conn = DriverManager.getConnection(connectionString)) {
conn.getMetaData().getFunctions("", null, "xp_%");
assertTrue(false, TestResource.getResource("R_noSchemaShouldFail"));
- } catch (Exception ae) {}
+ } catch (Exception ae) {
+
+ }
}
/**
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/BulkCopyWithSqlVariantTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/BulkCopyWithSqlVariantTest.java
index b6345e4381..6814627153 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/BulkCopyWithSqlVariantTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/BulkCopyWithSqlVariantTest.java
@@ -609,7 +609,7 @@ public void bulkCopyTestVarbinary8000() throws SQLException {
*
* @throws SQLException
*/
- @Test
+ @Test // TODO: check bitnull
public void bulkCopyTestBitNull() throws SQLException {
try (Connection con = DriverManager.getConnection(connectionString); Statement stmt = con.createStatement()) {
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/SQLServerSpatialDatatypeTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/SQLServerSpatialDatatypeTest.java
index cce188515e..6a95f29c9e 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/SQLServerSpatialDatatypeTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/SQLServerSpatialDatatypeTest.java
@@ -4,7 +4,6 @@
*/
package com.microsoft.sqlserver.jdbc.datatypes;
-import static org.junit.Assert.fail;
import static org.junit.jupiter.api.Assertions.assertEquals;
import java.io.IOException;
@@ -813,7 +812,7 @@ public void testPoint() throws SQLException {
String geoWKT = "POINT(1 2)";
Geometry geomWKT = Geometry.point(1, 2, 0);
- Geography geogWKT = Geography.point(2, 1, 4326);
+ Geography geogWKT = Geography.point(1, 2, 4326);
try (Connection con = (SQLServerConnection) DriverManager.getConnection(connectionString);
Statement stmt = con.createStatement()) {
@@ -969,8 +968,8 @@ public void testGetXGetY() throws SQLException {
x = geog.getLatitude();
y = geog.getLongitude();
- assertEquals(x, 2);
- assertEquals(y, 1);
+ assertEquals(x, 1);
+ assertEquals(y, 2);
}
@Test
@@ -1042,48 +1041,6 @@ public void testNull() throws SQLException {
}
}
}
-
- @Test
- public void testWrongtype() throws SQLException {
- beforeEachSetup();
-
- Geometry geomWKT = Geometry.point(1, 2, 0);
- Geography geogWKT = Geography.point(2, 1, 4326);
-
- try (Connection con = (SQLServerConnection) DriverManager.getConnection(connectionString);
- Statement stmt = con.createStatement()) {
-
- try (SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) con.prepareStatement(
- "insert into " + AbstractSQLGenerator.escapeIdentifier(geomTableName) + " values (?)");) {
- pstmt.setGeometry(1, geomWKT);
- pstmt.execute();
-
- try {
- SQLServerResultSet rs = (SQLServerResultSet) stmt.executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(geomTableName));
- rs.next();
- rs.getGeography(1); // should fail
- fail();
- } catch (SQLServerException e) {
- assertEquals(e.getMessage(), "The conversion from GEOMETRY to GEOGRAPHY is unsupported.");
- }
- }
-
- try (SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) con.prepareStatement(
- "insert into " + AbstractSQLGenerator.escapeIdentifier(geogTableName) + " values (?)");) {
- pstmt.setGeography(1, geogWKT);
- pstmt.execute();
-
- try {
- SQLServerResultSet rs = (SQLServerResultSet) stmt.executeQuery("select * from " + AbstractSQLGenerator.escapeIdentifier(geogTableName));
- rs.next();
- rs.getGeometry(1); // should fail
- fail();
- } catch (SQLServerException e) {
- assertEquals(e.getMessage(), "The conversion from GEOGRAPHY to GEOMETRY is unsupported.");
- }
- }
- }
- }
private void beforeEachSetup() throws SQLException {
try (Connection con = (SQLServerConnection) DriverManager.getConnection(connectionString);
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/TVPWithSqlVariantTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/TVPWithSqlVariantTest.java
index 307bbdcdf9..d58c5dd15a 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/TVPWithSqlVariantTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/datatypes/TVPWithSqlVariantTest.java
@@ -353,10 +353,8 @@ public void testDateTime() throws SQLException {
*
* @throws SQLException
* @throws SQLTimeoutException
- * https://msdn.microsoft.com/en-ca/library/dd303302.aspx?f=255&MSPPError=-2147217396
- * Data types cannot be NULL when inside a sql_variant
*/
- @Test
+ @Test // TODO We need to check this later. Right now sending null with TVP is not supported
public void testNull() throws SQLException {
tvp = new SQLServerDataTable();
tvp.addColumnMetadata("c1", microsoft.sql.Types.SQL_VARIANT);
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/fips/FipsEnvTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/fips/FipsEnvTest.java
index 32e40b5077..46b593730a 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/fips/FipsEnvTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/fips/FipsEnvTest.java
@@ -55,13 +55,16 @@ public static void populateProperties() {
currentJVM = IBM_JVM;
}
+ // TODO: Need to check this.
if (p.getProperty("java.vendor").startsWith("SAP")) {
currentJVM = SAP_JVM;
}
}
/**
- * Test FIPS in Oracle Env.
+ * After stabilizing parameterized test case TODO: Enable FIPS can be done in two ways.
+ * JVM Level - Done.
+ * Program Level - Not Done. We need to test both on different environments.
*
* @since 6.1.2
*/
@@ -88,7 +91,7 @@ public void testFIPSOnOracle() throws Exception {
}
/**
- * Test FIPS in IBM Env. If JVM is not IBM test will not fail. It will simply skipped.
+ * It will test FIPS on IBM Env. If JVM is not IBM test will not fail. It will simply skipped.
*
* @since 6.1.2
*/
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/timeouts/TimeoutTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/timeouts/TimeoutTest.java
deleted file mode 100644
index a61e097b17..0000000000
--- a/src/test/java/com/microsoft/sqlserver/jdbc/timeouts/TimeoutTest.java
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Microsoft JDBC Driver for SQL Server Copyright(c) Microsoft Corporation All rights reserved. This program is made
- * available under the terms of the MIT License. See the LICENSE file in the project root for more information.
- */
-
-package com.microsoft.sqlserver.jdbc.timeouts;
-
-import java.sql.Connection;
-import java.sql.DriverManager;
-import java.sql.PreparedStatement;
-import java.sql.SQLException;
-import java.sql.SQLTimeoutException;
-
-import org.junit.Assert;
-import org.junit.jupiter.api.Test;
-import org.junit.platform.runner.JUnitPlatform;
-import org.junit.runner.RunWith;
-
-import com.microsoft.sqlserver.testframework.AbstractTest;
-
-
-@RunWith(JUnitPlatform.class)
-public class TimeoutTest extends AbstractTest {
- @Test
- public void testBasicQueryTimeout() {
- boolean exceptionThrown = false;
- try {
- // wait 1 minute and timeout after 10 seconds
- Assert.assertTrue("Select succeeded", runQuery("WAITFOR DELAY '00:01'", 10));
- } catch (SQLException e) {
- exceptionThrown = true;
- Assert.assertTrue("Timeout exception not thrown", e.getClass().equals(SQLTimeoutException.class));
- }
- Assert.assertTrue("A SQLTimeoutException was expected", exceptionThrown);
- }
-
- @Test
- public void testQueryTimeoutValid() {
- boolean exceptionThrown = false;
- int timeoutInSeconds = 10;
- long start = System.currentTimeMillis();
- try {
- // wait 1 minute and timeout after 10 seconds
- Assert.assertTrue("Select succeeded", runQuery("WAITFOR DELAY '00:01'", timeoutInSeconds));
- } catch (SQLException e) {
- int secondsElapsed = (int) ((System.currentTimeMillis() - start) / 1000);
- Assert.assertTrue("Query did not timeout expected, elapsedTime=" + secondsElapsed,
- secondsElapsed >= timeoutInSeconds);
- exceptionThrown = true;
- Assert.assertTrue("Timeout exception not thrown", e.getClass().equals(SQLTimeoutException.class));
- }
- Assert.assertTrue("A SQLTimeoutException was expected", exceptionThrown);
- }
-
- private boolean runQuery(String query, int timeout) throws SQLException {
- try (Connection con = DriverManager.getConnection(connectionString);
- PreparedStatement preparedStatement = con.prepareStatement(query)) {
- // set provided timeout
- preparedStatement.setQueryTimeout(timeout);
- return preparedStatement.execute();
- }
- }
-}
diff --git a/src/test/java/com/microsoft/sqlserver/jdbc/tvp/TVPAllTypesTest.java b/src/test/java/com/microsoft/sqlserver/jdbc/tvp/TVPAllTypesTest.java
index d5c7e2f9cf..22408852f0 100644
--- a/src/test/java/com/microsoft/sqlserver/jdbc/tvp/TVPAllTypesTest.java
+++ b/src/test/java/com/microsoft/sqlserver/jdbc/tvp/TVPAllTypesTest.java
@@ -33,9 +33,12 @@
@RunWith(JUnitPlatform.class)
public class TVPAllTypesTest extends AbstractTest {
+ private static Connection conn = null;
+ static Statement stmt = null;
private static String tvpName;
private static String procedureName;
+
private static DBTable tableSrc = null;
private static DBTable tableDest = null;
@@ -56,36 +59,18 @@ public void testTVPResultSet() throws SQLException {
private void testTVPResultSet(boolean setSelectMethod, Integer resultSetType,
Integer resultSetConcurrency) throws SQLException {
-
- String connString;
- Statement stmt = null;
-
- if (setSelectMethod) {
- connString = connectionString + ";selectMethod=cursor;";
- } else {
- connString = connectionString;
- }
-
- try (Connection conn = DriverManager.getConnection(connString)) {
- if (null != resultSetType && null != resultSetConcurrency) {
- stmt = conn.createStatement(resultSetType, resultSetConcurrency);
- } else {
- stmt = conn.createStatement();
- }
-
- setupVariation(setSelectMethod, stmt);
- try (ResultSet rs = stmt.executeQuery("select * from " + tableSrc.getEscapedTableName());
- SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) conn.prepareStatement(
- "INSERT INTO " + tableDest.getEscapedTableName() + " select * from ? ;")) {
- pstmt.setStructured(1, tvpName, rs);
- pstmt.execute();
- ComparisonUtil.compareSrcTableAndDestTableIgnoreRowOrder(new DBConnection(connectionString), tableSrc,
- tableDest);
- } catch (Exception e) {
- fail(TestResource.getResource("R_unexpectedErrorMessage") + e.toString());
- } finally {
- stmt.close();
- }
+ setupVariation(setSelectMethod, resultSetType, resultSetConcurrency);
+
+ try (ResultSet rs = stmt.executeQuery("select * from " + tableSrc.getEscapedTableName());
+ SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) conn
+ .prepareStatement("INSERT INTO " + tableDest.getEscapedTableName() + " select * from ? ;")) {
+ pstmt.setStructured(1, tvpName, rs);
+ pstmt.execute();
+
+ ComparisonUtil.compareSrcTableAndDestTableIgnoreRowOrder(new DBConnection(connectionString), tableSrc,
+ tableDest);
+ } catch (Exception e) {
+ fail(TestResource.getResource("R_unexpectedErrorMessage") + e.toString());
} finally {
terminateVariation();
}
@@ -108,33 +93,15 @@ public void testTVPStoredProcedureResultSet() throws SQLException {
private void testTVPStoredProcedureResultSet(boolean setSelectMethod, Integer resultSetType,
Integer resultSetConcurrency) throws SQLException {
- String connString;
- Statement stmt = null;
-
- if (setSelectMethod) {
- connString = connectionString + ";selectMethod=cursor;";
- } else {
- connString = connectionString;
- }
-
- try (Connection conn = DriverManager.getConnection(connString)) {
- if (null != resultSetType && null != resultSetConcurrency) {
- stmt = conn.createStatement(resultSetType, resultSetConcurrency);
- } else {
- stmt = conn.createStatement();
- }
-
- setupVariation(setSelectMethod, stmt);
- try (ResultSet rs = stmt.executeQuery("select * from " + tableSrc.getEscapedTableName());
- SQLServerCallableStatement Cstmt = (SQLServerCallableStatement) conn
- .prepareCall("{call " + AbstractSQLGenerator.escapeIdentifier(procedureName) + "(?)}")) {
- Cstmt.setStructured(1, tvpName, rs);
- Cstmt.execute();
- ComparisonUtil.compareSrcTableAndDestTableIgnoreRowOrder(new DBConnection(connectionString), tableSrc,
- tableDest);
- } finally {
- stmt.close();
- }
+ setupVariation(setSelectMethod, resultSetType, resultSetConcurrency);
+ try (ResultSet rs = stmt.executeQuery("select * from " + tableSrc.getEscapedTableName());
+ SQLServerCallableStatement Cstmt = (SQLServerCallableStatement) conn
+ .prepareCall("{call " + AbstractSQLGenerator.escapeIdentifier(procedureName) + "(?)}")) {
+ Cstmt.setStructured(1, tvpName, rs);
+ Cstmt.execute();
+
+ ComparisonUtil.compareSrcTableAndDestTableIgnoreRowOrder(new DBConnection(connectionString), tableSrc,
+ tableDest);
} finally {
terminateVariation();
}
@@ -147,35 +114,33 @@ private void testTVPStoredProcedureResultSet(boolean setSelectMethod, Integer re
*/
@Test
public void testTVPDataTable() throws SQLException {
+ setupVariation(false, null, null);
+
+ SQLServerDataTable dt = new SQLServerDataTable();
+
+ int numberOfColumns = tableDest.getColumns().size();
+ Object[] values = new Object[numberOfColumns];
+ for (int i = 0; i < numberOfColumns; i++) {
+ SqlType sqlType = tableDest.getColumns().get(i).getSqlType();
+ dt.addColumnMetadata(tableDest.getColumnName(i), sqlType.getJdbctype().getVendorTypeNumber());
+ values[i] = sqlType.createdata();
+ }
- try (Connection conn = DriverManager.getConnection(connectionString); Statement stmt = conn.createStatement()) {
- setupVariation(false, stmt);
- SQLServerDataTable dt = new SQLServerDataTable();
- int numberOfColumns = tableDest.getColumns().size();
- Object[] values = new Object[numberOfColumns];
-
- for (int i = 0; i < numberOfColumns; i++) {
- SqlType sqlType = tableDest.getColumns().get(i).getSqlType();
- dt.addColumnMetadata(tableDest.getColumnName(i), sqlType.getJdbctype().getVendorTypeNumber());
- values[i] = sqlType.createdata();
- }
-
- int numberOfRows = 10;
- for (int i = 0; i < numberOfRows; i++) {
- dt.addRow(values);
- }
-
- try (SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) conn
- .prepareStatement("INSERT INTO " + tableDest.getEscapedTableName() + " select * from ? ;")) {
- pstmt.setStructured(1, tvpName, dt);
- pstmt.execute();
- }
+ int numberOfRows = 10;
+ for (int i = 0; i < numberOfRows; i++) {
+ dt.addRow(values);
+ }
+
+ try (SQLServerPreparedStatement pstmt = (SQLServerPreparedStatement) connection
+ .prepareStatement("INSERT INTO " + tableDest.getEscapedTableName() + " select * from ? ;")) {
+ pstmt.setStructured(1, tvpName, dt);
+ pstmt.execute();
} finally {
terminateVariation();
}
}
- private static void createProcedure(String procedureName, String destTable, Statement stmt) throws SQLException {
+ private static void createPreocedure(String procedureName, String destTable) throws SQLException {
String sql = "CREATE PROCEDURE " + AbstractSQLGenerator.escapeIdentifier(procedureName) + " @InputData "
+ AbstractSQLGenerator.escapeIdentifier(tvpName) + " READONLY " + " AS " + " BEGIN " + " INSERT INTO "
+ destTable + " SELECT * FROM @InputData" + " END";
@@ -183,17 +148,30 @@ private static void createProcedure(String procedureName, String destTable, Stat
stmt.execute(sql);
}
- private static void createTVPS(String tvpName, String TVPDefinition, Statement stmt) throws SQLException {
+ private static void createTVPS(String tvpName, String TVPDefinition) throws SQLException {
String TVPCreateCmd = "CREATE TYPE " + AbstractSQLGenerator.escapeIdentifier(tvpName) + " as table ("
+ TVPDefinition + ");";
stmt.executeUpdate(TVPCreateCmd);
}
- private void setupVariation(boolean setSelectMethod, Statement stmt) throws SQLException {
+ private void setupVariation(boolean setSelectMethod, Integer resultSetType,
+ Integer resultSetConcurrency) throws SQLException {
tvpName = RandomUtil.getIdentifier("TVP");
procedureName = RandomUtil.getIdentifier("TVP");
+ if (setSelectMethod) {
+ conn = DriverManager.getConnection(connectionString + ";selectMethod=cursor;");
+ } else {
+ conn = DriverManager.getConnection(connectionString);
+ }
+
+ if (null != resultSetType || null != resultSetConcurrency) {
+ stmt = conn.createStatement(resultSetType, resultSetConcurrency);
+ } else {
+ stmt = conn.createStatement();
+ }
+
TestUtils.dropProcedureIfExists(AbstractSQLGenerator.escapeIdentifier(procedureName), stmt);
TestUtils.dropTableIfExists(AbstractSQLGenerator.escapeIdentifier(tvpName), stmt);
@@ -206,19 +184,24 @@ private void setupVariation(boolean setSelectMethod, Statement stmt) throws SQLE
dbStmt.createTable(tableSrc);
dbStmt.createTable(tableDest);
- createTVPS(tvpName, tableSrc.getDefinitionOfColumns(), stmt);
- createProcedure(procedureName, tableDest.getEscapedTableName(), stmt);
+ createTVPS(tvpName, tableSrc.getDefinitionOfColumns());
+ createPreocedure(procedureName, tableDest.getEscapedTableName());
dbStmt.populateTable(tableSrc);
}
}
private void terminateVariation() throws SQLException {
- try (Connection conn = DriverManager.getConnection(connectionString); Statement stmt = conn.createStatement()) {
- TestUtils.dropProcedureIfExists(AbstractSQLGenerator.escapeIdentifier(procedureName), stmt);
- TestUtils.dropTableIfExists(tableSrc.getEscapedTableName(), stmt);
- TestUtils.dropTableIfExists(tableDest.getEscapedTableName(), stmt);
- TestUtils.dropTableIfExists(AbstractSQLGenerator.escapeIdentifier(tvpName), stmt);
+ TestUtils.dropProcedureIfExists(AbstractSQLGenerator.escapeIdentifier(procedureName), stmt);
+ TestUtils.dropTableIfExists(tableSrc.getEscapedTableName(), stmt);
+ TestUtils.dropTableIfExists(tableDest.getEscapedTableName(), stmt);
+ TestUtils.dropTableIfExists(AbstractSQLGenerator.escapeIdentifier(tvpName), stmt);
+
+ if (null != stmt) {
+ stmt.close();
+ }
+ if (null != conn) {
+ conn.close();
}
}
}
diff --git a/src/test/java/com/microsoft/sqlserver/testframework/sqlType/SqlFloat.java b/src/test/java/com/microsoft/sqlserver/testframework/sqlType/SqlFloat.java
index cdf227dfd7..f1881406f2 100644
--- a/src/test/java/com/microsoft/sqlserver/testframework/sqlType/SqlFloat.java
+++ b/src/test/java/com/microsoft/sqlserver/testframework/sqlType/SqlFloat.java
@@ -27,9 +27,10 @@ public SqlFloat() {
public Object createdata() {
// for float in SQL Server, any precision <=24 is considered as real so the value must be within
// SqlTypeValue.REAL.minValue/maxValue
- if (precision > 24) {
- return ThreadLocalRandom.current().nextDouble(((Double) minvalue), ((Double) maxvalue));
- } else {
+ if (precision > 24)
+ return Double.longBitsToDouble(ThreadLocalRandom.current().nextLong(((Double) minvalue).longValue(),
+ ((Double) maxvalue).longValue()));
+ else {
return ThreadLocalRandom.current().nextDouble((Float) SqlTypeValue.REAL.minValue,
(Float) SqlTypeValue.REAL.maxValue);
}