From 7cb73ff2ca00973550e4349453d6de4c0c193119 Mon Sep 17 00:00:00 2001 From: John Yun <140559986+sfc-gh-ext-simba-jy@users.noreply.github.com> Date: Sat, 27 Apr 2024 02:17:21 +0900 Subject: [PATCH] SNOW-1213117: Wrap connection, statement and result set in try with resources(2/4) (#1722) --- .../client/jdbc/DellBoomiCloudIT.java | 18 +- .../client/jdbc/FileUploaderLatestIT.java | 1177 ++++++++--------- .../snowflake/client/jdbc/GCPLargeResult.java | 19 +- .../client/jdbc/HeartbeatAsyncLatestIT.java | 34 +- .../snowflake/client/jdbc/HeartbeatIT.java | 68 +- .../client/jdbc/MultiStatementIT.java | 712 +++++----- .../client/jdbc/MultiStatementLatestIT.java | 530 ++++---- .../client/jdbc/OpenGroupCLIFuncIT.java | 4 +- .../client/jdbc/PreparedMultiStmtIT.java | 364 ++--- .../client/jdbc/PreparedStatement0IT.java | 6 +- .../client/jdbc/PreparedStatement1IT.java | 279 ++-- .../jdbc/PreparedStatement1LatestIT.java | 249 ++-- .../client/jdbc/PreparedStatement2IT.java | 579 ++++---- .../jdbc/PreparedStatement2LatestIT.java | 379 +++--- ...reparedStatementFeatureNotSupportedIT.java | 4 +- .../PreparedStatementLargeUpdateLatestIT.java | 90 +- 16 files changed, 2224 insertions(+), 2288 deletions(-) diff --git a/src/test/java/net/snowflake/client/jdbc/DellBoomiCloudIT.java b/src/test/java/net/snowflake/client/jdbc/DellBoomiCloudIT.java index f61ff65e7..794af78df 100644 --- a/src/test/java/net/snowflake/client/jdbc/DellBoomiCloudIT.java +++ b/src/test/java/net/snowflake/client/jdbc/DellBoomiCloudIT.java @@ -26,17 +26,15 @@ public void setup() { @Test public void testSelectLargeResultSet() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - ResultSet resultSet = - statement.executeQuery("select seq4() from table" + "(generator" + "(rowcount=>10000))"); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement(); + ResultSet resultSet = + statement.executeQuery( + "select seq4() from table" + "(generator" + "(rowcount=>10000))")) { - while (resultSet.next()) { - resultSet.getString(1); + while (resultSet.next()) { + resultSet.getString(1); + } } - - resultSet.close(); - statement.close(); - connection.close(); } } diff --git a/src/test/java/net/snowflake/client/jdbc/FileUploaderLatestIT.java b/src/test/java/net/snowflake/client/jdbc/FileUploaderLatestIT.java index ac1ffe249..66b33b9ab 100644 --- a/src/test/java/net/snowflake/client/jdbc/FileUploaderLatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/FileUploaderLatestIT.java @@ -67,24 +67,24 @@ public class FileUploaderLatestIT extends FileUploaderPrepIT { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetS3StageDataWithS3Session() throws SQLException { - Connection con = getConnection("s3testaccount"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - // Set UseRegionalS3EndpointsForPresignedURL to true in session - sfSession.setUseRegionalS3EndpointsForPresignedURL(true); - - // Get sample stage info with session - StageInfo stageInfo = SnowflakeFileTransferAgent.getStageInfo(exampleS3JsonNode, sfSession); - Assert.assertEquals(StageInfo.StageType.S3, stageInfo.getStageType()); - // Assert that true value from session is reflected in StageInfo - Assert.assertEquals(true, stageInfo.getUseS3RegionalUrl()); - - // Set UseRegionalS3EndpointsForPresignedURL to false in session - sfSession.setUseRegionalS3EndpointsForPresignedURL(false); - stageInfo = SnowflakeFileTransferAgent.getStageInfo(exampleS3JsonNode, sfSession); - Assert.assertEquals(StageInfo.StageType.S3, stageInfo.getStageType()); - // Assert that false value from session is reflected in StageInfo - Assert.assertEquals(false, stageInfo.getUseS3RegionalUrl()); - con.close(); + try (Connection con = getConnection("s3testaccount")) { + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + // Set UseRegionalS3EndpointsForPresignedURL to true in session + sfSession.setUseRegionalS3EndpointsForPresignedURL(true); + + // Get sample stage info with session + StageInfo stageInfo = SnowflakeFileTransferAgent.getStageInfo(exampleS3JsonNode, sfSession); + Assert.assertEquals(StageInfo.StageType.S3, stageInfo.getStageType()); + // Assert that true value from session is reflected in StageInfo + Assert.assertEquals(true, stageInfo.getUseS3RegionalUrl()); + + // Set UseRegionalS3EndpointsForPresignedURL to false in session + sfSession.setUseRegionalS3EndpointsForPresignedURL(false); + stageInfo = SnowflakeFileTransferAgent.getStageInfo(exampleS3JsonNode, sfSession); + Assert.assertEquals(StageInfo.StageType.S3, stageInfo.getStageType()); + // Assert that false value from session is reflected in StageInfo + Assert.assertEquals(false, stageInfo.getUseS3RegionalUrl()); + } } /** @@ -96,56 +96,56 @@ public void testGetS3StageDataWithS3Session() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetS3StageDataWithAzureSession() throws SQLException { - Connection con = getConnection("azureaccount"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - // Set UseRegionalS3EndpointsForPresignedURL to true in session. This is redundant since session - // is Azure - sfSession.setUseRegionalS3EndpointsForPresignedURL(true); - - // Get sample stage info with session - StageInfo stageInfo = SnowflakeFileTransferAgent.getStageInfo(exampleAzureJsonNode, sfSession); - Assert.assertEquals(StageInfo.StageType.AZURE, stageInfo.getStageType()); - Assert.assertEquals("EXAMPLE_LOCATION/", stageInfo.getLocation()); - // Assert that UseRegionalS3EndpointsForPresignedURL is false in StageInfo even if it was set to - // true. - // The value should always be false for non-S3 accounts - Assert.assertEquals(false, stageInfo.getUseS3RegionalUrl()); - con.close(); + try (Connection con = getConnection("azureaccount")) { + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + // Set UseRegionalS3EndpointsForPresignedURL to true in session. This is redundant since + // session + // is Azure + sfSession.setUseRegionalS3EndpointsForPresignedURL(true); + + // Get sample stage info with session + StageInfo stageInfo = + SnowflakeFileTransferAgent.getStageInfo(exampleAzureJsonNode, sfSession); + Assert.assertEquals(StageInfo.StageType.AZURE, stageInfo.getStageType()); + Assert.assertEquals("EXAMPLE_LOCATION/", stageInfo.getLocation()); + // Assert that UseRegionalS3EndpointsForPresignedURL is false in StageInfo even if it was set + // to + // true. + // The value should always be false for non-S3 accounts + Assert.assertEquals(false, stageInfo.getUseS3RegionalUrl()); + } } @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetObjectMetadataWithGCS() throws Exception { - Connection connection = null; - try { - Properties paramProperties = new Properties(); - paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); - connection = getConnection("gcpaccount", paramProperties); - Statement statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); - - String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); - String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; - statement.execute(putCommand); - - SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); - StageInfo info = sfAgent.getStageInfo(); - SnowflakeGCSClient client = - SnowflakeGCSClient.createSnowflakeGCSClient( - info, sfAgent.getEncryptionMaterial().get(0), sfSession); - - String location = info.getLocation(); - int idx = location.indexOf('/'); - String remoteStageLocation = location.substring(0, idx); - String path = location.substring(idx + 1) + TEST_DATA_FILE + ".gz"; - StorageObjectMetadata metadata = client.getObjectMetadata(remoteStageLocation, path); - Assert.assertEquals("gzip", metadata.getContentEncoding()); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists " + OBJ_META_STAGE); - connection.close(); + Properties paramProperties = new Properties(); + paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); + try (Connection connection = getConnection("gcpaccount", paramProperties); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); + + String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); + String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; + statement.execute(putCommand); + + SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); + StageInfo info = sfAgent.getStageInfo(); + SnowflakeGCSClient client = + SnowflakeGCSClient.createSnowflakeGCSClient( + info, sfAgent.getEncryptionMaterial().get(0), sfSession); + + String location = info.getLocation(); + int idx = location.indexOf('/'); + String remoteStageLocation = location.substring(0, idx); + String path = location.substring(idx + 1) + TEST_DATA_FILE + ".gz"; + StorageObjectMetadata metadata = client.getObjectMetadata(remoteStageLocation, path); + Assert.assertEquals("gzip", metadata.getContentEncoding()); + } finally { + statement.execute("DROP STAGE if exists " + OBJ_META_STAGE); } } } @@ -153,41 +153,38 @@ public void testGetObjectMetadataWithGCS() throws Exception { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetObjectMetadataFileNotFoundWithGCS() throws Exception { - Connection connection = null; - try { - Properties paramProperties = new Properties(); - paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); - connection = getConnection("gcpaccount", paramProperties); - Statement statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); - - String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); - String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; - statement.execute(putCommand); - - SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); - StageInfo info = sfAgent.getStageInfo(); - SnowflakeGCSClient client = - SnowflakeGCSClient.createSnowflakeGCSClient( - info, sfAgent.getEncryptionMaterial().get(0), sfSession); - - String location = info.getLocation(); - int idx = location.indexOf('/'); - String remoteStageLocation = location.substring(0, idx); - String path = location.substring(idx + 1) + "wrong_file.csv.gz"; - client.getObjectMetadata(remoteStageLocation, path); - fail("should raise exception"); - } catch (Exception ex) { - assertTrue( - "Wrong type of exception. Message: " + ex.getMessage(), - ex instanceof StorageProviderException); - assertTrue(ex.getMessage().matches(".*Blob.*not found in bucket.*")); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists " + OBJ_META_STAGE); - connection.close(); + Properties paramProperties = new Properties(); + paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); + try (Connection connection = getConnection("gcpaccount", paramProperties); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); + + String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); + String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; + statement.execute(putCommand); + + SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); + StageInfo info = sfAgent.getStageInfo(); + SnowflakeGCSClient client = + SnowflakeGCSClient.createSnowflakeGCSClient( + info, sfAgent.getEncryptionMaterial().get(0), sfSession); + + String location = info.getLocation(); + int idx = location.indexOf('/'); + String remoteStageLocation = location.substring(0, idx); + String path = location.substring(idx + 1) + "wrong_file.csv.gz"; + client.getObjectMetadata(remoteStageLocation, path); + fail("should raise exception"); + } catch (Exception ex) { + assertTrue( + "Wrong type of exception. Message: " + ex.getMessage(), + ex instanceof StorageProviderException); + assertTrue(ex.getMessage().matches(".*Blob.*not found in bucket.*")); + } finally { + statement.execute("DROP STAGE if exists " + OBJ_META_STAGE); } } } @@ -195,116 +192,114 @@ public void testGetObjectMetadataFileNotFoundWithGCS() throws Exception { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetObjectMetadataStorageExceptionWithGCS() throws Exception { - Connection connection = null; - try { - Properties paramProperties = new Properties(); - paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); - connection = getConnection("gcpaccount", paramProperties); - Statement statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); - - String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); - String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; - statement.execute(putCommand); - - SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); - StageInfo info = sfAgent.getStageInfo(); - SnowflakeGCSClient client = - SnowflakeGCSClient.createSnowflakeGCSClient( - info, sfAgent.getEncryptionMaterial().get(0), sfSession); - - String location = info.getLocation(); - int idx = location.indexOf('/'); - String remoteStageLocation = location.substring(0, idx); - client.getObjectMetadata(remoteStageLocation, ""); - fail("should raise exception"); - } catch (Exception ex) { - assertTrue( - "Wrong type of exception. Message: " + ex.getMessage(), - ex instanceof StorageProviderException); - assertTrue(ex.getMessage().matches(".*Permission.*denied.*")); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists " + OBJ_META_STAGE); - connection.close(); + Properties paramProperties = new Properties(); + paramProperties.put("GCS_USE_DOWNSCOPED_CREDENTIAL", true); + try (Connection connection = getConnection("gcpaccount", paramProperties); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); + + String sourceFilePath = getFullPathFileInResource(TEST_DATA_FILE); + String putCommand = "PUT file://" + sourceFilePath + " @" + OBJ_META_STAGE; + statement.execute(putCommand); + + SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); + StageInfo info = sfAgent.getStageInfo(); + SnowflakeGCSClient client = + SnowflakeGCSClient.createSnowflakeGCSClient( + info, sfAgent.getEncryptionMaterial().get(0), sfSession); + + String location = info.getLocation(); + int idx = location.indexOf('/'); + String remoteStageLocation = location.substring(0, idx); + client.getObjectMetadata(remoteStageLocation, ""); + fail("should raise exception"); + } catch (Exception ex) { + assertTrue( + "Wrong type of exception. Message: " + ex.getMessage(), + ex instanceof StorageProviderException); + assertTrue(ex.getMessage().matches(".*Permission.*denied.*")); + } finally { + statement.execute("DROP STAGE if exists " + OBJ_META_STAGE); } } } @Test public void testGetFileTransferCommandType() throws SQLException { - Connection con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - assertEquals(SFBaseFileTransferAgent.CommandType.UPLOAD, sfAgent.getCommandType()); - statement.execute("drop stage if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + assertEquals(SFBaseFileTransferAgent.CommandType.UPLOAD, sfAgent.getCommandType()); + } finally { + statement.execute("drop stage if exists testStage"); + } + } } @Test public void testNullCommand() throws SQLException { - Connection con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - try { - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(null, sfSession, new SFStatement(sfSession)); - } catch (SnowflakeSQLException err) { - Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); - Assert.assertTrue( - err.getMessage() - .contains("JDBC driver internal error: Missing sql for statement execution")); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(null, sfSession, new SFStatement(sfSession)); + } catch (SnowflakeSQLException err) { + Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); + Assert.assertTrue( + err.getMessage() + .contains("JDBC driver internal error: Missing sql for statement execution")); + } finally { + statement.execute("drop stage if exists testStage"); + } } - statement.execute("drop stage if exists testStage"); - con.close(); } @Test public void testCompressStreamWithGzipException() throws Exception { - Connection con = null; // inject the NoSuchAlgorithmException SnowflakeFileTransferAgent.setInjectedFileTransferException(new NoSuchAlgorithmException()); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - - List metadataList = sfAgent.getFileTransferMetadatas(); - SnowflakeFileTransferMetadataV1 metadata = - (SnowflakeFileTransferMetadataV1) metadataList.get(0); - - String srcPath = getFullPathFileInResource(TEST_DATA_FILE); - InputStream inputStream = new FileInputStream(srcPath); - SnowflakeFileTransferAgent.uploadWithoutConnection( - SnowflakeFileTransferConfig.Builder.newInstance() - .setSnowflakeFileTransferMetadata(metadata) - .setUploadStream(inputStream) - .setRequireCompress(true) - .setNetworkTimeoutInMilli(0) - .setOcspMode(OCSPMode.FAIL_OPEN) - .setSFSession(sfSession) - .setCommand(PUT_COMMAND) - .build()); - } catch (SnowflakeSQLException err) { - Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); - Assert.assertTrue( - err.getMessage() - .contains("JDBC driver internal error: error encountered for compression")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + List metadataList = sfAgent.getFileTransferMetadatas(); + SnowflakeFileTransferMetadataV1 metadata = + (SnowflakeFileTransferMetadataV1) metadataList.get(0); + + String srcPath = getFullPathFileInResource(TEST_DATA_FILE); + InputStream inputStream = new FileInputStream(srcPath); + SnowflakeFileTransferAgent.uploadWithoutConnection( + SnowflakeFileTransferConfig.Builder.newInstance() + .setSnowflakeFileTransferMetadata(metadata) + .setUploadStream(inputStream) + .setRequireCompress(true) + .setNetworkTimeoutInMilli(0) + .setOcspMode(OCSPMode.FAIL_OPEN) + .setSFSession(sfSession) + .setCommand(PUT_COMMAND) + .build()); + } catch (SnowflakeSQLException err) { + Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); + Assert.assertTrue( + err.getMessage() + .contains("JDBC driver internal error: error encountered for compression")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -312,46 +307,43 @@ public void testCompressStreamWithGzipException() throws Exception { @Test public void testCompressStreamWithGzipNoDigestException() throws Exception { - Connection con = null; // inject the IOException SnowflakeFileTransferAgent.setInjectedFileTransferException(new IOException()); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - - List metadataList = sfAgent.getFileTransferMetadatas(); - SnowflakeFileTransferMetadataV1 metadata = - (SnowflakeFileTransferMetadataV1) metadataList.get(0); - metadata.setEncryptionMaterial(null, null, null); - - String srcPath = getFullPathFileInResource(TEST_DATA_FILE); - - InputStream inputStream = new FileInputStream(srcPath); - SnowflakeFileTransferAgent.uploadWithoutConnection( - SnowflakeFileTransferConfig.Builder.newInstance() - .setSnowflakeFileTransferMetadata(metadata) - .setUploadStream(inputStream) - .setRequireCompress(true) - .setNetworkTimeoutInMilli(0) - .setOcspMode(OCSPMode.FAIL_OPEN) - .setSFSession(sfSession) - .setCommand(PUT_COMMAND) - .build()); - } catch (SnowflakeSQLException err) { - Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); - Assert.assertTrue( - err.getMessage() - .contains("JDBC driver internal error: error encountered for compression")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + List metadataList = sfAgent.getFileTransferMetadatas(); + SnowflakeFileTransferMetadataV1 metadata = + (SnowflakeFileTransferMetadataV1) metadataList.get(0); + metadata.setEncryptionMaterial(null, null, null); + + String srcPath = getFullPathFileInResource(TEST_DATA_FILE); + + InputStream inputStream = new FileInputStream(srcPath); + SnowflakeFileTransferAgent.uploadWithoutConnection( + SnowflakeFileTransferConfig.Builder.newInstance() + .setSnowflakeFileTransferMetadata(metadata) + .setUploadStream(inputStream) + .setRequireCompress(true) + .setNetworkTimeoutInMilli(0) + .setOcspMode(OCSPMode.FAIL_OPEN) + .setSFSession(sfSession) + .setCommand(PUT_COMMAND) + .build()); + } catch (SnowflakeSQLException err) { + Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); + Assert.assertTrue( + err.getMessage() + .contains("JDBC driver internal error: error encountered for compression")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -359,46 +351,43 @@ public void testCompressStreamWithGzipNoDigestException() throws Exception { @Test public void testUploadWithoutConnectionException() throws Exception { - Connection con = null; // inject the IOException SnowflakeFileTransferAgent.setInjectedFileTransferException( new Exception("Exception encountered during file upload: failed to push to remote store")); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - - List metadataList = sfAgent.getFileTransferMetadatas(); - SnowflakeFileTransferMetadataV1 metadata = - (SnowflakeFileTransferMetadataV1) metadataList.get(0); - - String srcPath = getFullPathFileInResource(TEST_DATA_FILE); - - InputStream inputStream = new FileInputStream(srcPath); - SnowflakeFileTransferAgent.uploadWithoutConnection( - SnowflakeFileTransferConfig.Builder.newInstance() - .setSnowflakeFileTransferMetadata(metadata) - .setUploadStream(inputStream) - .setRequireCompress(true) - .setNetworkTimeoutInMilli(0) - .setOcspMode(OCSPMode.FAIL_OPEN) - .setSFSession(sfSession) - .setCommand(PUT_COMMAND) - .build()); - } catch (Exception err) { - Assert.assertTrue( - err.getMessage() - .contains( - "Exception encountered during file upload: failed to push to remote store")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + List metadataList = sfAgent.getFileTransferMetadatas(); + SnowflakeFileTransferMetadataV1 metadata = + (SnowflakeFileTransferMetadataV1) metadataList.get(0); + + String srcPath = getFullPathFileInResource(TEST_DATA_FILE); + + InputStream inputStream = new FileInputStream(srcPath); + SnowflakeFileTransferAgent.uploadWithoutConnection( + SnowflakeFileTransferConfig.Builder.newInstance() + .setSnowflakeFileTransferMetadata(metadata) + .setUploadStream(inputStream) + .setRequireCompress(true) + .setNetworkTimeoutInMilli(0) + .setOcspMode(OCSPMode.FAIL_OPEN) + .setSFSession(sfSession) + .setCommand(PUT_COMMAND) + .build()); + } catch (Exception err) { + Assert.assertTrue( + err.getMessage() + .contains( + "Exception encountered during file upload: failed to push to remote store")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -406,73 +395,64 @@ public void testUploadWithoutConnectionException() throws Exception { @Test public void testInitFileMetadataFileNotFound() throws Exception { - Connection con = null; - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - - sfAgent.execute(); - } catch (SnowflakeSQLException err) { - Assert.assertEquals(200008, err.getErrorCode()); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + sfAgent.execute(); + } catch (SnowflakeSQLException err) { + Assert.assertEquals(200008, err.getErrorCode()); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } } @Test public void testInitFileMetadataFileIsDirectory() throws Exception { - Connection con = null; - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - String srcPath = - getFullPathFileInResource(""); // will pull the resources directory without a file - String command = "put file://" + srcPath + " @testStage"; - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - sfAgent.execute(); - } catch (SnowflakeSQLException err) { - Assert.assertEquals(200009, err.getErrorCode()); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + String srcPath = + getFullPathFileInResource(""); // will pull the resources directory without a file + String command = "put file://" + srcPath + " @testStage"; + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + sfAgent.execute(); + } catch (SnowflakeSQLException err) { + Assert.assertEquals(200009, err.getErrorCode()); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } } @Test public void testCompareAndSkipFilesException() throws Exception { - Connection con = null; // inject the NoSuchAlgorithmException SnowflakeFileTransferAgent.setInjectedFileTransferException(new NoSuchAlgorithmException()); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - - sfAgent.execute(); - } catch (SnowflakeSQLException err) { - Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); - Assert.assertTrue(err.getMessage().contains("Error reading:")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + + sfAgent.execute(); + } catch (SnowflakeSQLException err) { + Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); + Assert.assertTrue(err.getMessage().contains("Error reading:")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -480,24 +460,22 @@ public void testCompareAndSkipFilesException() throws Exception { @Test public void testParseCommandException() throws SQLException { - Connection con = null; // inject the SnowflakeSQLException SnowflakeFileTransferAgent.setInjectedFileTransferException( new SnowflakeSQLException("invalid data")); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - } catch (SnowflakeSQLException err) { - Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); - Assert.assertTrue(err.getMessage().contains("Failed to parse the locations")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + } catch (SnowflakeSQLException err) { + Assert.assertEquals((long) ErrorCode.INTERNAL_ERROR.getMessageCode(), err.getErrorCode()); + Assert.assertTrue(err.getMessage().contains("Failed to parse the locations")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -505,63 +483,58 @@ public void testParseCommandException() throws SQLException { @Test public void testPopulateStatusRowsWithSortOn() throws Exception { - Connection con = null; - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - statement.execute("set-sf-property sort on"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - - // upload files orders_101.csv and orders_100.csv - String command = "PUT file://" + getFullPathFileInResource("") + "/orders_10*.csv @testStage"; - SnowflakeFileTransferAgent sfAgent1 = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - sfAgent1.execute(); // upload files - - // check that source files were sorted - assertEquals(2, sfAgent1.statusRows.size()); - assertEquals("orders_100.csv", sfAgent1.getNextRow().get(0).toString()); - - String getCommand = "GET @testStage file:///tmp"; - SnowflakeFileTransferAgent sfAgent2 = - new SnowflakeFileTransferAgent(getCommand, sfSession, new SFStatement(sfSession)); - sfAgent2.execute(); - // check that files are sorted on download - assertEquals(2, sfAgent2.statusRows.size()); - assertEquals("orders_100.csv.gz", sfAgent2.getNextRow().get(0).toString()); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + statement.execute("set-sf-property sort on"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + + // upload files orders_101.csv and orders_100.csv + String command = + "PUT file://" + getFullPathFileInResource("") + "/orders_10*.csv @testStage"; + SnowflakeFileTransferAgent sfAgent1 = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + sfAgent1.execute(); // upload files + + // check that source files were sorted + assertEquals(2, sfAgent1.statusRows.size()); + assertEquals("orders_100.csv", sfAgent1.getNextRow().get(0).toString()); + + String getCommand = "GET @testStage file:///tmp"; + SnowflakeFileTransferAgent sfAgent2 = + new SnowflakeFileTransferAgent(getCommand, sfSession, new SFStatement(sfSession)); + sfAgent2.execute(); + // check that files are sorted on download + assertEquals(2, sfAgent2.statusRows.size()); + assertEquals("orders_100.csv.gz", sfAgent2.getNextRow().get(0).toString()); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } } @Test public void testListObjectsStorageException() throws Exception { - Connection con = null; // inject the StorageProviderException SnowflakeFileTransferAgent.setInjectedFileTransferException( new StorageProviderException(new Exception("could not list objects"))); - try { - con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("create or replace stage testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - - sfAgent.execute(); - } catch (SnowflakeSQLException err) { - Assert.assertEquals(200016, err.getErrorCode()); - Assert.assertTrue(err.getMessage().contains("Encountered exception during listObjects")); - } finally { - if (con != null) { - con.createStatement().execute("DROP STAGE if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + + sfAgent.execute(); + } catch (SnowflakeSQLException err) { + Assert.assertEquals(200016, err.getErrorCode()); + Assert.assertTrue(err.getMessage().contains("Encountered exception during listObjects")); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -572,75 +545,73 @@ public void testUploadStreamInterruptedException() throws IOException, SQLExcept final String DEST_PREFIX = TEST_UUID + "/testUploadStream"; // inject the InterruptedException SnowflakeFileTransferAgent.setInjectedFileTransferException(new InterruptedException()); - Connection connection = null; - Statement statement = null; - try { - connection = getConnection(); - - statement = connection.createStatement(); - - FileBackedOutputStream outputStream = new FileBackedOutputStream(1000000); - outputStream.write("hello".getBytes(StandardCharsets.UTF_8)); - outputStream.flush(); - - // upload the data to user stage under testUploadStream with name hello.txt - connection - .unwrap(SnowflakeConnection.class) - .uploadStream( - "~", DEST_PREFIX, outputStream.asByteSource().openStream(), "hello.txt", false); - - } catch (SnowflakeSQLLoggedException err) { - Assert.assertEquals(200003, err.getErrorCode()); - } finally { - if (statement != null) { + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + FileBackedOutputStream outputStream = new FileBackedOutputStream(1000000); + outputStream.write("hello".getBytes(StandardCharsets.UTF_8)); + outputStream.flush(); + + // upload the data to user stage under testUploadStream with name hello.txt + connection + .unwrap(SnowflakeConnection.class) + .uploadStream( + "~", DEST_PREFIX, outputStream.asByteSource().openStream(), "hello.txt", false); + + } catch (SnowflakeSQLLoggedException err) { + Assert.assertEquals(200003, err.getErrorCode()); + } finally { statement.execute("rm @~/" + DEST_PREFIX); - statement.close(); } - closeSQLObjects(statement, connection); } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); } @Test public void testFileTransferStageInfo() throws SQLException { - Connection con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); - - StageInfo stageInfo = sfAgent.getStageInfo(); - assertEquals(sfAgent.getStageCredentials(), stageInfo.getCredentials()); - assertEquals(sfAgent.getStageLocation(), stageInfo.getLocation()); - - statement.execute("drop stage if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(PUT_COMMAND, sfSession, new SFStatement(sfSession)); + + StageInfo stageInfo = sfAgent.getStageInfo(); + assertEquals(sfAgent.getStageCredentials(), stageInfo.getCredentials()); + assertEquals(sfAgent.getStageLocation(), stageInfo.getLocation()); + } finally { + statement.execute("drop stage if exists testStage"); + } + } } @Test public void testFileTransferMappingFromSourceFile() throws SQLException { - Connection con = getConnection(); - Statement statement = con.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); - - String command = "PUT file://" + getFullPathFileInResource("") + "/orders_10*.csv @testStage"; - SnowflakeFileTransferAgent sfAgent1 = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - sfAgent1.execute(); - - SnowflakeFileTransferAgent sfAgent2 = - new SnowflakeFileTransferAgent( - "GET @testStage file:///tmp/", sfSession, new SFStatement(sfSession)); - - assertEquals(2, sfAgent2.getSrcToMaterialsMap().size()); - assertEquals(2, sfAgent2.getSrcToPresignedUrlMap().size()); - - statement.execute("drop stage if exists testStage"); - con.close(); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + SFSession sfSession = con.unwrap(SnowflakeConnectionV1.class).getSfSession(); + + String command = + "PUT file://" + getFullPathFileInResource("") + "/orders_10*.csv @testStage"; + SnowflakeFileTransferAgent sfAgent1 = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + sfAgent1.execute(); + + SnowflakeFileTransferAgent sfAgent2 = + new SnowflakeFileTransferAgent( + "GET @testStage file:///tmp/", sfSession, new SFStatement(sfSession)); + + assertEquals(2, sfAgent2.getSrcToMaterialsMap().size()); + assertEquals(2, sfAgent2.getSrcToPresignedUrlMap().size()); + } finally { + statement.execute("drop stage if exists testStage"); + } + } } @Test @@ -648,25 +619,20 @@ public void testUploadFileCallableFileNotFound() throws Exception { // inject the FileNotFoundException SnowflakeFileTransferAgent.setInjectedFileTransferException( new FileNotFoundException("file does not exist")); - Connection connection = null; - Statement statement = null; - try { - connection = getConnection(); - - statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); - - String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); - sfAgent.execute(); - } catch (Exception err) { - assertEquals(err.getCause(), instanceOf(FileNotFoundException.class)); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists testStage"); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); + + String command = "PUT file://" + getFullPathFileInResource(TEST_DATA_FILE) + " @testStage"; + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(command, sfSession, new SFStatement(sfSession)); + sfAgent.execute(); + } catch (Exception err) { + assertEquals(err.getCause(), instanceOf(FileNotFoundException.class)); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } SnowflakeFileTransferAgent.setInjectedFileTransferException(null); @@ -674,64 +640,59 @@ public void testUploadFileCallableFileNotFound() throws Exception { @Test public void testUploadFileStreamWithNoOverwrite() throws Exception { - Connection connection = null; - - try { - connection = getConnection(); - Statement statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - - uploadFileToStageUsingStream(connection, false); - ResultSet resultSet = statement.executeQuery("LIST @testStage"); - resultSet.next(); - String expectedValue = resultSet.getString("last_modified"); - - Thread.sleep(1000); // add 1 sec delay between uploads. - - uploadFileToStageUsingStream(connection, false); - resultSet = statement.executeQuery("LIST @testStage"); - resultSet.next(); - String actualValue = resultSet.getString("last_modified"); - - assertTrue(expectedValue.equals(actualValue)); - } catch (Exception e) { - Assert.fail("testUploadFileStreamWithNoOverwrite failed " + e.getMessage()); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists testStage"); - connection.close(); + String expectedValue = null; + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + + uploadFileToStageUsingStream(connection, false); + try (ResultSet resultSet = statement.executeQuery("LIST @testStage")) { + assertTrue(resultSet.next()); + expectedValue = resultSet.getString("last_modified"); + } + Thread.sleep(1000); // add 1 sec delay between uploads. + + uploadFileToStageUsingStream(connection, false); + try (ResultSet resultSet = statement.executeQuery("LIST @testStage")) { + assertTrue(resultSet.next()); + String actualValue = resultSet.getString("last_modified"); + assertEquals(expectedValue, actualValue); + } + } catch (Exception e) { + Assert.fail("testUploadFileStreamWithNoOverwrite failed " + e.getMessage()); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } } @Test public void testUploadFileStreamWithOverwrite() throws Exception { - Connection connection = null; - - try { - connection = getConnection(); - Statement statement = connection.createStatement(); - statement.execute("CREATE OR REPLACE STAGE testStage"); - - uploadFileToStageUsingStream(connection, true); - ResultSet resultSet = statement.executeQuery("LIST @testStage"); - resultSet.next(); - String expectedValue = resultSet.getString("last_modified"); - - Thread.sleep(1000); // add 1 sec delay between uploads. - - uploadFileToStageUsingStream(connection, true); - resultSet = statement.executeQuery("LIST @testStage"); - resultSet.next(); - String actualValue = resultSet.getString("last_modified"); - - assertFalse(expectedValue.equals(actualValue)); - } catch (Exception e) { - Assert.fail("testUploadFileStreamWithNoOverwrite failed " + e.getMessage()); - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists testStage"); - connection.close(); + String expectedValue = null; + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("CREATE OR REPLACE STAGE testStage"); + + uploadFileToStageUsingStream(connection, true); + try (ResultSet resultSet = statement.executeQuery("LIST @testStage")) { + assertTrue(resultSet.next()); + expectedValue = resultSet.getString("last_modified"); + } + Thread.sleep(1000); // add 1 sec delay between uploads. + + uploadFileToStageUsingStream(connection, true); + try (ResultSet resultSet = statement.executeQuery("LIST @testStage")) { + assertTrue(resultSet.next()); + String actualValue = resultSet.getString("last_modified"); + + assertFalse(expectedValue.equals(actualValue)); + } + } catch (Exception e) { + Assert.fail("testUploadFileStreamWithNoOverwrite failed " + e.getMessage()); + } finally { + statement.execute("DROP STAGE if exists testStage"); } } } @@ -739,71 +700,67 @@ public void testUploadFileStreamWithOverwrite() throws Exception { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testGetS3StorageObjectMetadata() throws Throwable { - Connection connection = null; - try { - connection = getConnection("s3testaccount"); - Statement statement = connection.createStatement(); - + try (Connection connection = getConnection("s3testaccount"); + Statement statement = connection.createStatement()) { // create a stage to put the file in - statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); - - SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); - - // Test put file with internal compression - String putCommand = "put file:///dummy/path/file1.gz @" + OBJ_META_STAGE; - SnowflakeFileTransferAgent sfAgent = - new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); - List metadata = sfAgent.getFileTransferMetadatas(); - - String srcPath = getFullPathFileInResource(TEST_DATA_FILE); - for (SnowflakeFileTransferMetadata oneMetadata : metadata) { - InputStream inputStream = new FileInputStream(srcPath); - - SnowflakeFileTransferAgent.uploadWithoutConnection( - SnowflakeFileTransferConfig.Builder.newInstance() - .setSnowflakeFileTransferMetadata(oneMetadata) - .setUploadStream(inputStream) - .setRequireCompress(true) - .setNetworkTimeoutInMilli(0) - .setOcspMode(OCSPMode.FAIL_OPEN) - .setSFSession(sfSession) - .setCommand(putCommand) - .build()); - - SnowflakeStorageClient client = - StorageClientFactory.getFactory() - .createClient( - ((SnowflakeFileTransferMetadataV1) oneMetadata).getStageInfo(), - 1, - null, - /*session = */ null); - - String location = - ((SnowflakeFileTransferMetadataV1) oneMetadata).getStageInfo().getLocation(); - int idx = location.indexOf('/'); - String remoteStageLocation = location.substring(0, idx); - String path = location.substring(idx + 1) + "file1.gz"; - StorageObjectMetadata meta = client.getObjectMetadata(remoteStageLocation, path); - - ObjectMetadata s3Meta = new ObjectMetadata(); - s3Meta.setContentLength(meta.getContentLength()); - s3Meta.setContentEncoding(meta.getContentEncoding()); - s3Meta.setUserMetadata(meta.getUserMetadata()); - - S3StorageObjectMetadata s3Metadata = new S3StorageObjectMetadata(s3Meta); - RemoteStoreFileEncryptionMaterial encMat = sfAgent.getEncryptionMaterial().get(0); - Map matDesc = - mapper.readValue(s3Metadata.getUserMetadata().get("x-amz-matdesc"), Map.class); - - assertEquals(encMat.getQueryId(), matDesc.get("queryId")); - assertEquals(encMat.getSmkId().toString(), matDesc.get("smkId")); - assertEquals(1360, s3Metadata.getContentLength()); - assertEquals("gzip", s3Metadata.getContentEncoding()); - } - } finally { - if (connection != null) { - connection.createStatement().execute("DROP STAGE if exists " + OBJ_META_STAGE); - connection.close(); + try { + statement.execute("CREATE OR REPLACE STAGE " + OBJ_META_STAGE); + + SFSession sfSession = connection.unwrap(SnowflakeConnectionV1.class).getSfSession(); + + // Test put file with internal compression + String putCommand = "put file:///dummy/path/file1.gz @" + OBJ_META_STAGE; + SnowflakeFileTransferAgent sfAgent = + new SnowflakeFileTransferAgent(putCommand, sfSession, new SFStatement(sfSession)); + List metadata = sfAgent.getFileTransferMetadatas(); + + String srcPath = getFullPathFileInResource(TEST_DATA_FILE); + for (SnowflakeFileTransferMetadata oneMetadata : metadata) { + InputStream inputStream = new FileInputStream(srcPath); + + SnowflakeFileTransferAgent.uploadWithoutConnection( + SnowflakeFileTransferConfig.Builder.newInstance() + .setSnowflakeFileTransferMetadata(oneMetadata) + .setUploadStream(inputStream) + .setRequireCompress(true) + .setNetworkTimeoutInMilli(0) + .setOcspMode(OCSPMode.FAIL_OPEN) + .setSFSession(sfSession) + .setCommand(putCommand) + .build()); + + SnowflakeStorageClient client = + StorageClientFactory.getFactory() + .createClient( + ((SnowflakeFileTransferMetadataV1) oneMetadata).getStageInfo(), + 1, + null, + /*session = */ null); + + String location = + ((SnowflakeFileTransferMetadataV1) oneMetadata).getStageInfo().getLocation(); + int idx = location.indexOf('/'); + String remoteStageLocation = location.substring(0, idx); + String path = location.substring(idx + 1) + "file1.gz"; + StorageObjectMetadata meta = client.getObjectMetadata(remoteStageLocation, path); + + ObjectMetadata s3Meta = new ObjectMetadata(); + s3Meta.setContentLength(meta.getContentLength()); + s3Meta.setContentEncoding(meta.getContentEncoding()); + s3Meta.setUserMetadata(meta.getUserMetadata()); + + S3StorageObjectMetadata s3Metadata = new S3StorageObjectMetadata(s3Meta); + RemoteStoreFileEncryptionMaterial encMat = sfAgent.getEncryptionMaterial().get(0); + Map matDesc = + mapper.readValue(s3Metadata.getUserMetadata().get("x-amz-matdesc"), Map.class); + + assertEquals(encMat.getQueryId(), matDesc.get("queryId")); + assertEquals(encMat.getSmkId().toString(), matDesc.get("smkId")); + assertEquals(1360, s3Metadata.getContentLength()); + assertEquals("gzip", s3Metadata.getContentEncoding()); + } + } finally { + statement.execute("DROP STAGE if exists " + OBJ_META_STAGE); } } } @@ -832,10 +789,6 @@ private void uploadFileToStageUsingStream(Connection connection, boolean overwri @Test public void testUploadFileWithTildeInFolderName() throws SQLException, IOException { - Connection connection = null; - Statement statement = null; - ResultSet resultSet = null; - Writer writer = null; Path topDataDir = null; try { @@ -847,47 +800,40 @@ public void testUploadFileWithTildeInFolderName() throws SQLException, IOExcepti // create a test data File dataFile = new File(subDir.toFile(), "test.txt"); - writer = + try (Writer writer = new BufferedWriter( new OutputStreamWriter( Files.newOutputStream(Paths.get(dataFile.getCanonicalPath())), - StandardCharsets.UTF_8)); - writer.write("1,test1"); - writer.close(); - - connection = getConnection(); - statement = connection.createStatement(); - statement.execute("create or replace stage testStage"); - String sql = String.format("PUT 'file://%s' @testStage", dataFile.getCanonicalPath()); - - // Escape backslashes. This must be done by the application. - sql = sql.replaceAll("\\\\", "\\\\\\\\"); - resultSet = statement.executeQuery(sql); - while (resultSet.next()) { - assertEquals("UPLOADED", resultSet.getString("status")); - } - } finally { - if (connection != null) { - connection.createStatement().execute("drop stage if exists testStage"); + StandardCharsets.UTF_8))) { + writer.write("1,test1"); } - closeSQLObjects(resultSet, statement, connection); - if (writer != null) { - writer.close(); + + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + String sql = String.format("PUT 'file://%s' @testStage", dataFile.getCanonicalPath()); + + // Escape backslashes. This must be done by the application. + sql = sql.replaceAll("\\\\", "\\\\\\\\"); + try (ResultSet resultSet = statement.executeQuery(sql)) { + while (resultSet.next()) { + assertEquals("UPLOADED", resultSet.getString("status")); + } + } + } finally { + statement.execute("drop stage if exists testStage"); + } } + } finally { FileUtils.deleteDirectory(topDataDir.toFile()); } } @Test public void testUploadWithTildeInPath() throws SQLException, IOException { - Connection connection = null; - Statement statement = null; - ResultSet resultSet = null; - Writer writer = null; Path subDir = null; - try { - String homeDir = systemGetProperty("user.home"); // create sub directory where the name includes ~ @@ -895,30 +841,29 @@ public void testUploadWithTildeInPath() throws SQLException, IOException { // create a test data File dataFile = new File(subDir.toFile(), "test.txt"); - writer = + try (Writer writer = new BufferedWriter( new OutputStreamWriter( Files.newOutputStream(Paths.get(dataFile.getCanonicalPath())), - StandardCharsets.UTF_8)); - writer.write("1,test1"); - writer.close(); - - connection = getConnection(); - statement = connection.createStatement(); - statement.execute("create or replace stage testStage"); - - resultSet = statement.executeQuery("PUT 'file://~/snowflake/test.txt' @testStage"); - while (resultSet.next()) { - assertEquals("UPLOADED", resultSet.getString("status")); - } - } finally { - if (connection != null) { - connection.createStatement().execute("drop stage if exists testStage"); + StandardCharsets.UTF_8))) { + writer.write("1,test1"); } - closeSQLObjects(resultSet, statement, connection); - if (writer != null) { - writer.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("create or replace stage testStage"); + + try (ResultSet resultSet = + statement.executeQuery("PUT 'file://~/snowflake/test.txt' @testStage")) { + while (resultSet.next()) { + assertEquals("UPLOADED", resultSet.getString("status")); + } + } + } finally { + statement.execute("drop stage if exists testStage"); + } } + } finally { FileUtils.deleteDirectory(subDir.toFile()); } } diff --git a/src/test/java/net/snowflake/client/jdbc/GCPLargeResult.java b/src/test/java/net/snowflake/client/jdbc/GCPLargeResult.java index 7cb79b404..b2c316d50 100644 --- a/src/test/java/net/snowflake/client/jdbc/GCPLargeResult.java +++ b/src/test/java/net/snowflake/client/jdbc/GCPLargeResult.java @@ -37,17 +37,18 @@ Connection init() throws SQLException { @Test public void testLargeResultSetGCP() throws Throwable { - try (Connection con = init()) { - PreparedStatement stmt = - con.prepareStatement( - "select seq8(), randstr(1000, random()) from table(generator(rowcount=>1000))"); + try (Connection con = init(); + PreparedStatement stmt = + con.prepareStatement( + "select seq8(), randstr(1000, random()) from table(generator(rowcount=>1000))")) { stmt.setMaxRows(999); - ResultSet rset = stmt.executeQuery(); - int cnt = 0; - while (rset.next()) { - ++cnt; + try (ResultSet rset = stmt.executeQuery()) { + int cnt = 0; + while (rset.next()) { + ++cnt; + } + assertEquals(cnt, 999); } - assertEquals(cnt, 999); } } } diff --git a/src/test/java/net/snowflake/client/jdbc/HeartbeatAsyncLatestIT.java b/src/test/java/net/snowflake/client/jdbc/HeartbeatAsyncLatestIT.java index c59ddc987..e7217f695 100644 --- a/src/test/java/net/snowflake/client/jdbc/HeartbeatAsyncLatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/HeartbeatAsyncLatestIT.java @@ -39,21 +39,17 @@ public class HeartbeatAsyncLatestIT extends HeartbeatIT { @Override protected void submitQuery(boolean useKeepAliveSession, int queryIdx) throws SQLException, InterruptedException { - Connection connection = null; - ResultSet resultSet = null; - try { - Properties sessionParams = new Properties(); - sessionParams.put( - "CLIENT_SESSION_KEEP_ALIVE", - useKeepAliveSession ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); + Properties sessionParams = new Properties(); + sessionParams.put( + "CLIENT_SESSION_KEEP_ALIVE", + useKeepAliveSession ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); - connection = getConnection(sessionParams); - - Statement stmt = connection.createStatement(); - // Query will take 5 seconds to run, but ResultSet will be returned immediately - resultSet = - stmt.unwrap(SnowflakeStatement.class) - .executeAsyncQuery("SELECT count(*) FROM TABLE(generator(timeLimit => 5))"); + try (Connection connection = getConnection(sessionParams); + Statement stmt = connection.createStatement(); + // Query will take 5 seconds to run, but ResultSet will be returned immediately + ResultSet resultSet = + stmt.unwrap(SnowflakeStatement.class) + .executeAsyncQuery("SELECT count(*) FROM TABLE(generator(timeLimit => 5))")) { Thread.sleep(61000); // sleep 61 seconds to await original session expiration time QueryStatus qs = resultSet.unwrap(SnowflakeResultSet.class).getStatus(); // Ensure query succeeded. Avoid flaky test failure by waiting until query is complete to @@ -69,10 +65,6 @@ protected void submitQuery(boolean useKeepAliveSession, int queryIdx) assertTrue(resultSet.next()); assertFalse(resultSet.next()); logger.fine("Query " + queryIdx + " passed "); - - } finally { - resultSet.close(); - connection.close(); } } @@ -92,16 +84,12 @@ public void testAsynchronousQueryFailure() throws Exception { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testIsValidWithInvalidSession() throws Exception { - Connection connection = null; - try { - connection = getConnection(); + try (Connection connection = getConnection()) { // assert that connection starts out valid assertTrue(connection.isValid(5)); Thread.sleep(61000); // sleep 61 seconds to await session expiration time // assert that connection is no longer valid after session has expired assertFalse(connection.isValid(5)); - } finally { - connection.close(); } } } diff --git a/src/test/java/net/snowflake/client/jdbc/HeartbeatIT.java b/src/test/java/net/snowflake/client/jdbc/HeartbeatIT.java index 16e8364d6..eb41ce76f 100644 --- a/src/test/java/net/snowflake/client/jdbc/HeartbeatIT.java +++ b/src/test/java/net/snowflake/client/jdbc/HeartbeatIT.java @@ -46,15 +46,14 @@ public class HeartbeatIT extends AbstractDriverIT { @BeforeClass public static void setUpClass() throws Exception { if (!RunningOnGithubAction.isRunningOnGithubAction()) { - Connection connection = getSnowflakeAdminConnection(); - connection - .createStatement() - .execute( - "alter system set" - + " master_token_validity=60" - + ",session_token_validity=20" - + ",SESSION_RECORD_ACCESS_INTERVAL_SECS=1"); - connection.close(); + try (Connection connection = getSnowflakeAdminConnection(); + Statement statement = connection.createStatement()) { + statement.execute( + "alter system set" + + " master_token_validity=60" + + ",session_token_validity=20" + + ",SESSION_RECORD_ACCESS_INTERVAL_SECS=1"); + } } } @@ -65,15 +64,14 @@ public static void setUpClass() throws Exception { @AfterClass public static void tearDownClass() throws Exception { if (!RunningOnGithubAction.isRunningOnGithubAction()) { - Connection connection = getSnowflakeAdminConnection(); - connection - .createStatement() - .execute( - "alter system set" - + " master_token_validity=default" - + ",session_token_validity=default" - + ",SESSION_RECORD_ACCESS_INTERVAL_SECS=default"); - connection.close(); + try (Connection connection = getSnowflakeAdminConnection(); + Statement statement = connection.createStatement()) { + statement.execute( + "alter system set" + + " master_token_validity=default" + + ",session_token_validity=default" + + ",SESSION_RECORD_ACCESS_INTERVAL_SECS=default"); + } } } @@ -87,34 +85,28 @@ public static void tearDownClass() throws Exception { */ protected void submitQuery(boolean useKeepAliveSession, int queryIdx) throws SQLException, InterruptedException { - Connection connection = null; - Statement statement = null; - ResultSet resultSet = null; ResultSetMetaData resultSetMetaData; - try { - Properties sessionParams = new Properties(); - sessionParams.put( - "CLIENT_SESSION_KEEP_ALIVE", - useKeepAliveSession ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); + Properties sessionParams = new Properties(); + sessionParams.put( + "CLIENT_SESSION_KEEP_ALIVE", + useKeepAliveSession ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); - connection = getConnection(sessionParams); - statement = connection.createStatement(); + try (Connection connection = getConnection(sessionParams); + Statement statement = connection.createStatement()) { Thread.sleep(61000); // sleep 61 seconds - resultSet = statement.executeQuery("SELECT 1"); - resultSetMetaData = resultSet.getMetaData(); + try (ResultSet resultSet = statement.executeQuery("SELECT 1")) { + resultSetMetaData = resultSet.getMetaData(); - // assert column count - assertEquals(1, resultSetMetaData.getColumnCount()); + // assert column count + assertEquals(1, resultSetMetaData.getColumnCount()); - // assert we get 1 row - assertTrue(resultSet.next()); + // assert we get 1 row + assertTrue(resultSet.next()); - logger.fine("Query " + queryIdx + " passed "); - statement.close(); - } finally { - closeSQLObjects(resultSet, statement, connection); + logger.fine("Query " + queryIdx + " passed "); + } } } diff --git a/src/test/java/net/snowflake/client/jdbc/MultiStatementIT.java b/src/test/java/net/snowflake/client/jdbc/MultiStatementIT.java index e12c3c5fb..c090bab03 100644 --- a/src/test/java/net/snowflake/client/jdbc/MultiStatementIT.java +++ b/src/test/java/net/snowflake/client/jdbc/MultiStatementIT.java @@ -31,356 +31,339 @@ public class MultiStatementIT extends BaseJDBCTest { public static Connection getConnection() throws SQLException { Connection conn = BaseJDBCTest.getConnection(); - Statement stmt = conn.createStatement(); - stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); - stmt.close(); + try (Statement stmt = conn.createStatement()) { + stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); + } return conn; } @Test public void testMultiStmtExecuteUpdateFail() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - String multiStmtQuery = - "select 1;\n" - + "create or replace temporary table test_multi (cola int);\n" - + "insert into test_multi VALUES (1), (2);\n" - + "select cola from test_multi order by cola asc"; - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); - try { - statement.executeUpdate(multiStmtQuery); - fail("executeUpdate should have failed because the first statement yields a result set"); - } catch (SQLException ex) { - assertThat( - ex.getErrorCode(), is(ErrorCode.UPDATE_FIRST_RESULT_NOT_UPDATE_COUNT.getMessageCode())); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + String multiStmtQuery = + "select 1;\n" + + "create or replace temporary table test_multi (cola int);\n" + + "insert into test_multi VALUES (1), (2);\n" + + "select cola from test_multi order by cola asc"; + + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); + try { + statement.executeUpdate(multiStmtQuery); + fail("executeUpdate should have failed because the first statement yields a result set"); + } catch (SQLException ex) { + assertThat( + ex.getErrorCode(), is(ErrorCode.UPDATE_FIRST_RESULT_NOT_UPDATE_COUNT.getMessageCode())); + } } - - statement.close(); - connection.close(); } @Test public void testMultiStmtExecuteQueryFail() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - String multiStmtQuery = - "create or replace temporary table test_multi (cola int);\n" - + "insert into test_multi VALUES (1), (2);\n" - + "select cola from test_multi order by cola asc"; - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); - try { - statement.executeQuery(multiStmtQuery); - fail("executeQuery should have failed because the first statement yields an update count"); - } catch (SQLException ex) { - assertThat( - ex.getErrorCode(), is(ErrorCode.QUERY_FIRST_RESULT_NOT_RESULT_SET.getMessageCode())); - } + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + String multiStmtQuery = + "create or replace temporary table test_multi (cola int);\n" + + "insert into test_multi VALUES (1), (2);\n" + + "select cola from test_multi order by cola asc"; - statement.close(); - connection.close(); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); + try { + statement.executeQuery(multiStmtQuery); + fail("executeQuery should have failed because the first statement yields an update count"); + } catch (SQLException ex) { + assertThat( + ex.getErrorCode(), is(ErrorCode.QUERY_FIRST_RESULT_NOT_RESULT_SET.getMessageCode())); + } + } } @Test public void testMultiStmtSetUnset() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - // setting session variable should propagate outside of query - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("set testvar = 1; select 1"); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - ResultSet rs = statement.executeQuery("select $testvar"); - rs.next(); - assertEquals(1, rs.getInt(1)); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { - // selecting unset variable should cause error - try { + // setting session variable should propagate outside of query statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("unset testvar; select $testvar"); - fail("Expected a failure"); - } catch (SQLException ex) { - assertEquals(SqlState.PLSQL_ERROR, ex.getSQLState()); - } + statement.execute("set testvar = 1; select 1"); - // unsetting session variable should propagate outside of query - try { statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("select $testvar"); - fail("Expected a failure"); - } catch (SQLException ex) { - assertEquals(SqlState.NO_DATA, ex.getSQLState()); + try (ResultSet rs = statement.executeQuery("select $testvar")) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + + // selecting unset variable should cause error + try { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("unset testvar; select $testvar"); + fail("Expected a failure"); + } catch (SQLException ex) { + assertEquals(SqlState.PLSQL_ERROR, ex.getSQLState()); + } + + // unsetting session variable should propagate outside of query + try { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("select $testvar"); + fail("Expected a failure"); + } catch (SQLException ex) { + assertEquals(SqlState.NO_DATA, ex.getSQLState()); + } + } } - - statement.close(); - connection.close(); } @Test public void testMultiStmtParseError() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.execute("set testvar = 1"); - try { - // fails in the antlr parser - statement.execute("garbage text; set testvar = 2"); - fail("Expected a compiler error to be thrown"); - } catch (SQLException ex) { - assertEquals(SqlState.SYNTAX_ERROR_OR_ACCESS_RULE_VIOLATION, ex.getSQLState()); - } + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { - ResultSet rs = statement.executeQuery("select $testvar"); - rs.next(); - assertEquals(1, rs.getInt(1)); + statement.execute("set testvar = 1"); + try { + // fails in the antlr parser + statement.execute("garbage text; set testvar = 2"); + fail("Expected a compiler error to be thrown"); + } catch (SQLException ex) { + assertEquals(SqlState.SYNTAX_ERROR_OR_ACCESS_RULE_VIOLATION, ex.getSQLState()); + } - statement.close(); - connection.close(); + try (ResultSet rs = statement.executeQuery("select $testvar")) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + } + } } @Test public void testMultiStmtExecError() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); + // fails during execution (javascript invokes statement where it gets typechecked) + statement.execute( + "set testvar = 1; select nonexistent_column from nonexistent_table; set testvar = 2"); + fail("Expected an execution error to be thrown"); + } catch (SQLException ex) { + assertEquals(SqlState.PLSQL_ERROR, ex.getSQLState()); + } - try { - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); - // fails during execution (javascript invokes statement where it gets typechecked) - statement.execute( - "set testvar = 1; select nonexistent_column from nonexistent_table; set testvar = 2"); - fail("Expected an execution error to be thrown"); - } catch (SQLException ex) { - assertEquals(SqlState.PLSQL_ERROR, ex.getSQLState()); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + try (ResultSet rs = statement.executeQuery("select $testvar")) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + } } - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - ResultSet rs = statement.executeQuery("select $testvar"); - rs.next(); - assertEquals(1, rs.getInt(1)); - - statement.close(); - connection.close(); } @Test public void testMultiStmtTempTable() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - String entry = "success"; - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute( - "create or replace temporary table test_multi (cola string); insert into test_multi values ('" - + entry - + "')"); - // temporary table should persist outside of the above statement - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - ResultSet rs = statement.executeQuery("select * from test_multi"); - rs.next(); - assertEquals(entry, rs.getString(1)); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + + String entry = "success"; + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute( + "create or replace temporary table test_multi (cola string); insert into test_multi values ('" + + entry + + "')"); + // temporary table should persist outside of the above statement + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + try (ResultSet rs = statement.executeQuery("select * from test_multi")) { + assertTrue(rs.next()); + assertEquals(entry, rs.getString(1)); + } + } } @Test public void testMultiStmtUseStmt() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - SFSession session = - statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { - String originalSchema = session.getSchema(); + SFSession session = + statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("use schema public; select 1"); - // current schema change should persist outside of the above statement + String originalSchema = session.getSchema(); - assertEquals("PUBLIC", session.getSchema()); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - ResultSet rs = statement.executeQuery("select current_schema()"); - rs.next(); - assertEquals("PUBLIC", rs.getString(1)); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute(String.format("use schema %s; select 1", originalSchema)); - // current schema change should persist outside of the above statement + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("use schema public; select 1"); + // current schema change should persist outside of the above statement - session = statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); - assertEquals(originalSchema, session.getSchema()); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - rs = statement.executeQuery("select current_schema()"); - rs.next(); - assertEquals(originalSchema, rs.getString(1)); + assertEquals("PUBLIC", session.getSchema()); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + try (ResultSet rs = statement.executeQuery("select current_schema()")) { + assertTrue(rs.next()); + assertEquals("PUBLIC", rs.getString(1)); + } + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute(String.format("use schema %s; select 1", originalSchema)); + // current schema change should persist outside of the above statement - statement.close(); - connection.close(); + session = statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); + assertEquals(originalSchema, session.getSchema()); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + try (ResultSet rs = statement.executeQuery("select current_schema()")) { + assertTrue(rs.next()); + assertEquals(originalSchema, rs.getString(1)); + } + } } @Test public void testMultiStmtAlterSessionParams() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - SFSession session = - statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); - - // we need an arbitrary parameter which is updated by the client after each query for this test - String param = "AUTOCOMMIT"; - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("alter session set " + param + "=false; select 1"); - assertFalse(session.getAutoCommit()); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("alter session set " + param + "=true; select 1"); - assertTrue(session.getAutoCommit()); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + + SFSession session = + statement.getConnection().unwrap(SnowflakeConnectionV1.class).getSfSession(); + + // we need an arbitrary parameter which is updated by the client after each query for this + // test + String param = "AUTOCOMMIT"; + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("alter session set " + param + "=false; select 1"); + assertFalse(session.getAutoCommit()); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("alter session set " + param + "=true; select 1"); + assertTrue(session.getAutoCommit()); + } } @Test public void testMultiStmtMultiLine() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - // these statements should not fail - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("select 1;\nselect 2"); - statement.execute("select \n 1; select 2"); - statement.execute("select \r\n 1; select 2"); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + // these statements should not fail + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("select 1;\nselect 2"); + statement.execute("select \n 1; select 2"); + statement.execute("select \r\n 1; select 2"); + } } @Test public void testMultiStmtQuotes() throws SQLException { // test various quotation usage and ensure they succeed - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute( - "create or replace temporary table \"test_multi\" (cola string); select * from \"test_multi\""); - statement.execute( - "create or replace temporary table `test_multi` (cola string); select * from `test_multi`"); - statement.execute("select 'str'; select 'str2'"); - statement.execute("select '\\` backticks'; select '\\\\` more `backticks`'"); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute( + "create or replace temporary table \"test_multi\" (cola string); select * from \"test_multi\""); + statement.execute( + "create or replace temporary table `test_multi` (cola string); select * from `test_multi`"); + statement.execute("select 'str'; select 'str2'"); + statement.execute("select '\\` backticks'; select '\\\\` more `backticks`'"); + } } @Test public void testMultiStmtCommitRollback() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.execute("create or replace table test_multi (cola string)"); - statement.execute("begin"); - statement.execute("insert into test_multi values ('abc')"); - // "commit" inside multistatement commits previous DML calls - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("insert into test_multi values ('def'); commit"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("rollback"); - ResultSet rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - statement.execute("begin"); - statement.execute("insert into test_multi values ('abc')"); - // "rollback" inside multistatement rolls back previous DML calls - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("insert into test_multi values ('def'); rollback"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("commit"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(0, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - // open transaction inside multistatement continues after - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("begin; insert into test_multi values ('abc')"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("insert into test_multi values ('def')"); - statement.execute("commit"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - // open transaction inside multistatement continues after - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("begin; insert into test_multi values ('abc')"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("insert into test_multi values ('def')"); - statement.execute("rollback"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(0, rs.getInt(1)); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + + statement.execute("create or replace table test_multi (cola string)"); + statement.execute("begin"); + statement.execute("insert into test_multi values ('abc')"); + // "commit" inside multistatement commits previous DML calls + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("insert into test_multi values ('def'); commit"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("rollback"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + } + + statement.execute("create or replace table test_multi (cola string)"); + statement.execute("begin"); + statement.execute("insert into test_multi values ('abc')"); + // "rollback" inside multistatement rolls back previous DML calls + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("insert into test_multi values ('def'); rollback"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("commit"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(0, rs.getInt(1)); + } + statement.execute("create or replace table test_multi (cola string)"); + // open transaction inside multistatement continues after + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("begin; insert into test_multi values ('abc')"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("insert into test_multi values ('def')"); + statement.execute("commit"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + } + statement.execute("create or replace table test_multi (cola string)"); + // open transaction inside multistatement continues after + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("begin; insert into test_multi values ('abc')"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("insert into test_multi values ('def')"); + statement.execute("rollback"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(0, rs.getInt(1)); + } + } } @Test public void testMultiStmtCommitRollbackNoAutocommit() throws SQLException { - Connection connection = getConnection(); - connection.setAutoCommit(false); - Statement statement = connection.createStatement(); - - statement.execute("create or replace table test_multi (cola string)"); - statement.execute("insert into test_multi values ('abc')"); - // "commit" inside multistatement commits previous DML calls - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("insert into test_multi values ('def'); commit"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("rollback"); - ResultSet rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - statement.execute("insert into test_multi values ('abc')"); - // "rollback" inside multistatement rolls back previous DML calls - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute("insert into test_multi values ('def'); rollback"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("commit"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(0, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - // open transaction inside multistatement continues after - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute( - "insert into test_multi values ('abc'); insert into test_multi values ('def')"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("commit"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - - statement.execute("create or replace table test_multi (cola string)"); - // open transaction inside multistatement continues after - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - statement.execute( - "insert into test_multi values ('abc'); insert into test_multi values ('def')"); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("rollback"); - rs = statement.executeQuery("select count(*) from test_multi"); - assertTrue(rs.next()); - assertEquals(0, rs.getInt(1)); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + connection.setAutoCommit(false); + statement.execute("create or replace table test_multi (cola string)"); + statement.execute("insert into test_multi values ('abc')"); + // "commit" inside multistatement commits previous DML calls + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("insert into test_multi values ('def'); commit"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("rollback"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + } + + statement.execute("create or replace table test_multi (cola string)"); + statement.execute("insert into test_multi values ('abc')"); + // "rollback" inside multistatement rolls back previous DML calls + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute("insert into test_multi values ('def'); rollback"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("commit"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(0, rs.getInt(1)); + } + + statement.execute("create or replace table test_multi (cola string)"); + // open transaction inside multistatement continues after + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute( + "insert into test_multi values ('abc'); insert into test_multi values ('def')"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("commit"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + } + statement.execute("create or replace table test_multi (cola string)"); + // open transaction inside multistatement continues after + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + statement.execute( + "insert into test_multi values ('abc'); insert into test_multi values ('def')"); + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("rollback"); + try (ResultSet rs = statement.executeQuery("select count(*) from test_multi")) { + assertTrue(rs.next()); + assertEquals(0, rs.getInt(1)); + } + } } @Test @@ -388,97 +371,102 @@ public void testMultiStmtLarge() throws SQLException { // this test verifies that multiple-statement support does not break // with many statements // it also ensures that results are returned in the correct order - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - StringBuilder multiStmtBuilder = new StringBuilder(); - String query = "SELECT %d;"; - for (int i = 0; i < 100; i++) { - multiStmtBuilder.append(String.format(query, i)); - } - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 100); - - assertTrue(statement.execute(multiStmtBuilder.toString())); - for (int i = 0; i < 100; i++) { - ResultSet rs = statement.getResultSet(); - assertNotNull(rs); - assertEquals(-1, statement.getUpdateCount()); - assertTrue(rs.next()); - assertEquals(i, rs.getInt(1)); - assertFalse(rs.next()); - - if (i != 99) { - assertTrue(statement.getMoreResults()); - } else { - assertFalse(statement.getMoreResults()); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + StringBuilder multiStmtBuilder = new StringBuilder(); + String query = "SELECT %d;"; + for (int i = 0; i < 100; i++) { + multiStmtBuilder.append(String.format(query, i)); + } + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 100); + + assertTrue(statement.execute(multiStmtBuilder.toString())); + for (int i = 0; i < 100; i++) { + try (ResultSet rs = statement.getResultSet()) { + assertNotNull(rs); + assertEquals(-1, statement.getUpdateCount()); + assertTrue(rs.next()); + assertEquals(i, rs.getInt(1)); + assertFalse(rs.next()); + + if (i != 99) { + assertTrue(statement.getMoreResults()); + } else { + assertFalse(statement.getMoreResults()); + } + } } } - - statement.close(); - connection.close(); } @Test public void testMultiStmtCountNotMatch() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - try { - statement.execute("select 1; select 2; select 3"); - fail(); - } catch (SQLException e) { - assertThat(e.getErrorCode(), is(8)); - } + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("select 1; select 2; select 3"); + fail(); + } catch (SQLException e) { + assertThat(e.getErrorCode(), is(8)); + } - try { - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); - statement.execute("select 1"); - fail(); - } catch (SQLException e) { - assertThat(e.getErrorCode(), is(8)); - } + try { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); + statement.execute("select 1"); + fail(); + } catch (SQLException e) { + assertThat(e.getErrorCode(), is(8)); + } - // 0 means any number of statement can be executed - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 0); - statement.execute("select 1; select 2; select 3"); + // 0 means any number of statement can be executed + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 0); + statement.execute("select 1; select 2; select 3"); + } } @Test @ConditionalIgnore(condition = RunningOnGithubAction.class) public void testInvalidParameterCount() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - ResultSet rs = statement.executeQuery("select current_account_locator()"); - rs.next(); - String accountName = rs.getString(1); - - rs = statement.executeQuery("select current_user()"); - rs.next(); - String userName = rs.getString(1); - - String[] testSuites = new String[5]; - testSuites[0] = - String.format("alter account %s set " + "multi_statement_count = 20", accountName); - testSuites[1] = - String.format("alter account %s set " + "multi_statement_count = -1", accountName); - testSuites[2] = String.format("alter user %s set " + "multi_statement_count = 20", userName); - testSuites[3] = String.format("alter user %s set " + "multi_statement_count = -1", userName); - testSuites[4] = "alter session set " + "multi_statement_count = -1"; - - int[] expectedErrorCodes = new int[5]; - expectedErrorCodes[0] = 1008; - expectedErrorCodes[1] = 1008; - expectedErrorCodes[2] = 1006; - expectedErrorCodes[3] = 1006; - expectedErrorCodes[4] = 1008; - - statement.execute("use role accountadmin"); - - for (int i = 0; i < testSuites.length; i++) { - try { - statement.execute(testSuites[i]); - Assert.fail(); - } catch (SQLException e) { - assertThat(e.getErrorCode(), is(expectedErrorCodes[i])); + String userName = null; + String accountName = null; + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + + try (ResultSet rs = statement.executeQuery("select current_account_locator()")) { + assertTrue(rs.next()); + accountName = rs.getString(1); + } + + try (ResultSet rs = statement.executeQuery("select current_user()")) { + assertTrue(rs.next()); + userName = rs.getString(1); + } + + String[] testSuites = new String[5]; + testSuites[0] = + String.format("alter account %s set " + "multi_statement_count = 20", accountName); + testSuites[1] = + String.format("alter account %s set " + "multi_statement_count = -1", accountName); + testSuites[2] = String.format("alter user %s set " + "multi_statement_count = 20", userName); + testSuites[3] = String.format("alter user %s set " + "multi_statement_count = -1", userName); + testSuites[4] = "alter session set " + "multi_statement_count = -1"; + + int[] expectedErrorCodes = new int[5]; + expectedErrorCodes[0] = 1008; + expectedErrorCodes[1] = 1008; + expectedErrorCodes[2] = 1006; + expectedErrorCodes[3] = 1006; + expectedErrorCodes[4] = 1008; + + statement.execute("use role accountadmin"); + + for (int i = 0; i < testSuites.length; i++) { + try { + statement.execute(testSuites[i]); + Assert.fail(); + } catch (SQLException e) { + assertThat(e.getErrorCode(), is(expectedErrorCodes[i])); + } } } } diff --git a/src/test/java/net/snowflake/client/jdbc/MultiStatementLatestIT.java b/src/test/java/net/snowflake/client/jdbc/MultiStatementLatestIT.java index c4e91e872..59f5ba795 100644 --- a/src/test/java/net/snowflake/client/jdbc/MultiStatementLatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/MultiStatementLatestIT.java @@ -29,302 +29,300 @@ public class MultiStatementLatestIT extends BaseJDBCTest { public static Connection getConnection() throws SQLException { Connection conn = BaseJDBCTest.getConnection(); - Statement stmt = conn.createStatement(); - stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); - stmt.close(); + try (Statement stmt = conn.createStatement()) { + stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); + } return conn; } @Test public void testMultiStmtExecute() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); - String multiStmtQuery = - "create or replace temporary table test_multi (cola int);\n" - + "insert into test_multi VALUES (1), (2);\n" - + "select cola from test_multi order by cola asc"; - - boolean hasResultSet = statement.execute(multiStmtQuery); - // first statement - assertFalse(hasResultSet); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // second statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(2, statement.getUpdateCount()); - - // third statement - assertTrue(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - ResultSet rs = statement.getResultSet(); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - assertFalse(rs.next()); - - assertFalse(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); + String multiStmtQuery = + "create or replace temporary table test_multi (cola int);\n" + + "insert into test_multi VALUES (1), (2);\n" + + "select cola from test_multi order by cola asc"; + + boolean hasResultSet = statement.execute(multiStmtQuery); + // first statement + assertFalse(hasResultSet); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // second statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(2, statement.getUpdateCount()); + + // third statement + assertTrue(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + try (ResultSet rs = statement.getResultSet()) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + assertFalse(rs.next()); + + assertFalse(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + } + } } @Test public void testMultiStmtTransaction() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.execute( - "create or replace table test_multi_txn(c1 number, c2 string)" + " as select 10, 'z'"); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); - String multiStmtQuery = - "begin;\n" - + "delete from test_multi_txn;\n" - + "insert into test_multi_txn values (1, 'a'), (2, 'b');\n" - + "commit"; - - boolean hasResultSet = statement.execute(multiStmtQuery); - // first statement - assertFalse(hasResultSet); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // second statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(1, statement.getUpdateCount()); - - // third statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(2, statement.getUpdateCount()); - - // fourth statement - assertFalse(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - assertFalse(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("drop table if exists test_multi_txn"); - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute( + "create or replace table test_multi_txn(c1 number, c2 string)" + " as select 10, 'z'"); + + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); + String multiStmtQuery = + "begin;\n" + + "delete from test_multi_txn;\n" + + "insert into test_multi_txn values (1, 'a'), (2, 'b');\n" + + "commit"; + + boolean hasResultSet = statement.execute(multiStmtQuery); + // first statement + assertFalse(hasResultSet); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // second statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(1, statement.getUpdateCount()); + + // third statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(2, statement.getUpdateCount()); + + // fourth statement + assertFalse(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + assertFalse(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + + } finally { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("drop table if exists test_multi_txn"); + } + } } @Test public void testMultiStmtExecuteUpdate() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - String multiStmtQuery = - "create or replace temporary table test_multi (cola int);\n" - + "insert into test_multi VALUES (1), (2);\n" - + "select cola from test_multi order by cola asc"; - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); - int rowCount = statement.executeUpdate(multiStmtQuery); - // first statement - assertEquals(0, rowCount); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // second statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(2, statement.getUpdateCount()); - - // third statement - assertTrue(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - ResultSet rs = statement.getResultSet(); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - assertFalse(rs.next()); - - assertFalse(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + String multiStmtQuery = + "create or replace temporary table test_multi (cola int);\n" + + "insert into test_multi VALUES (1), (2);\n" + + "select cola from test_multi order by cola asc"; + + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 3); + int rowCount = statement.executeUpdate(multiStmtQuery); + // first statement + assertEquals(0, rowCount); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // second statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(2, statement.getUpdateCount()); + + // third statement + assertTrue(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + try (ResultSet rs = statement.getResultSet()) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + assertFalse(rs.next()); + + assertFalse(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + } + } } @Test public void testMultiStmtTransactionRollback() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - - statement.execute( - "create or replace table test_multi_txn_rb(c1 number, c2 string)" + " as select 10, 'z'"); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); - String multiStmtQuery = - "begin;\n" - + "delete from test_multi_txn_rb;\n" - + "rollback;\n" - + "select count(*) from test_multi_txn_rb"; - - boolean hasResultSet = statement.execute(multiStmtQuery); - // first statement - assertFalse(hasResultSet); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // second statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(1, statement.getUpdateCount()); - - // third statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // fourth statement - assertTrue(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - ResultSet rs = statement.getResultSet(); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - assertFalse(rs.next()); - - assertFalse(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); - statement.execute("drop table if exists test_multi_txn_rb"); - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute( + "create or replace table test_multi_txn_rb(c1 number, c2 string)" + + " as select 10, 'z'"); + + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); + String multiStmtQuery = + "begin;\n" + + "delete from test_multi_txn_rb;\n" + + "rollback;\n" + + "select count(*) from test_multi_txn_rb"; + + boolean hasResultSet = statement.execute(multiStmtQuery); + // first statement + assertFalse(hasResultSet); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // second statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(1, statement.getUpdateCount()); + + // third statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // fourth statement + assertTrue(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + try (ResultSet rs = statement.getResultSet()) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + assertFalse(rs.next()); + + assertFalse(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + } + } finally { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 1); + statement.execute("drop table if exists test_multi_txn_rb"); + } + } } @Test public void testMultiStmtExecuteQuery() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - String multiStmtQuery = - "select 1;\n" - + "create or replace temporary table test_multi (cola int);\n" - + "insert into test_multi VALUES (1), (2);\n" - + "select cola from test_multi order by cola asc"; - - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); - ResultSet rs = statement.executeQuery(multiStmtQuery); - // first statement - assertNotNull(rs); - assertNotNull(statement.getResultSet()); - assertEquals(-1, statement.getUpdateCount()); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - assertFalse(rs.next()); - - // second statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(0, statement.getUpdateCount()); - - // third statement - assertTrue(statement.getMoreResults()); - assertNull(statement.getResultSet()); - assertEquals(2, statement.getUpdateCount()); - - // fourth statement - assertTrue(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - rs = statement.getResultSet(); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - assertTrue(rs.next()); - assertEquals(2, rs.getInt(1)); - assertFalse(rs.next()); - - assertFalse(statement.getMoreResults()); - assertEquals(-1, statement.getUpdateCount()); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + String multiStmtQuery = + "select 1;\n" + + "create or replace temporary table test_multi (cola int);\n" + + "insert into test_multi VALUES (1), (2);\n" + + "select cola from test_multi order by cola asc"; + + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 4); + try (ResultSet rs = statement.executeQuery(multiStmtQuery)) { + // first statement + assertNotNull(rs); + assertNotNull(statement.getResultSet()); + assertEquals(-1, statement.getUpdateCount()); + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + assertFalse(rs.next()); + + // second statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(0, statement.getUpdateCount()); + + // third statement + assertTrue(statement.getMoreResults()); + assertNull(statement.getResultSet()); + assertEquals(2, statement.getUpdateCount()); + + // fourth statement + assertTrue(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + } + try (ResultSet rs = statement.getResultSet()) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + assertTrue(rs.next()); + assertEquals(2, rs.getInt(1)); + assertFalse(rs.next()); + + assertFalse(statement.getMoreResults()); + assertEquals(-1, statement.getUpdateCount()); + } + } } @Test public void testMultiStmtUpdateCount() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); - boolean isResultSet = - statement.execute( - "CREATE OR REPLACE TEMPORARY TABLE TABLIST AS " - + "SELECT TABLE_SCHEMA, TABLE_NAME FROM INFORMATION_SCHEMA.TABLES " - + "WHERE TABLE_NAME LIKE 'K%' " - + "ORDER BY TABLE_SCHEMA, TABLE_NAME; " - + "SELECT * FROM TABLIST " - + "JOIN INFORMATION_SCHEMA.COLUMNS " - + "ON COLUMNS.TABLE_SCHEMA = TABLIST.TABLE_SCHEMA " - + "AND COLUMNS.TABLE_NAME = TABLIST.TABLE_NAME;"); - assertEquals(isResultSet, false); - int statementUpdateCount = statement.getUpdateCount(); - assertEquals(statementUpdateCount, 0); - isResultSet = statement.getMoreResults(); - assertEquals(isResultSet, true); - statementUpdateCount = statement.getUpdateCount(); - assertEquals(statementUpdateCount, -1); - - statement.close(); - connection.close(); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + statement.unwrap(SnowflakeStatement.class).setParameter("MULTI_STATEMENT_COUNT", 2); + boolean isResultSet = + statement.execute( + "CREATE OR REPLACE TEMPORARY TABLE TABLIST AS " + + "SELECT TABLE_SCHEMA, TABLE_NAME FROM INFORMATION_SCHEMA.TABLES " + + "WHERE TABLE_NAME LIKE 'K%' " + + "ORDER BY TABLE_SCHEMA, TABLE_NAME; " + + "SELECT * FROM TABLIST " + + "JOIN INFORMATION_SCHEMA.COLUMNS " + + "ON COLUMNS.TABLE_SCHEMA = TABLIST.TABLE_SCHEMA " + + "AND COLUMNS.TABLE_NAME = TABLIST.TABLE_NAME;"); + assertEquals(isResultSet, false); + int statementUpdateCount = statement.getUpdateCount(); + assertEquals(statementUpdateCount, 0); + isResultSet = statement.getMoreResults(); + assertEquals(isResultSet, true); + statementUpdateCount = statement.getUpdateCount(); + assertEquals(statementUpdateCount, -1); + } } /** Test use of anonymous blocks (SNOW-758262) */ @Test public void testAnonymousBlocksUse() throws SQLException { - Connection connection = getConnection(); - Statement statement = connection.createStatement(); - statement.execute("create or replace table tab758262(c1 number)"); - // Test anonymous block with multistatement - int multistatementcount = 2; - statement - .unwrap(SnowflakeStatement.class) - .setParameter("MULTI_STATEMENT_COUNT", multistatementcount); - String multiStmtQuery = - "begin\n" - + "insert into tab758262 values (1);\n" - + "return 'done';\n" - + "end;\n" - + "select * from tab758262;"; - - statement.execute(multiStmtQuery); - for (int i = 0; i < multistatementcount - 1; i++) { - assertTrue(statement.getMoreResults()); - } - ResultSet rs = statement.getResultSet(); - assertTrue(rs.next()); - assertEquals(1, rs.getInt(1)); - - // Test anonymous block in the middle of other queries in multistatement - multiStmtQuery = - "insert into tab758262 values (25), (26);\n" - + "begin\n" - + "insert into tab758262 values (27);\n" - + "return 'done';\n" - + "end;\n" - + "select * from tab758262;"; - multistatementcount = 3; - statement - .unwrap(SnowflakeStatement.class) - .setParameter("MULTI_STATEMENT_COUNT", multistatementcount); - statement.execute(multiStmtQuery); - for (int i = 0; i < multistatementcount - 1; i++) { - assertTrue(statement.getMoreResults()); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + statement.execute("create or replace table tab758262(c1 number)"); + // Test anonymous block with multistatement + int multistatementcount = 2; + statement + .unwrap(SnowflakeStatement.class) + .setParameter("MULTI_STATEMENT_COUNT", multistatementcount); + String multiStmtQuery = + "begin\n" + + "insert into tab758262 values (1);\n" + + "return 'done';\n" + + "end;\n" + + "select * from tab758262;"; + + statement.execute(multiStmtQuery); + for (int i = 0; i < multistatementcount - 1; i++) { + assertTrue(statement.getMoreResults()); + } + try (ResultSet rs = statement.getResultSet()) { + assertTrue(rs.next()); + assertEquals(1, rs.getInt(1)); + } + + // Test anonymous block in the middle of other queries in multistatement + multiStmtQuery = + "insert into tab758262 values (25), (26);\n" + + "begin\n" + + "insert into tab758262 values (27);\n" + + "return 'done';\n" + + "end;\n" + + "select * from tab758262;"; + multistatementcount = 3; + statement + .unwrap(SnowflakeStatement.class) + .setParameter("MULTI_STATEMENT_COUNT", multistatementcount); + statement.execute(multiStmtQuery); + for (int i = 0; i < multistatementcount - 1; i++) { + assertTrue(statement.getMoreResults()); + } + try (ResultSet rs = statement.getResultSet()) { + assertEquals(4, getSizeOfResultSet(rs)); + } } - rs = statement.getResultSet(); - assertEquals(4, getSizeOfResultSet(rs)); - rs.close(); - statement.close(); - connection.close(); } } diff --git a/src/test/java/net/snowflake/client/jdbc/OpenGroupCLIFuncIT.java b/src/test/java/net/snowflake/client/jdbc/OpenGroupCLIFuncIT.java index d34cc4bc9..d767456a2 100644 --- a/src/test/java/net/snowflake/client/jdbc/OpenGroupCLIFuncIT.java +++ b/src/test/java/net/snowflake/client/jdbc/OpenGroupCLIFuncIT.java @@ -142,8 +142,8 @@ public void testSystemFunctions() throws SQLException { } static void testFunction(Connection connection, String sql, String expected) throws SQLException { - try (Statement statement = connection.createStatement()) { - ResultSet resultSet = statement.executeQuery(sql); + try (Statement statement = connection.createStatement(); + ResultSet resultSet = statement.executeQuery(sql)) { assertTrue(resultSet.next()); assertEquals(expected, resultSet.getString(1)); } diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedMultiStmtIT.java b/src/test/java/net/snowflake/client/jdbc/PreparedMultiStmtIT.java index 112df2724..3d1997193 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedMultiStmtIT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedMultiStmtIT.java @@ -3,6 +3,7 @@ import static org.hamcrest.CoreMatchers.is; import static org.hamcrest.CoreMatchers.nullValue; import static org.hamcrest.MatcherAssert.assertThat; +import static org.junit.Assert.assertTrue; import java.sql.Connection; import java.sql.PreparedStatement; @@ -21,204 +22,215 @@ public class PreparedMultiStmtIT extends BaseJDBCTest { public static Connection getConnection() throws SQLException { Connection conn = BaseJDBCTest.getConnection(); - Statement stmt = conn.createStatement(); - stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); - stmt.close(); + try (Statement stmt = conn.createStatement()) { + stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); + } return conn; } @Test public void testExecuteUpdateCount() throws Exception { - SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); - Statement statement = connection.createStatement(); - statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); - statement.execute("create or replace table test_multi_bind(c1 number)"); - - PreparedStatement preparedStatement = - connection.prepareStatement( - "insert into test_multi_bind(c1) values(?); insert into " - + "test_multi_bind values (?), (?)"); - - assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); - - preparedStatement.setInt(1, 20); - preparedStatement.setInt(2, 30); - preparedStatement.setInt(3, 40); - - // first statement - int rowCount = preparedStatement.executeUpdate(); - assertThat(rowCount, is(1)); - assertThat(preparedStatement.getResultSet(), is(nullValue())); - assertThat(preparedStatement.getUpdateCount(), is(1)); - - // second statement - assertThat(preparedStatement.getMoreResults(), is(false)); - assertThat(preparedStatement.getUpdateCount(), is(2)); - - ResultSet resultSet = statement.executeQuery("select c1 from test_multi_bind order by c1 asc"); - resultSet.next(); - assertThat(resultSet.getInt(1), is(20)); - resultSet.next(); - assertThat(resultSet.getInt(1), is(30)); - resultSet.next(); - assertThat(resultSet.getInt(1), is(40)); - - statement.execute("drop table if exists test_multi_bind"); - - preparedStatement.close(); - connection.close(); + try (SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); + statement.execute("create or replace table test_multi_bind(c1 number)"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement( + "insert into test_multi_bind(c1) values(?); insert into " + + "test_multi_bind values (?), (?)")) { + + assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); + + preparedStatement.setInt(1, 20); + preparedStatement.setInt(2, 30); + preparedStatement.setInt(3, 40); + + // first statement + int rowCount = preparedStatement.executeUpdate(); + assertThat(rowCount, is(1)); + assertThat(preparedStatement.getResultSet(), is(nullValue())); + assertThat(preparedStatement.getUpdateCount(), is(1)); + + // second statement + assertThat(preparedStatement.getMoreResults(), is(false)); + assertThat(preparedStatement.getUpdateCount(), is(2)); + + try (ResultSet resultSet = + statement.executeQuery("select c1 from test_multi_bind order by c1 asc")) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(20)); + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(30)); + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(40)); + } + } + } finally { + statement.execute("drop table if exists test_multi_bind"); + } + } } /** Less bindings than expected in statement */ @Test public void testExecuteLessBindings() throws Exception { - SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); - Statement statement = connection.createStatement(); - statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); - statement.execute("create or replace table test_multi_bind(c1 number)"); - - PreparedStatement preparedStatement = - connection.prepareStatement( - "insert into test_multi_bind(c1) values(?); insert into " - + "test_multi_bind values (?), (?)"); - - assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); - - preparedStatement.setInt(1, 20); - preparedStatement.setInt(2, 30); - - // first statement - try { - preparedStatement.executeUpdate(); - Assert.fail(); - } catch (SQLException e) { - // error code comes from xp, which is js execution failed. - assertThat(e.getErrorCode(), is(100132)); + try (SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); + statement.execute("create or replace table test_multi_bind(c1 number)"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement( + "insert into test_multi_bind(c1) values(?); insert into " + + "test_multi_bind values (?), (?)")) { + + assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); + + preparedStatement.setInt(1, 20); + preparedStatement.setInt(2, 30); + + // first statement + try { + preparedStatement.executeUpdate(); + Assert.fail(); + } catch (SQLException e) { + // error code comes from xp, which is js execution failed. + assertThat(e.getErrorCode(), is(100132)); + } + } + } finally { + statement.execute("drop table if exists test_multi_bind"); + } } - - statement.execute("drop table if exists test_multi_bind"); - preparedStatement.close(); - connection.close(); } @Test public void testExecuteMoreBindings() throws Exception { - SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); - Statement statement = connection.createStatement(); - statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); - statement.execute("create or replace table test_multi_bind(c1 number)"); - - PreparedStatement preparedStatement = - connection.prepareStatement( - "insert into test_multi_bind(c1) values(?); insert into " - + "test_multi_bind values (?), (?)"); - - assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); - - preparedStatement.setInt(1, 20); - preparedStatement.setInt(2, 30); - preparedStatement.setInt(3, 40); - // 4th binding should be ignored - preparedStatement.setInt(4, 50); - - // first statement - int rowCount = preparedStatement.executeUpdate(); - assertThat(rowCount, is(1)); - assertThat(preparedStatement.getResultSet(), is(nullValue())); - assertThat(preparedStatement.getUpdateCount(), is(1)); - - // second statement - assertThat(preparedStatement.getMoreResults(), is(false)); - assertThat(preparedStatement.getUpdateCount(), is(2)); - - ResultSet resultSet = statement.executeQuery("select c1 from test_multi_bind order by c1 asc"); - resultSet.next(); - assertThat(resultSet.getInt(1), is(20)); - resultSet.next(); - assertThat(resultSet.getInt(1), is(30)); - resultSet.next(); - assertThat(resultSet.getInt(1), is(40)); - - statement.execute("drop table if exists test_multi_bind"); - - preparedStatement.close(); - connection.close(); + try (SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); + statement.execute("create or replace table test_multi_bind(c1 number)"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement( + "insert into test_multi_bind(c1) values(?); insert into " + + "test_multi_bind values (?), (?)")) { + + assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(3)); + + preparedStatement.setInt(1, 20); + preparedStatement.setInt(2, 30); + preparedStatement.setInt(3, 40); + // 4th binding should be ignored + preparedStatement.setInt(4, 50); + + // first statement + int rowCount = preparedStatement.executeUpdate(); + assertThat(rowCount, is(1)); + assertThat(preparedStatement.getResultSet(), is(nullValue())); + assertThat(preparedStatement.getUpdateCount(), is(1)); + + // second statement + assertThat(preparedStatement.getMoreResults(), is(false)); + assertThat(preparedStatement.getUpdateCount(), is(2)); + + try (ResultSet resultSet = + statement.executeQuery("select c1 from test_multi_bind order by c1 asc")) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(20)); + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(30)); + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(40)); + } + } + } finally { + statement.execute("drop table if exists test_multi_bind"); + } + } } @Test public void testExecuteQueryBindings() throws Exception { - SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); - Statement statement = connection.createStatement(); - statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); - - PreparedStatement preparedStatement = - connection.prepareStatement("select ?; select ?, ?; select ?, ?, ?"); - - assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(6)); - - preparedStatement.setInt(1, 10); - preparedStatement.setInt(2, 20); - preparedStatement.setInt(3, 30); - preparedStatement.setInt(4, 40); - preparedStatement.setInt(5, 50); - preparedStatement.setInt(6, 60); - - // first statement - ResultSet resultSet = preparedStatement.executeQuery(); - assertThat(resultSet.next(), is(true)); - assertThat(resultSet.getInt(1), is(10)); - - // second statement - assertThat(preparedStatement.getMoreResults(), is(true)); - resultSet = preparedStatement.getResultSet(); - resultSet.next(); - assertThat(resultSet.getInt(1), is(20)); - assertThat(resultSet.getInt(2), is(30)); - - // third statement - assertThat(preparedStatement.getMoreResults(), is(true)); - resultSet = preparedStatement.getResultSet(); - resultSet.next(); - assertThat(resultSet.getInt(1), is(40)); - assertThat(resultSet.getInt(2), is(50)); - assertThat(resultSet.getInt(3), is(60)); - - preparedStatement.close(); - connection.close(); + try (SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); + Statement statement = connection.createStatement()) { + statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement("select ?; select ?, ?; select ?, ?, ?")) { + + assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(6)); + + preparedStatement.setInt(1, 10); + preparedStatement.setInt(2, 20); + preparedStatement.setInt(3, 30); + preparedStatement.setInt(4, 40); + preparedStatement.setInt(5, 50); + preparedStatement.setInt(6, 60); + + // first statement + try (ResultSet resultSet = preparedStatement.executeQuery()) { + assertThat(resultSet.next(), is(true)); + assertThat(resultSet.getInt(1), is(10)); + } + // second statement + assertThat(preparedStatement.getMoreResults(), is(true)); + try (ResultSet resultSet = preparedStatement.getResultSet()) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(20)); + assertThat(resultSet.getInt(2), is(30)); + } + + // third statement + assertThat(preparedStatement.getMoreResults(), is(true)); + try (ResultSet resultSet = preparedStatement.getResultSet()) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(40)); + assertThat(resultSet.getInt(2), is(50)); + assertThat(resultSet.getInt(3), is(60)); + } + } + } } @Test public void testExecuteQueryNoBindings() throws Exception { - SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); - Statement statement = connection.createStatement(); - statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); - - PreparedStatement preparedStatement = - connection.prepareStatement("select 10; select 20, 30; select 40, 50, 60"); - - assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(0)); - - // first statement - ResultSet resultSet = preparedStatement.executeQuery(); - assertThat(resultSet.next(), is(true)); - assertThat(resultSet.getInt(1), is(10)); - - // second statement - assertThat(preparedStatement.getMoreResults(), is(true)); - resultSet = preparedStatement.getResultSet(); - resultSet.next(); - assertThat(resultSet.getInt(1), is(20)); - assertThat(resultSet.getInt(2), is(30)); - - // third statement - assertThat(preparedStatement.getMoreResults(), is(true)); - resultSet = preparedStatement.getResultSet(); - resultSet.next(); - assertThat(resultSet.getInt(1), is(40)); - assertThat(resultSet.getInt(2), is(50)); - assertThat(resultSet.getInt(3), is(60)); - - preparedStatement.close(); - connection.close(); + try (SnowflakeConnectionV1 connection = (SnowflakeConnectionV1) getConnection(); + Statement statement = connection.createStatement()) { + statement.execute("alter session set MULTI_STATEMENT_COUNT=0"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement("select 10; select 20, 30; select 40, 50, 60")) { + + assertThat(preparedStatement.getParameterMetaData().getParameterCount(), is(0)); + + // first statement + try (ResultSet resultSet = preparedStatement.executeQuery()) { + assertThat(resultSet.next(), is(true)); + assertThat(resultSet.getInt(1), is(10)); + } + + // second statement + assertThat(preparedStatement.getMoreResults(), is(true)); + try (ResultSet resultSet = preparedStatement.getResultSet()) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(20)); + assertThat(resultSet.getInt(2), is(30)); + } + + // third statement + assertThat(preparedStatement.getMoreResults(), is(true)); + try (ResultSet resultSet = preparedStatement.getResultSet()) { + assertTrue(resultSet.next()); + assertThat(resultSet.getInt(1), is(40)); + assertThat(resultSet.getInt(2), is(50)); + assertThat(resultSet.getInt(3), is(60)); + } + } + } } } diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatement0IT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatement0IT.java index f3a2c942a..7c05163dc 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatement0IT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatement0IT.java @@ -15,9 +15,9 @@ abstract class PreparedStatement0IT extends BaseJDBCTest { Connection init() throws SQLException { Connection conn = BaseJDBCTest.getConnection(); - Statement stmt = conn.createStatement(); - stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); - stmt.close(); + try (Statement stmt = conn.createStatement()) { + stmt.execute("alter session set jdbc_query_result_format = '" + queryResultFormat + "'"); + } return conn; } diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatement1IT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatement1IT.java index bd23d803d..56bef419f 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatement1IT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatement1IT.java @@ -85,7 +85,8 @@ public void testGetParameterMetaData() throws SQLException { /** Trigger default stage array binding threshold so that it can be run on travis */ @Test public void testInsertStageArrayBind() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { connection .createStatement() .execute("create or replace table testStageArrayBind(c1 integer)"); @@ -98,14 +99,12 @@ public void testInsertStageArrayBind() throws SQLException { } prepStatement.executeBatch(); - try (Statement statement = connection.createStatement()) { - try (ResultSet resultSet = - statement.executeQuery("select * from testStageArrayBind order by c1 asc")) { - int count = 0; - while (resultSet.next()) { - assertThat(resultSet.getInt(1), is(count)); - count++; - } + try (ResultSet resultSet = + statement.executeQuery("select * from testStageArrayBind order by c1 asc")) { + int count = 0; + while (resultSet.next()) { + assertThat(resultSet.getInt(1), is(count)); + count++; } } } @@ -227,16 +226,15 @@ public void testInsertBatchStageMultipleTimes() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testStageBatchNull() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { int[] thresholds = {0, 6}; // disabled, enabled for (int threshold : thresholds) { - connection.createStatement().execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table - connection - .createStatement() - .execute( - String.format( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); + statement.execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table + statement.execute( + String.format( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { prepStatement.setNull(1, Types.INTEGER); prepStatement.setNull(2, Types.DOUBLE); @@ -250,9 +248,8 @@ public void testStageBatchNull() throws SQLException { assertEquals(1, countResult[0]); } - try (ResultSet resultSet = - connection.createStatement().executeQuery("SELECT * FROM TEST_PREPST")) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery("SELECT * FROM TEST_PREPST")) { + assertTrue(resultSet.next()); String errorMessage = "Column should be null (" + (threshold > 0 ? "stage" : "non-stage") + ")"; resultSet.getInt(1); @@ -275,19 +272,18 @@ public void testStageBatchNull() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testStageString() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { int[] thresholds = {0, 6}; // disabled, enabled String[] rows = { null, "", "\"", ",", "\n", "\r\n", "\"\"", "null", "\\\n", "\",", "\\\",\\\"" }; for (int threshold : thresholds) { - connection.createStatement().execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table - connection - .createStatement() - .execute( - String.format( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); + statement.execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table + statement.execute( + String.format( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { for (int i = 0; i < rows.length; i++) { bindOneParamSet(prepStatement, i, 0.0, 0.0f, rows[i], 0, (short) 0); @@ -296,13 +292,11 @@ public void testStageString() throws SQLException { prepStatement.executeBatch(); try (ResultSet resultSet = - connection - .createStatement() - .executeQuery("SELECT colC FROM TEST_PREPST ORDER BY id ASC")) { + statement.executeQuery("SELECT colC FROM TEST_PREPST ORDER BY id ASC")) { String errorMessage = "Strings should match (" + (threshold > 0 ? "stage" : "non-stage") + ")"; for (String row : rows) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(errorMessage, row, resultSet.getString(1)); } } @@ -314,16 +308,15 @@ public void testStageString() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testIncorrectTypes() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { int[] thresholds = {0, 6}; // disabled, enabled for (int threshold : thresholds) { - connection.createStatement().execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table - connection - .createStatement() - .execute( - String.format( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); + statement.execute("DELETE FROM TEST_PREPST WHERE 1=1"); // clear table + statement.execute( + String.format( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = %d", threshold)); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { prepStatement.setString(1, "notAnInt"); // should cause error @@ -348,7 +341,8 @@ public void testIncorrectTypes() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testStageBatchTimestamps() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { Timestamp tsEpoch = new Timestamp(0L); Timestamp tsEpochMinusOneSec = new Timestamp(-1000L); // negative epoch no fraction of seconds Timestamp tsPast = new Timestamp(-2208988800100L); // very large negative epoch @@ -363,22 +357,14 @@ public void testStageBatchTimestamps() throws SQLException { try { // Test that stage and non-stage bindings are consistent for each timestamp type for (String tsType : tsTypes) { - connection - .createStatement() - .execute("ALTER SESSION SET TIMESTAMP_TYPE_MAPPING = " + tsType); - connection - .createStatement() - .execute("ALTER SESSION SET CLIENT_TIMESTAMP_TYPE_MAPPING = " + tsType); - - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_ts (id INTEGER, tz TIMESTAMP)"); + statement.execute("ALTER SESSION SET TIMESTAMP_TYPE_MAPPING = " + tsType); + statement.execute("ALTER SESSION SET CLIENT_TIMESTAMP_TYPE_MAPPING = " + tsType); + + statement.execute("CREATE OR REPLACE TABLE test_prepst_ts (id INTEGER, tz TIMESTAMP)"); try (PreparedStatement prepStatement = connection.prepareStatement("INSERT INTO test_prepst_ts(id, tz) VALUES(?,?)")) { // First, run with non-stage binding - connection - .createStatement() - .executeQuery("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); + statement.executeQuery("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); for (int i = 0; i < timestamps.length; i++) { prepStatement.setInt(1, i); prepStatement.setTimestamp(2, timestamps[i]); @@ -390,22 +376,18 @@ public void testStageBatchTimestamps() throws SQLException { } Timestamp[] nonStageResult = new Timestamp[timestamps.length]; - ResultSet rsNonStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_ts ORDER BY id ASC"); - for (int i = 0; i < nonStageResult.length; i++) { - rsNonStage.next(); - nonStageResult[i] = rsNonStage.getTimestamp(2); + try (ResultSet rsNonStage = + statement.executeQuery("SELECT * FROM test_prepst_ts ORDER BY id ASC")) { + for (int i = 0; i < nonStageResult.length; i++) { + assertTrue(rsNonStage.next()); + nonStageResult[i] = rsNonStage.getTimestamp(2); + } } - - connection.createStatement().execute("DELETE FROM test_prepst_ts WHERE 1=1"); + statement.execute("DELETE FROM test_prepst_ts WHERE 1=1"); // Now, run with stage binding - connection - .createStatement() - .execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage // bind for (int i = 0; i < timestamps.length; i++) { prepStatement.setInt(1, i); @@ -418,27 +400,26 @@ public void testStageBatchTimestamps() throws SQLException { } Timestamp[] stageResult = new Timestamp[timestamps.length]; - ResultSet rsStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_ts ORDER BY id ASC"); - for (int i = 0; i < stageResult.length; i++) { - rsStage.next(); - stageResult[i] = rsStage.getTimestamp(2); - } - - for (int i = 0; i < timestamps.length; i++) { - assertEquals( - "Stage binding timestamp should match non-stage binding timestamp (" - + tsType - + ")", - nonStageResult[i], - stageResult[i]); + try (ResultSet rsStage = + statement.executeQuery("SELECT * FROM test_prepst_ts ORDER BY id ASC")) { + for (int i = 0; i < stageResult.length; i++) { + assertTrue(rsStage.next()); + stageResult[i] = rsStage.getTimestamp(2); + } + + for (int i = 0; i < timestamps.length; i++) { + assertEquals( + "Stage binding timestamp should match non-stage binding timestamp (" + + tsType + + ")", + nonStageResult[i], + stageResult[i]); + } } } } } finally { - connection.createStatement().execute("DROP TABLE IF EXISTS test_prepst_ts"); + statement.execute("DROP TABLE IF EXISTS test_prepst_ts"); } } } @@ -446,7 +427,8 @@ public void testStageBatchTimestamps() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testStageBatchTimes() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { Time tMidnight = new Time(0); Time tNeg = new Time(-1); Time tPos = new Time(1); @@ -455,16 +437,12 @@ public void testStageBatchTimes() throws SQLException { Time[] times = new Time[] {tMidnight, tNeg, tPos, tNow, tNoon, null}; int[] countResult; try { - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_time (id INTEGER, tod TIME)"); + statement.execute("CREATE OR REPLACE TABLE test_prepst_time (id INTEGER, tod TIME)"); try (PreparedStatement prepStatement = connection.prepareStatement("INSERT INTO test_prepst_time(id, tod) VALUES(?,?)")) { // First, run with non-stage binding - connection - .createStatement() - .execute("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); + statement.execute("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); for (int i = 0; i < times.length; i++) { prepStatement.setInt(1, i); prepStatement.setTime(2, times[i]); @@ -477,21 +455,17 @@ public void testStageBatchTimes() throws SQLException { Time[] nonStageResult = new Time[times.length]; ResultSet rsNonStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_time ORDER BY id ASC"); + statement.executeQuery("SELECT * FROM test_prepst_time ORDER BY id ASC"); for (int i = 0; i < nonStageResult.length; i++) { - rsNonStage.next(); + assertTrue(rsNonStage.next()); nonStageResult[i] = rsNonStage.getTime(2); } - connection.createStatement().execute("DELETE FROM test_prepst_time WHERE 1=1"); + statement.execute("DELETE FROM test_prepst_time WHERE 1=1"); // Now, run with stage binding - connection - .createStatement() - .execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage // bind for (int i = 0; i < times.length; i++) { prepStatement.setInt(1, i); @@ -504,24 +478,23 @@ public void testStageBatchTimes() throws SQLException { } Time[] stageResult = new Time[times.length]; - ResultSet rsStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_time ORDER BY id ASC"); - for (int i = 0; i < stageResult.length; i++) { - rsStage.next(); - stageResult[i] = rsStage.getTime(2); - } + try (ResultSet rsStage = + statement.executeQuery("SELECT * FROM test_prepst_time ORDER BY id ASC")) { + for (int i = 0; i < stageResult.length; i++) { + assertTrue(rsStage.next()); + stageResult[i] = rsStage.getTime(2); + } - for (int i = 0; i < times.length; i++) { - assertEquals( - "Stage binding time should match non-stage binding time", - nonStageResult[i], - stageResult[i]); + for (int i = 0; i < times.length; i++) { + assertEquals( + "Stage binding time should match non-stage binding time", + nonStageResult[i], + stageResult[i]); + } } } } finally { - connection.createStatement().execute("DROP TABLE IF EXISTS test_prepst_time"); + statement.execute("DROP TABLE IF EXISTS test_prepst_time"); } } } @@ -541,7 +514,7 @@ public void testClearParameters() throws SQLException { prepStatement.executeUpdate(); try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(3, resultSet.getInt(1)); assertFalse(resultSet.next()); } @@ -574,7 +547,7 @@ public void testClearBatch() throws SQLException { assertThat(batchSize, is(0)); try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(3, resultSet.getInt(1)); assertFalse(resultSet.next()); } @@ -584,15 +557,14 @@ public void testClearBatch() throws SQLException { @Test public void testInsertOneRow() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); assertEquals(1, prepStatement.executeUpdate()); } - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { assertEquals(1, getSizeOfResultSet(resultSet)); } try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { @@ -606,10 +578,9 @@ public void testInsertOneRow() throws SQLException { @Test public void testUpdateOneRow() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); prepStatement.addBatch(); @@ -621,8 +592,8 @@ public void testUpdateOneRow() throws SQLException { prepStatement.setInt(1, 1); int count = prepStatement.executeUpdate(); assertEquals(1, count); - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { + assertTrue(resultSet.next()); assertEquals("newString", resultSet.getString(4)); } } @@ -631,9 +602,9 @@ public void testUpdateOneRow() throws SQLException { assertFalse(prepStatement.execute()); assertEquals(1, prepStatement.getUpdateCount()); assertEquals(1L, prepStatement.getLargeUpdateCount()); - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { + assertTrue(resultSet.next()); + assertTrue(resultSet.next()); assertEquals("newString", resultSet.getString(4)); } } @@ -642,10 +613,9 @@ public void testUpdateOneRow() throws SQLException { @Test public void testDeleteOneRow() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); prepStatement.addBatch(); @@ -658,7 +628,7 @@ public void testDeleteOneRow() throws SQLException { prepStatement.setInt(1, 1); int count = prepStatement.executeUpdate(); assertEquals(1, count); - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { assertEquals(1, getSizeOfResultSet(resultSet)); } // evaluate query ids @@ -672,7 +642,7 @@ public void testDeleteOneRow() throws SQLException { assertFalse(prepStatement.execute()); assertEquals(1, prepStatement.getUpdateCount()); assertEquals(1L, prepStatement.getLargeUpdateCount()); - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { assertEquals(0, getSizeOfResultSet(resultSet)); // evaluate query ids assertTrue(prepStatement.isWrapperFor(SnowflakePreparedStatement.class)); @@ -736,9 +706,9 @@ public void testUpdateBatch() throws SQLException { assertEquals(0, prepStatement.getUpdateCount()); assertEquals(0L, prepStatement.getLargeUpdateCount()); try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); + assertTrue(resultSet.next()); assertThat(resultSet.getString(4), is("newString")); - resultSet.next(); + assertTrue(resultSet.next()); assertThat(resultSet.getString(4), is("newString")); } } @@ -748,9 +718,10 @@ public void testUpdateBatch() throws SQLException { @Test public void testBatchInsertWithCacheEnabled() throws SQLException { int[] countResult; - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { // ensure enable the cache result use - connection.createStatement().execute(enableCacheReuse); + statement.execute(enableCacheReuse); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 1); @@ -770,14 +741,14 @@ public void testBatchInsertWithCacheEnabled() throws SQLException { assertEquals(1, countResult[0]); assertEquals(1, countResult[1]); - try (ResultSet resultSet = connection.createStatement().executeQuery(selectAllSQL)) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery(selectAllSQL)) { + assertTrue(resultSet.next()); assertEquals(1, resultSet.getInt(1)); - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(2, resultSet.getInt(1)); - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(3, resultSet.getInt(1)); - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(4, resultSet.getInt(1)); assertFalse(resultSet.next()); } @@ -805,16 +776,18 @@ public void manualTestForPreparedStatementLogging() throws SQLException { props.put("user", params.get("user")); props.put("password", params.get("password")); props.put("tracing", "info"); - Connection con = DriverManager.getConnection(uri, props); - con.createStatement() - .executeUpdate("alter session set CLIENT_ENABLE_LOG_INFO_STATEMENT_PARAMETERS=true"); - con.createStatement().execute(createTableSQL); - PreparedStatement prepStatement = con.prepareStatement(insertSQL, Statement.NO_GENERATED_KEYS); - bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); - prepStatement.addBatch(); - prepStatement.executeBatch(); - con.createStatement() - .executeUpdate("alter session set CLIENT_ENABLE_LOG_INFO_STATEMENT_PARAMETERS=false"); - con.close(); + try (Connection con = DriverManager.getConnection(uri, props); + Statement statement = con.createStatement()) { + statement.executeUpdate("alter session set CLIENT_ENABLE_LOG_INFO_STATEMENT_PARAMETERS=true"); + statement.execute(createTableSQL); + try (PreparedStatement prepStatement = + con.prepareStatement(insertSQL, Statement.NO_GENERATED_KEYS)) { + bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); + prepStatement.addBatch(); + prepStatement.executeBatch(); + statement.executeUpdate( + "alter session set CLIENT_ENABLE_LOG_INFO_STATEMENT_PARAMETERS=false"); + } + } } } diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatement1LatestIT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatement1LatestIT.java index 52b4f4518..872c8aab6 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatement1LatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatement1LatestIT.java @@ -42,9 +42,10 @@ public PreparedStatement1LatestIT() { @Test public void testPrepStWithCacheEnabled() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { // ensure enable the cache result use - connection.createStatement().execute(enableCacheReuse); + statement.execute(enableCacheReuse); try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); @@ -54,13 +55,12 @@ public void testPrepStWithCacheEnabled() throws SQLException { prepStatement.execute(); } - try (ResultSet resultSet = - connection.createStatement().executeQuery("select * from test_prepst")) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery("select * from test_prepst")) { + assertTrue(resultSet.next()); assertEquals(resultSet.getInt(1), 1); - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(resultSet.getInt(1), 1); - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(resultSet.getInt(1), 100); } @@ -69,13 +69,13 @@ public void testPrepStWithCacheEnabled() throws SQLException { prepStatement.setInt(1, 1); prepStatement.setInt(2, 1); try (ResultSet resultSet = prepStatement.executeQuery()) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(resultSet.getInt(2), 2); prepStatement.setInt(1, 1); prepStatement.setInt(2, 100); } try (ResultSet resultSet = prepStatement.executeQuery()) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(resultSet.getInt(2), 101); } } @@ -110,35 +110,37 @@ public void testPrepStWithCacheEnabled() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testInsertStageArrayBindWithTime() throws SQLException { - try (Connection connection = init()) { - Statement statement = connection.createStatement(); - statement.execute("alter session set CLIENT_STAGE_ARRAY_BINDING_THRESHOLD=2"); - statement.execute("create or replace table testStageBindTime (c1 time, c2 time)"); - PreparedStatement prepSt = - connection.prepareStatement("insert into testStageBindTime values (?, ?)"); - Time[][] timeValues = { - {new Time(0), new Time(1)}, - {new Time(1000), new Time(Integer.MAX_VALUE)}, - {new Time(123456), new Time(55555)}, - {Time.valueOf("01:02:00"), new Time(-100)}, - }; - for (Time[] value : timeValues) { - prepSt.setTime(1, value[0]); - prepSt.setTime(2, value[1]); - prepSt.addBatch(); - } - prepSt.executeBatch(); - // check results - ResultSet rs = statement.executeQuery("select * from testStageBindTime"); - for (Time[] timeValue : timeValues) { - rs.next(); - assertEquals(timeValue[0].toString(), rs.getTime(1).toString()); - assertEquals(timeValue[1].toString(), rs.getTime(2).toString()); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute("alter session set CLIENT_STAGE_ARRAY_BINDING_THRESHOLD=2"); + statement.execute("create or replace table testStageBindTime (c1 time, c2 time)"); + PreparedStatement prepSt = + connection.prepareStatement("insert into testStageBindTime values (?, ?)"); + Time[][] timeValues = { + {new Time(0), new Time(1)}, + {new Time(1000), new Time(Integer.MAX_VALUE)}, + {new Time(123456), new Time(55555)}, + {Time.valueOf("01:02:00"), new Time(-100)}, + }; + for (Time[] value : timeValues) { + prepSt.setTime(1, value[0]); + prepSt.setTime(2, value[1]); + prepSt.addBatch(); + } + prepSt.executeBatch(); + // check results + try (ResultSet rs = statement.executeQuery("select * from testStageBindTime")) { + for (Time[] timeValue : timeValues) { + assertTrue(rs.next()); + assertEquals(timeValue[0].toString(), rs.getTime(1).toString()); + assertEquals(timeValue[1].toString(), rs.getTime(2).toString()); + } + } + } finally { + statement.execute("drop table if exists testStageBindTime"); + statement.execute("alter session unset CLIENT_STAGE_ARRAY_BINDING_THRESHOLD"); } - rs.close(); - statement.execute("drop table if exists testStageBindTime"); - statement.execute("alter session unset CLIENT_STAGE_ARRAY_BINDING_THRESHOLD"); - statement.close(); } } @@ -155,48 +157,48 @@ public void testInsertStageArrayBindWithTime() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testSetObjectForTimestampTypes() throws SQLException { - try (Connection connection = init()) { - Statement statement = connection.createStatement(); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { // set timestamp mapping to default value - statement.execute("ALTER SESSION UNSET CLIENT_TIMESTAMP_TYPE_MAPPING"); - statement.execute("create or replace table TS (ntz TIMESTAMP_NTZ, ltz TIMESTAMP_LTZ)"); - PreparedStatement prepst = connection.prepareStatement("insert into TS values (?, ?)"); - String date1 = "2014-01-01 16:00:00"; - String date2 = "1945-11-12 5:25:00"; - Timestamp[] testTzs = {Timestamp.valueOf(date1), Timestamp.valueOf(date2)}; - for (int i = 0; i < testTzs.length; i++) { - // Disable stage array binding and insert the timestamp values - statement.execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); // disable stage bind - prepst.setObject(1, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_NTZ); - prepst.setObject(2, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_LTZ); - prepst.addBatch(); - prepst.executeBatch(); - // Enable stage array binding and insert the same timestamp values as above - statement.execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage bind - prepst.setObject(1, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_NTZ); - prepst.setObject(2, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_LTZ); - prepst.addBatch(); - prepst.executeBatch(); - } - ResultSet rs = statement.executeQuery("select * from TS"); - // Get results for each timestamp value tested - for (int i = 0; i < testTzs.length; i++) { - // Assert that the first row of inserts with payload binding matches the second row of - // inserts that used stage array binding - rs.next(); - Timestamp expectedNTZTs = rs.getTimestamp(1); - Timestamp expectedLTZTs = rs.getTimestamp(2); - rs.next(); - assertEquals(expectedNTZTs, rs.getTimestamp(1)); - assertEquals(expectedLTZTs, rs.getTimestamp(2)); + try { + statement.execute("ALTER SESSION UNSET CLIENT_TIMESTAMP_TYPE_MAPPING"); + statement.execute("create or replace table TS (ntz TIMESTAMP_NTZ, ltz TIMESTAMP_LTZ)"); + PreparedStatement prepst = connection.prepareStatement("insert into TS values (?, ?)"); + String date1 = "2014-01-01 16:00:00"; + String date2 = "1945-11-12 5:25:00"; + Timestamp[] testTzs = {Timestamp.valueOf(date1), Timestamp.valueOf(date2)}; + for (int i = 0; i < testTzs.length; i++) { + // Disable stage array binding and insert the timestamp values + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); // disable stage bind + prepst.setObject(1, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_NTZ); + prepst.setObject(2, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_LTZ); + prepst.addBatch(); + prepst.executeBatch(); + // Enable stage array binding and insert the same timestamp values as above + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage bind + prepst.setObject(1, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_NTZ); + prepst.setObject(2, testTzs[i], SnowflakeUtil.EXTRA_TYPES_TIMESTAMP_LTZ); + prepst.addBatch(); + prepst.executeBatch(); + } + try (ResultSet rs = statement.executeQuery("select * from TS")) { + // Get results for each timestamp value tested + for (int i = 0; i < testTzs.length; i++) { + // Assert that the first row of inserts with payload binding matches the second row of + // inserts that used stage array binding + assertTrue(rs.next()); + Timestamp expectedNTZTs = rs.getTimestamp(1); + Timestamp expectedLTZTs = rs.getTimestamp(2); + assertTrue(rs.next()); + assertEquals(expectedNTZTs, rs.getTimestamp(1)); + assertEquals(expectedLTZTs, rs.getTimestamp(2)); + } + } + } finally { + statement.execute("ALTER SESSION UNSET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD;"); } - - // clean up - statement.execute("ALTER SESSION UNSET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD;"); - rs.close(); - statement.close(); } } @@ -290,26 +292,29 @@ public void testSetObjectMethodWithLargeBigIntegerColumn() { @Test public void testBatchInsertWithTimestampInputFormatSet() throws SQLException { - try (Connection connection = init()) { - Statement statement = connection.createStatement(); - statement.execute("alter session set TIMESTAMP_INPUT_FORMAT='YYYY-MM-DD HH24:MI:SS.FFTZH'"); - statement.execute( - "create or replace table testStageBindTypes (c1 date, c2 datetime, c3 timestamp)"); - java.util.Date today = new java.util.Date(); - java.sql.Date sqldate = new java.sql.Date(today.getDate()); - java.sql.Timestamp todaySQL = new java.sql.Timestamp(today.getTime()); - PreparedStatement prepSt = - connection.prepareStatement("insert into testStageBindTypes values (?, ?, ?)"); - for (int i = 1; i < 30000; i++) { - prepSt.setDate(1, sqldate); - prepSt.setDate(2, sqldate); - prepSt.setTimestamp(3, todaySQL); - prepSt.addBatch(); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute("alter session set TIMESTAMP_INPUT_FORMAT='YYYY-MM-DD HH24:MI:SS.FFTZH'"); + statement.execute( + "create or replace table testStageBindTypes (c1 date, c2 datetime, c3 timestamp)"); + java.util.Date today = new java.util.Date(); + java.sql.Date sqldate = new java.sql.Date(today.getDate()); + java.sql.Timestamp todaySQL = new java.sql.Timestamp(today.getTime()); + try (PreparedStatement prepSt = + connection.prepareStatement("insert into testStageBindTypes values (?, ?, ?)")) { + for (int i = 1; i < 30000; i++) { + prepSt.setDate(1, sqldate); + prepSt.setDate(2, sqldate); + prepSt.setTimestamp(3, todaySQL); + prepSt.addBatch(); + } + prepSt.executeBatch(); // should not throw a parsing error. + } + } finally { + statement.execute("drop table if exists testStageBindTypes"); + statement.execute("alter session unset TIMESTAMP_INPUT_FORMAT"); } - prepSt.executeBatch(); // should not throw a parsing error. - statement.execute("drop table if exists testStageBindTypes"); - statement.execute("alter session unset TIMESTAMP_INPUT_FORMAT"); - statement.close(); } } @@ -322,34 +327,36 @@ public void testBatchInsertWithTimestampInputFormatSet() throws SQLException { @Test @Ignore public void testCallStatement() throws SQLException { - try (Connection connection = getConnection()) { - Statement statement = connection.createStatement(); - statement.executeQuery( - "ALTER SESSION SET USE_STATEMENT_TYPE_CALL_FOR_STORED_PROC_CALLS=true"); - statement.executeQuery( - "create or replace procedure\n" - + "TEST_SP_CALL_STMT_ENABLED(in1 float, in2 variant)\n" - + "returns string language javascript as $$\n" - + "let res = snowflake.execute({sqlText: 'select ? c1, ? c2', binds:[IN1, JSON.stringify(IN2)]});\n" - + "res.next();\n" - + "return res.getColumnValueAsString(1) + ' ' + res.getColumnValueAsString(2) + ' ' + IN2;\n" - + "$$;"); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.executeQuery( + "ALTER SESSION SET USE_STATEMENT_TYPE_CALL_FOR_STORED_PROC_CALLS=true"); + statement.executeQuery( + "create or replace procedure\n" + + "TEST_SP_CALL_STMT_ENABLED(in1 float, in2 variant)\n" + + "returns string language javascript as $$\n" + + "let res = snowflake.execute({sqlText: 'select ? c1, ? c2', binds:[IN1, JSON.stringify(IN2)]});\n" + + "res.next();\n" + + "return res.getColumnValueAsString(1) + ' ' + res.getColumnValueAsString(2) + ' ' + IN2;\n" + + "$$;"); - PreparedStatement prepStatement = - connection.prepareStatement("call TEST_SP_CALL_STMT_ENABLED(?, to_variant(?))"); - prepStatement.setDouble(1, 1); - prepStatement.setString(2, "[2,3]"); + try (PreparedStatement prepStatement = + connection.prepareStatement("call TEST_SP_CALL_STMT_ENABLED(?, to_variant(?))")) { + prepStatement.setDouble(1, 1); + prepStatement.setString(2, "[2,3]"); - ResultSet rs = prepStatement.executeQuery(); - String result = "1 \"[2,3]\" [2,3]"; - while (rs.next()) { - assertEquals(result, rs.getString(1)); + try (ResultSet rs = prepStatement.executeQuery()) { + String result = "1 \"[2,3]\" [2,3]"; + while (rs.next()) { + assertEquals(result, rs.getString(1)); + } + } + } + } finally { + statement.executeQuery( + "drop procedure if exists TEST_SP_CALL_STMT_ENABLED(float, variant)"); } - - statement.executeQuery("drop procedure if exists TEST_SP_CALL_STMT_ENABLED(float, variant)"); - rs.close(); - prepStatement.close(); - statement.close(); } } } diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatement2IT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatement2IT.java index 71f2fe3d5..efb8ef944 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatement2IT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatement2IT.java @@ -48,7 +48,8 @@ public PreparedStatement2IT() { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testStageBatchDates() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { Date dEpoch = new Date(0); Date dAfterEpoch = new Date(24 * 60 * 60 * 1000); Date dBeforeEpoch = new Date(-1 * 24 * 60 * 60 * 1000); @@ -59,16 +60,12 @@ public void testStageBatchDates() throws SQLException { int[] countResult; try { - connection - .createStatement() - .execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); + statement.execute("CREATE OR REPLACE TABLE test_prepst_date (id INTEGER, d DATE)"); try (PreparedStatement prepStatement = connection.prepareStatement("INSERT INTO test_prepst_date(id, d) VALUES(?,?)")) { // First, run with non-stage binding - connection - .createStatement() - .execute("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); + statement.execute("ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 0"); for (int i = 0; i < dates.length; i++) { prepStatement.setInt(1, i); prepStatement.setDate(2, dates[i]); @@ -80,22 +77,19 @@ public void testStageBatchDates() throws SQLException { } Date[] nonStageResult = new Date[dates.length]; - ResultSet rsNonStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_date ORDER BY id ASC"); - for (int i = 0; i < nonStageResult.length; i++) { - rsNonStage.next(); - nonStageResult[i] = rsNonStage.getDate(2); - } + try (ResultSet rsNonStage = + statement.executeQuery("SELECT * FROM test_prepst_date ORDER BY id ASC")) { - connection.createStatement().execute("DELETE FROM test_prepst_date WHERE 1=1"); + for (int i = 0; i < nonStageResult.length; i++) { + assertTrue(rsNonStage.next()); + nonStageResult[i] = rsNonStage.getDate(2); + } + } + statement.execute("DELETE FROM test_prepst_date WHERE 1=1"); // Now, run with stage binding - connection - .createStatement() - .execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage // bind for (int i = 0; i < dates.length; i++) { prepStatement.setInt(1, i); @@ -108,35 +102,33 @@ public void testStageBatchDates() throws SQLException { } Date[] stageResult = new Date[dates.length]; - ResultSet rsStage = - connection - .createStatement() - .executeQuery("SELECT * FROM test_prepst_date ORDER BY id ASC"); - for (int i = 0; i < stageResult.length; i++) { - rsStage.next(); - stageResult[i] = rsStage.getDate(2); - } + try (ResultSet rsStage = + statement.executeQuery("SELECT * FROM test_prepst_date ORDER BY id ASC")) { + for (int i = 0; i < stageResult.length; i++) { + assertTrue(rsStage.next()); + stageResult[i] = rsStage.getDate(2); + } - for (int i = 0; i < dates.length; i++) { - assertEquals( - "Stage binding date should match non-stage binding date", - nonStageResult[i], - stageResult[i]); + for (int i = 0; i < dates.length; i++) { + assertEquals( + "Stage binding date should match non-stage binding date", + nonStageResult[i], + stageResult[i]); + } } } } finally { - connection.createStatement().execute("DROP TABLE IF EXISTS test_prepst_date"); + statement.execute("DROP TABLE IF EXISTS test_prepst_date"); } } } @Test public void testBindWithNullValue() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute( - "create or replace table testBindNull(cola date, colb time, colc timestamp, cold number)"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute( + "create or replace table testBindNull(cola date, colb time, colc timestamp, cold number)"); try (PreparedStatement prepStatement = connection.prepareStatement("insert into testBindNull values (?, ?, ?, ?)")) { @@ -146,9 +138,8 @@ public void testBindWithNullValue() throws SQLException { prepStatement.setBigDecimal(4, null); prepStatement.addBatch(); prepStatement.executeBatch(); - try (ResultSet resultSet = - connection.createStatement().executeQuery("select * from testBindNull")) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery("select * from testBindNull")) { + assertTrue(resultSet.next()); Date date = resultSet.getDate(1); assertNull(date); assertTrue(resultSet.wasNull()); @@ -165,7 +156,7 @@ public void testBindWithNullValue() throws SQLException { assertNull(bg); assertTrue(resultSet.wasNull()); } - connection.createStatement().execute("TRUNCATE table testbindnull"); + statement.execute("TRUNCATE table testbindnull"); prepStatement.setDate(1, null, Calendar.getInstance()); prepStatement.setTime(2, null, Calendar.getInstance()); prepStatement.setTimestamp(3, null, Calendar.getInstance()); @@ -174,9 +165,8 @@ public void testBindWithNullValue() throws SQLException { prepStatement.addBatch(); prepStatement.executeBatch(); - try (ResultSet resultSet = - connection.createStatement().executeQuery("select * from testBindNull")) { - resultSet.next(); + try (ResultSet resultSet = statement.executeQuery("select * from testBindNull")) { + assertTrue(resultSet.next()); Date date = resultSet.getDate(1); assertNull(date); assertTrue(resultSet.wasNull()); @@ -195,20 +185,20 @@ public void testBindWithNullValue() throws SQLException { @Test public void testPrepareDDL() throws SQLException { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { try { try (PreparedStatement prepStatement = connection.prepareStatement("create or replace table testprepareddl(cola number)")) { prepStatement.execute(); } - try (ResultSet resultSet = - connection.createStatement().executeQuery("show tables like 'testprepareddl'")) { + try (ResultSet resultSet = statement.executeQuery("show tables like 'testprepareddl'")) { // result should only have one row since table is created assertThat(resultSet.next(), is(true)); assertThat(resultSet.next(), is(false)); } } finally { - connection.createStatement().execute("drop table if exists testprepareddl"); + statement.execute("drop table if exists testprepareddl"); } } } @@ -236,7 +226,7 @@ public void testPrepareTCL() throws SQLException { for (String testCase : testCases) { try (PreparedStatement prepStatement = connection.prepareStatement(testCase)) { try (ResultSet resultSet = prepStatement.executeQuery()) { - resultSet.next(); + assertTrue(resultSet.next()); assertThat(resultSet.getString(1), is("Statement executed successfully.")); } } @@ -266,26 +256,26 @@ public void testPrepareShowCommand() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testPrepareTimeout() throws SQLException, InterruptedException { - try (Connection adminCon = getSnowflakeAdminConnection()) { - adminCon.createStatement().execute("alter system set enable_combined_describe=true"); + try (Connection adminCon = getSnowflakeAdminConnection(); + Statement adminStatement = adminCon.createStatement()) { + adminStatement.execute("alter system set enable_combined_describe=true"); try { - try (Connection connection = init()) { - connection.createStatement().execute("create or replace table t(c1 string) as select 1"); - connection - .createStatement() - .execute("alter session set jdbc_enable_combined_describe=true"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute("create or replace table t(c1 string) as select 1"); + statement.execute("alter session set jdbc_enable_combined_describe=true"); try (PreparedStatement prepStatement = connection.prepareStatement("select c1 from t order by c1 limit 1")) { Thread.sleep(5000); try (ResultSet resultSet = prepStatement.executeQuery()) { - resultSet.next(); + assertTrue(resultSet.next()); assertThat(resultSet.getInt(1), is(1)); } } - connection.createStatement().execute("drop table if exists t"); + statement.execute("drop table if exists t"); } } finally { - adminCon.createStatement().execute("alter system set enable_combined_describe=default"); + adminStatement.execute("alter system set enable_combined_describe=default"); } } } @@ -293,40 +283,41 @@ public void testPrepareTimeout() throws SQLException, InterruptedException { /** Test case to make sure 2 non null bind refs was not constant folded into one */ @Test public void testSnow36284() throws Exception { - Connection connection = init(); - String query = "select * from (values ('a'), ('b')) x where x.COLUMN1 in (?,?);"; - PreparedStatement preparedStatement = connection.prepareStatement(query); - preparedStatement.setString(1, "a"); - preparedStatement.setString(2, "b"); - ResultSet rs = preparedStatement.executeQuery(); - int rowcount = 0; - Set valuesReturned = Sets.newHashSetWithExpectedSize(2); - while (rs.next()) { - rowcount++; - valuesReturned.add(rs.getString(1)); + + try (Connection connection = init(); + PreparedStatement preparedStatement = connection.prepareStatement(query)) { + preparedStatement.setString(1, "a"); + preparedStatement.setString(2, "b"); + try (ResultSet rs = preparedStatement.executeQuery()) { + int rowcount = 0; + Set valuesReturned = Sets.newHashSetWithExpectedSize(2); + while (rs.next()) { + rowcount++; + valuesReturned.add(rs.getString(1)); + } + assertEquals("Should get back 2 rows", 2, rowcount); + assertEquals("", valuesReturned, Sets.newHashSet("a", "b")); + } } - assertEquals("Should get back 2 rows", 2, rowcount); - assertEquals("", valuesReturned, Sets.newHashSet("a", "b")); } /** Test for coalesce with bind and null arguments in a prepared statement */ @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testSnow35923() throws Exception { - try (Connection connection = init()) { - connection - .createStatement() - .execute("alter session set " + "optimizer_eliminate_scans_for_constant_select=false"); - connection.createStatement().execute("create or replace table inc(a int, b int)"); - connection - .createStatement() - .execute("insert into inc(a, b) values (1, 2), " + "(NULL, 4), (5,NULL), (7,8)"); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + statement.execute( + "alter session set " + "optimizer_eliminate_scans_for_constant_select=false"); + statement.execute("create or replace table inc(a int, b int)"); + statement.execute("insert into inc(a, b) values (1, 2), " + "(NULL, 4), (5,NULL), (7,8)"); // Query used to cause an incident. - PreparedStatement preparedStatement = - connection.prepareStatement("SELECT coalesce(?, NULL) from inc;"); - preparedStatement.setInt(1, 0); - ResultSet rs = preparedStatement.executeQuery(); + try (PreparedStatement preparedStatement = + connection.prepareStatement("SELECT coalesce(?, NULL) from inc;")) { + preparedStatement.setInt(1, 0); + try (ResultSet rs = preparedStatement.executeQuery()) {} + } } } @@ -337,162 +328,180 @@ public void testSnow35923() throws Exception { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testBindObjectLiteral() throws Exception { - try (Connection conn = init()) { - Statement stmt = conn.createStatement(); + long t1Id = 0; + long t2Id = 0; + String t1 = null; - String sqlText = "create or replace table identifier(?) (c1 number)"; - SnowflakePreparedStatementV1 pStmt = - (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - String t1 = "bindObjectTable1"; - // Bind the table name - pStmt.setString(1, t1); - ResultSet result = pStmt.executeQuery(); + try (Connection conn = init(); + Statement stmt = conn.createStatement()) { + String sqlText = "create or replace table identifier(?) (c1 number)"; + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + t1 = "bindObjectTable1"; + // Bind the table name + pStmt.setString(1, t1); + try (ResultSet result = pStmt.executeQuery()) {} + } // Verify the table has been created and get the table ID stmt.execute("select parse_json(system$dict_id('table', '" + t1 + "')):entityId;"); - result = stmt.getResultSet(); - - long t1Id = 0; - if (result.next()) { - t1Id = Long.valueOf(result.getString(1)); + try (ResultSet result = stmt.getResultSet()) { + if (result.next()) { + t1Id = Long.valueOf(result.getString(1)); + } + assertTrue(t1Id != 0); } - assertTrue(t1Id != 0); - // Mix of object literal binds and value binds sqlText = "insert into identifier(?) values (1), (2), (3)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setParameter("resolve_object_ids", true); - // Bind by object IDs - pStmt.setLong(1, t1Id); - - result = pStmt.executeQuery(); - + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setParameter("resolve_object_ids", true); + // Bind by object IDs + pStmt.setLong(1, t1Id); + try (ResultSet result = pStmt.executeQuery()) {} + } // Perform some selection sqlText = "select * from identifier(?) order by 1"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setString(1, t1); - result = pStmt.executeQuery(); - // Verify 3 rows have been inserted - for (int i = 0; i < 3; i++) { - assertTrue(result.next()); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setString(1, t1); + try (ResultSet result = pStmt.executeQuery()) { + // Verify 3 rows have been inserted + for (int i = 0; i < 3; i++) { + assertTrue(result.next()); + } + assertFalse(result.next()); + } } - assertFalse(result.next()); - // Alter Table sqlText = "alter table identifier(?) add column c2 number"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setParameter("resolve_object_ids", true); - pStmt.setLong(1, t1Id); - result = pStmt.executeQuery(); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setParameter("resolve_object_ids", true); + pStmt.setLong(1, t1Id); + try (ResultSet result = pStmt.executeQuery()) {} + } // Describe sqlText = "desc table identifier(?)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setString(1, t1); - result = pStmt.executeQuery(); - // Verify two columns have been created - for (int i = 0; i < 2; i++) { - assertTrue(result.next()); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setString(1, t1); + try (ResultSet result = pStmt.executeQuery()) { + // Verify two columns have been created + for (int i = 0; i < 2; i++) { + assertTrue(result.next()); + } + assertFalse(result.next()); + } } - assertFalse(result.next()); // Create another table String t2 = "bindObjectTable2"; sqlText = "create or replace table identifier(?) (c1 number)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setString(1, t2); - result = pStmt.executeQuery(); - + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setString(1, t2); + try (ResultSet result = pStmt.executeQuery()) {} + } // Verify the table has been created and get the table ID stmt.execute("select parse_json(system$dict_id('table', '" + t2 + "')):entityId;"); - result = stmt.getResultSet(); - - long t2Id = 0; - if (result.next()) { - t2Id = Long.valueOf(result.getString(1)); + try (ResultSet result = stmt.getResultSet()) { + if (result.next()) { + t2Id = Long.valueOf(result.getString(1)); + } + assertTrue(t2Id != 0); } - assertTrue(t2Id != 0); - // Mix object binds with value binds sqlText = "insert into identifier(?) values (?), (?), (?)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setString(1, t2); - pStmt.setInt(2, 1); - pStmt.setInt(3, 2); - pStmt.setInt(4, 3); - result = pStmt.executeQuery(); - + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setString(1, t2); + pStmt.setInt(2, 1); + pStmt.setInt(3, 2); + pStmt.setInt(4, 3); + try (ResultSet result = pStmt.executeQuery()) {} + } // Verify that 3 rows have been inserted sqlText = "select * from identifier(?) order by 1"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setParameter("resolve_object_ids", true); - pStmt.setLong(1, t2Id); - result = pStmt.executeQuery(); - for (int i = 0; i < 3; i++) { - assertTrue(result.next()); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setParameter("resolve_object_ids", true); + pStmt.setLong(1, t2Id); + try (ResultSet result = pStmt.executeQuery()) { + for (int i = 0; i < 3; i++) { + assertTrue(result.next()); + } + assertFalse(result.next()); + } } - assertFalse(result.next()); // Multiple Object Binds sqlText = "select t2.c1 from identifier(?) as t1, identifier(?) as t2 " + "where t1.c1 = t2.c1 and t1.c1 > (?)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setParameter("resolve_object_ids", true); - pStmt.setString(1, t1); - pStmt.setLong(2, t2Id); - pStmt.setInt(3, 1); - result = pStmt.executeQuery(); - for (int i = 0; i < 2; i++) { - assertTrue(result.next()); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setParameter("resolve_object_ids", true); + pStmt.setString(1, t1); + pStmt.setLong(2, t2Id); + pStmt.setInt(3, 1); + try (ResultSet result = pStmt.executeQuery()) { + for (int i = 0; i < 2; i++) { + assertTrue(result.next()); + } + assertFalse(result.next()); + } } - assertFalse(result.next()); // Drop Tables sqlText = "drop table identifier(?)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setString(1, "bindObjectTable1"); - result = pStmt.executeQuery(); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setString(1, "bindObjectTable1"); + try (ResultSet result = pStmt.executeQuery()) {} + } sqlText = "drop table identifier(?)"; - pStmt = (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText); - pStmt.setParameter("resolve_object_ids", true); - pStmt.setLong(1, t2Id); - result = pStmt.executeQuery(); + try (SnowflakePreparedStatementV1 pStmt = + (SnowflakePreparedStatementV1) conn.prepareStatement(sqlText)) { + pStmt.setParameter("resolve_object_ids", true); + pStmt.setLong(1, t2Id); + try (ResultSet result = pStmt.executeQuery()) {} + } // Verify that the tables have been dropped stmt.execute("show tables like 'bindobjecttable%'"); - result = stmt.getResultSet(); - assertFalse(result.next()); + try (ResultSet result = stmt.getResultSet()) { + assertFalse(result.next()); + } } } @Test public void testBindTimestampTZViaString() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute( - "alter session set timestamp_tz_output_format='YYYY-MM" - + "-DD HH24:MI:SS.FF9 TZHTZM'"); - connection - .createStatement() - .execute("create or replace table testbindtstz(cola timestamp_tz)"); - - try (PreparedStatement preparedStatement = - connection.prepareStatement("insert into testbindtstz values(?)")) { - preparedStatement.setString(1, "2017-11-30T18:17:05.123456789+08:00"); - int count = preparedStatement.executeUpdate(); - assertThat(count, is(1)); - } - try (ResultSet resultSet = - connection.createStatement().executeQuery("select * from testbindtstz")) { - assertTrue(resultSet.next()); - assertThat(resultSet.getString(1), is("2017-11-30 18:17:05.123456789 +0800")); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute( + "alter session set timestamp_tz_output_format='YYYY-MM" + "-DD HH24:MI:SS.FF9 TZHTZM'"); + statement.execute("create or replace table testbindtstz(cola timestamp_tz)"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement("insert into testbindtstz values(?)")) { + preparedStatement.setString(1, "2017-11-30T18:17:05.123456789+08:00"); + int count = preparedStatement.executeUpdate(); + assertThat(count, is(1)); + } + try (ResultSet resultSet = statement.executeQuery("select * from testbindtstz")) { + assertTrue(resultSet.next()); + assertThat(resultSet.getString(1), is("2017-11-30 18:17:05.123456789 +0800")); + } + } finally { + statement.execute("drop table if exists testbindtstz"); } - connection.createStatement().execute("drop table if exists testbindtstz"); } } @@ -503,41 +512,40 @@ public void testBindTimestampTZViaString() throws SQLException { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testBindTimestampTZViaStringBatch() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute( - "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage bind - connection - .createStatement() - .execute("create or replace table testbindtstz(cola timestamp_tz, colb timestamp_ntz)"); - - try (PreparedStatement preparedStatement = - connection.prepareStatement("insert into testbindtstz values(?,?)")) { - - preparedStatement.setString(1, "2017-11-30 18:17:05.123456789 +08:00"); - preparedStatement.setString(2, "2017-11-30 18:17:05.123456789"); - preparedStatement.addBatch(); - preparedStatement.setString(1, "2017-05-03 16:44:42.0"); - preparedStatement.setString(2, "2017-05-03 16:44:42.0"); - preparedStatement.addBatch(); - int[] count = preparedStatement.executeBatch(); - assertThat(count[0], is(1)); - - try (ResultSet resultSet = - connection - .createStatement() - .executeQuery("select * from testbindtstz order by 1 desc")) { - assertTrue(resultSet.next()); - assertThat(resultSet.getString(1), is("Thu, 30 Nov 2017 18:17:05 +0800")); - assertThat(resultSet.getString(2), is("Thu, 30 Nov 2017 18:17:05 Z")); - - assertTrue(resultSet.next()); - assertThat(resultSet.getString(1), is("Wed, 03 May 2017 16:44:42 -0700")); - assertThat(resultSet.getString(2), is("Wed, 03 May 2017 16:44:42 Z")); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute( + "ALTER SESSION SET CLIENT_STAGE_ARRAY_BINDING_THRESHOLD = 1"); // enable stage bind + statement.execute( + "create or replace table testbindtstz(cola timestamp_tz, colb timestamp_ntz)"); + + try (PreparedStatement preparedStatement = + connection.prepareStatement("insert into testbindtstz values(?,?)")) { + + preparedStatement.setString(1, "2017-11-30 18:17:05.123456789 +08:00"); + preparedStatement.setString(2, "2017-11-30 18:17:05.123456789"); + preparedStatement.addBatch(); + preparedStatement.setString(1, "2017-05-03 16:44:42.0"); + preparedStatement.setString(2, "2017-05-03 16:44:42.0"); + preparedStatement.addBatch(); + int[] count = preparedStatement.executeBatch(); + assertThat(count[0], is(1)); + + try (ResultSet resultSet = + statement.executeQuery("select * from testbindtstz order by 1 desc")) { + assertTrue(resultSet.next()); + assertThat(resultSet.getString(1), is("Thu, 30 Nov 2017 18:17:05 +0800")); + assertThat(resultSet.getString(2), is("Thu, 30 Nov 2017 18:17:05 Z")); + + assertTrue(resultSet.next()); + assertThat(resultSet.getString(1), is("Wed, 03 May 2017 16:44:42 -0700")); + assertThat(resultSet.getString(2), is("Wed, 03 May 2017 16:44:42 Z")); + } } + } finally { + statement.execute("drop table if exists testbindtstz"); } - connection.createStatement().execute("drop table if exists testbindtstz"); } } @@ -549,14 +557,11 @@ public void testBindTimestampTZViaStringBatch() throws SQLException { */ @Test public void testSnow41620() throws Exception { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { // Create a table and insert 3 records - connection - .createStatement() - .execute("CREATE or REPLACE TABLE SNOW41620 (c1 varchar(20)," + "c2 int" + " )"); - connection - .createStatement() - .execute("insert into SNOW41620 values('value1', 1), ('value2', 2), ('value3', 3)"); + statement.execute("CREATE or REPLACE TABLE SNOW41620 (c1 varchar(20)," + "c2 int" + " )"); + statement.execute("insert into SNOW41620 values('value1', 1), ('value2', 2), ('value3', 3)"); String PARAMETERIZED_QUERY = "SELECT t0.C1, " @@ -564,28 +569,24 @@ public void testSnow41620() throws Exception { + "CASE WHEN t0.C1 IN (?, ?) THEN t0.C2 ELSE null END " + "FROM SNOW41620 t0"; - ResultSet bindStmtResultSet; try (PreparedStatement pst = connection.prepareStatement(PARAMETERIZED_QUERY)) { // bind values pst.setObject(1, "value1"); pst.setObject(2, "value3"); pst.setObject(3, "value2"); pst.setObject(4, "value3"); - bindStmtResultSet = pst.executeQuery(); - - // Execute the same query with bind values replaced in the sql - String DIRECT_QUERY = - "SELECT t0.C1, " - + "CASE WHEN t0.C1 IN ('value1', 'value3') THEN t0.C2 ELSE null END," - + "CASE WHEN t0.C1 IN ('value2', 'value3') THEN t0.C2 ELSE null END " - + "FROM SNOW41620 t0"; - try (PreparedStatement pst1 = connection.prepareStatement(DIRECT_QUERY)) { - ResultSet directStmtResultSet = pst1.executeQuery(); - - checkResultSetEqual(bindStmtResultSet, directStmtResultSet); - - bindStmtResultSet.close(); - directStmtResultSet.close(); + try (ResultSet bindStmtResultSet = pst.executeQuery()) { + + // Execute the same query with bind values replaced in the sql + String DIRECT_QUERY = + "SELECT t0.C1, " + + "CASE WHEN t0.C1 IN ('value1', 'value3') THEN t0.C2 ELSE null END," + + "CASE WHEN t0.C1 IN ('value2', 'value3') THEN t0.C2 ELSE null END " + + "FROM SNOW41620 t0"; + try (PreparedStatement pst1 = connection.prepareStatement(DIRECT_QUERY); + ResultSet directStmtResultSet = pst1.executeQuery()) { + checkResultSetEqual(bindStmtResultSet, directStmtResultSet); + } } } } @@ -650,8 +651,9 @@ public void testPreparedStatementWithSkipParsing() throws Exception { @Test public void testPreparedStatementWithSkipParsingAndBinding() throws Exception { - try (Connection con = init()) { - con.createStatement().execute("create or replace table t(c1 int)"); + try (Connection con = init(); + Statement statement = con.createStatement()) { + statement.execute("create or replace table t(c1 int)"); try { try (PreparedStatement stmt = con.unwrap(SnowflakeConnectionV1.class) @@ -661,13 +663,13 @@ public void testPreparedStatementWithSkipParsingAndBinding() throws Exception { assertThat(ret, is(1)); } try (PreparedStatement stmt = - con.unwrap(SnowflakeConnectionV1.class).prepareStatement("select * from t", true)) { - ResultSet rs = stmt.executeQuery(); + con.unwrap(SnowflakeConnectionV1.class).prepareStatement("select * from t", true); + ResultSet rs = stmt.executeQuery()) { assertThat(rs.next(), is(true)); assertThat(rs.getInt(1), is(123)); } } finally { - con.createStatement().execute("drop table if exists t"); + statement.execute("drop table if exists t"); } } } @@ -685,11 +687,12 @@ public void testSnow44393() throws Exception { .execute("alter session set timestamp_ntz_output_format='YYYY-MM-DD HH24:MI:SS'")); try (PreparedStatement stmt = con.prepareStatement("select to_timestamp_ntz(?, 3)")) { stmt.setBigDecimal(1, new BigDecimal("1261440000000")); - ResultSet resultSet = stmt.executeQuery(); - resultSet.next(); + try (ResultSet resultSet = stmt.executeQuery()) { + assertTrue(resultSet.next()); - String res = resultSet.getString(1); - assertThat(res, is("2009-12-22 00:00:00")); + String res = resultSet.getString(1); + assertThat(res, is("2009-12-22 00:00:00")); + } } } } @@ -775,36 +778,38 @@ public void testAddBatchNumericNullFloatMixed() throws Exception { @Test public void testInvalidUsageOfApi() throws Exception { - Connection connection = init(); - final PreparedStatement preparedStatement = connection.prepareStatement("select 1"); - final int expectedCode = ErrorCode.UNSUPPORTED_STATEMENT_TYPE_IN_EXECUTION_API.getMessageCode(); - - assertException( - new RunnableWithSQLException() { - @Override - public void run() throws SQLException { - preparedStatement.executeUpdate("select 1"); - } - }, - expectedCode); - - assertException( - new RunnableWithSQLException() { - @Override - public void run() throws SQLException { - preparedStatement.execute("select 1"); - } - }, - expectedCode); - - assertException( - new RunnableWithSQLException() { - @Override - public void run() throws SQLException { - preparedStatement.addBatch("select 1"); - } - }, - expectedCode); + try (Connection connection = init(); + PreparedStatement preparedStatement = connection.prepareStatement("select 1")) { + final int expectedCode = + ErrorCode.UNSUPPORTED_STATEMENT_TYPE_IN_EXECUTION_API.getMessageCode(); + + assertException( + new RunnableWithSQLException() { + @Override + public void run() throws SQLException { + preparedStatement.executeUpdate("select 1"); + } + }, + expectedCode); + + assertException( + new RunnableWithSQLException() { + @Override + public void run() throws SQLException { + preparedStatement.execute("select 1"); + } + }, + expectedCode); + + assertException( + new RunnableWithSQLException() { + @Override + public void run() throws SQLException { + preparedStatement.addBatch("select 1"); + } + }, + expectedCode); + } } private void assertException(RunnableWithSQLException runnable, int expectedCode) { diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatement2LatestIT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatement2LatestIT.java index 84e5f20ea..f7ca395de 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatement2LatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatement2LatestIT.java @@ -41,23 +41,20 @@ public PreparedStatement2LatestIT() { @Test public void testPrepareUDTF() throws Exception { - try (Connection connection = init()) { + try (Connection connection = init(); + Statement statement = connection.createStatement()) { try { - connection - .createStatement() - .execute("create or replace table employee(id number, address text)"); - connection - .createStatement() - .execute( - "create or replace function employee_detail(sid number, addr text)\n" - + " returns table(id number, address text)\n" - + "LANGUAGE SQL\n" - + "as\n" - + "$$\n" - + "select *\n" - + "from employee\n" - + "where id=sid\n" - + "$$;"); + statement.execute("create or replace table employee(id number, address text)"); + statement.execute( + "create or replace function employee_detail(sid number, addr text)\n" + + " returns table(id number, address text)\n" + + "LANGUAGE SQL\n" + + "as\n" + + "$$\n" + + "select *\n" + + "from employee\n" + + "where id=sid\n" + + "$$;"); // should resolve successfully try (PreparedStatement prepStatement = @@ -87,17 +84,15 @@ public void testPrepareUDTF() throws Exception { } // create a udf with same name but different arguments and return type - connection - .createStatement() - .execute( - "create or replace function employee_detail(name text , addr text)\n" - + " returns table(id number)\n" - + "LANGUAGE SQL\n" - + "as\n" - + "$$\n" - + "select id\n" - + "from employee\n" - + "$$;"); + statement.execute( + "create or replace function employee_detail(name text , addr text)\n" + + " returns table(id number)\n" + + "LANGUAGE SQL\n" + + "as\n" + + "$$\n" + + "select id\n" + + "from employee\n" + + "$$;"); try (PreparedStatement prepStatement = connection.prepareStatement("select * from table(employee_detail(?, 'abc'))")) { @@ -105,10 +100,8 @@ public void testPrepareUDTF() throws Exception { prepStatement.execute(); } } finally { - connection - .createStatement() - .execute("drop function if exists employee_detail(number, text)"); - connection.createStatement().execute("drop function if exists employee_detail(text, text)"); + statement.execute("drop function if exists employee_detail(number, text)"); + statement.execute("drop function if exists employee_detail(text, text)"); } } } @@ -119,38 +112,34 @@ public void testPrepareUDTF() throws Exception { */ @Test public void testSelectWithBinding() throws Throwable { - try (Connection connection = init()) { - connection - .createStatement() - .execute("create or replace table TESTNULL(created_time timestamp_ntz, mid int)"); - PreparedStatement ps; - ResultSet rs; + try (Connection connection = init(); + Statement statement = connection.createStatement()) { try { + statement.execute("create or replace table TESTNULL(created_time timestamp_ntz, mid int)"); // skip bind parameter index check if prepare fails and defer the error checks to execute - ps = + try (PreparedStatement ps = connection.prepareStatement( - "SELECT 1 FROM TESTNULL WHERE CREATED_TIME = TO_TIMESTAMP(?, 3) and MID = ?"); - ps.setObject(1, 0); - ps.setObject(2, null); - rs = ps.executeQuery(); - assertFalse(rs.next()); - rs.close(); - ps.close(); + "SELECT 1 FROM TESTNULL WHERE CREATED_TIME = TO_TIMESTAMP(?, 3) and MID = ?")) { + ps.setObject(1, 0); + ps.setObject(2, null); + try (ResultSet rs = ps.executeQuery()) { + assertFalse(rs.next()); + } + } // describe is success and do the index range check - ps = + try (PreparedStatement ps = connection.prepareStatement( - "SELECT 1 FROM TESTNULL WHERE CREATED_TIME = TO_TIMESTAMP(?::NUMBER, 3) and MID = ?"); - ps.setObject(1, 0); - ps.setObject(2, null); - - rs = ps.executeQuery(); - assertFalse(rs.next()); - rs.close(); - ps.close(); + "SELECT 1 FROM TESTNULL WHERE CREATED_TIME = TO_TIMESTAMP(?::NUMBER, 3) and MID = ?")) { + ps.setObject(1, 0); + ps.setObject(2, null); + try (ResultSet rs = ps.executeQuery()) { + assertFalse(rs.next()); + } + } } finally { - connection.createStatement().execute("drop table if exists TESTNULL"); + statement.execute("drop table if exists TESTNULL"); } } } @@ -175,7 +164,7 @@ public void testConstOptLimitBind() throws SQLException { prepStatement.setInt(1, 10); prepStatement.setInt(2, 0); try (ResultSet resultSet = prepStatement.executeQuery()) { - resultSet.next(); + assertTrue(resultSet.next()); assertThat(resultSet.getInt(1), is(1)); assertThat(resultSet.next(), is(false)); } @@ -198,8 +187,9 @@ public void testTableFuncBindInput() throws SQLException { @Test public void testExecuteLargeBatch() throws SQLException { - try (Connection con = init()) { - try (Statement statement = con.createStatement()) { + try (Connection con = init(); + Statement statement = con.createStatement()) { + try { statement.execute("create or replace table mytab(id int)"); try (PreparedStatement pstatement = con.prepareStatement("insert into mytab(id) values (?)")) { @@ -212,117 +202,138 @@ public void testExecuteLargeBatch() throws SQLException { pstatement.executeLargeBatch(); con.commit(); try (ResultSet resultSet = statement.executeQuery("select * from mytab")) { - resultSet.next(); + assertTrue(resultSet.next()); assertEquals(4, resultSet.getInt(1)); } - statement.execute("drop table if exists mytab"); } + } finally { + statement.execute("drop table if exists mytab"); } } } @Test public void testRemoveExtraDescribeCalls() throws SQLException { - Connection connection = init(); - Statement statement = connection.createStatement(); - statement.execute("create or replace table test_uuid_with_bind(c1 number)"); - - PreparedStatement preparedStatement = - connection.prepareStatement("insert into test_uuid_with_bind values (?)"); - preparedStatement.setInt(1, 5); - assertEquals(1, preparedStatement.executeUpdate()); - String queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); - // Calling getMetadata() should no longer require an additional server call because we have the - // metadata form the executeUpdate - String queryId2 = - preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); - // Assert the query IDs are the same. This will be the case if there is no additional describe - // call for getMetadata(). - assertEquals(queryId1, queryId2); - - preparedStatement.addBatch(); - - preparedStatement = - connection.prepareStatement("select * from test_uuid_with_bind where c1 = ?"); - assertFalse(preparedStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - preparedStatement.setInt(1, 5); - - ResultSet resultSet = preparedStatement.executeQuery(); - assertThat(resultSet.next(), is(true)); - queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); - queryId2 = - preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); - String queryId3 = resultSet.unwrap(SnowflakeResultSet.class).getQueryID(); - // Assert all 3 query IDs are the same because only 1 server call was executed - assertEquals(queryId1, queryId2); - assertEquals(queryId1, queryId3); - - resultSet.close(); - preparedStatement.close(); - - statement.execute("drop table if exists test_uuid_with_bind"); - connection.close(); + String queryId1 = null; + String queryId2 = null; + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute("create or replace table test_uuid_with_bind(c1 number)"); + try (PreparedStatement preparedStatement = + connection.prepareStatement("insert into test_uuid_with_bind values (?)")) { + preparedStatement.setInt(1, 5); + assertEquals(1, preparedStatement.executeUpdate()); + queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); + // Calling getMetadata() should no longer require an additional server call because we + // have + // the + // metadata form the executeUpdate + queryId2 = + preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); + // Assert the query IDs are the same. This will be the case if there is no additional + // describe + // call for getMetadata(). + assertEquals(queryId1, queryId2); + + preparedStatement.addBatch(); + } + try (PreparedStatement preparedStatement = + connection.prepareStatement("select * from test_uuid_with_bind where c1 = ?")) { + assertFalse( + preparedStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + preparedStatement.setInt(1, 5); + + try (ResultSet resultSet = preparedStatement.executeQuery()) { + assertThat(resultSet.next(), is(true)); + queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); + queryId2 = + preparedStatement + .getMetaData() + .unwrap(SnowflakeResultSetMetaData.class) + .getQueryID(); + String queryId3 = resultSet.unwrap(SnowflakeResultSet.class).getQueryID(); + // Assert all 3 query IDs are the same because only 1 server call was executed + assertEquals(queryId1, queryId2); + assertEquals(queryId1, queryId3); + } + } + } finally { + statement.execute("drop table if exists test_uuid_with_bind"); + } + } } @Test public void testRemoveExtraDescribeCallsSanityCheck() throws SQLException { - Connection connection = init(); - PreparedStatement preparedStatement = - connection.prepareStatement( - "create or replace table test_uuid_with_bind(c1 number, c2 string)"); - preparedStatement.execute(); - String queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); - preparedStatement = - connection.prepareStatement("insert into test_uuid_with_bind values (?, ?)"); - assertFalse(preparedStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - preparedStatement.setInt(1, 5); - preparedStatement.setString(2, "hello"); - preparedStatement.addBatch(); - preparedStatement.setInt(1, 7); - preparedStatement.setString(2, "hello1"); - preparedStatement.addBatch(); - String queryId2 = - preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); - // These query IDs should not match because they are from 2 different prepared statements - assertNotEquals(queryId1, queryId2); - preparedStatement.executeBatch(); - String queryId3 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); - // Another execute call was created, so prepared statement has new query ID - assertNotEquals(queryId2, queryId3); - // Calling getMetadata() should no longer require an additional server call because we have the - // metadata form the executeUpdate - String queryId4 = - preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); - // Assert the query IDs for the 2 identical getMetadata() calls are the same. They should match - // since metadata no longer gets overwritten after successive query calls. - assertEquals(queryId2, queryId4); - - connection.createStatement().execute("drop table if exists test_uuid_with_bind"); - preparedStatement.close(); - connection.close(); + String queryId1; + try (Connection connection = init()) { + try (PreparedStatement preparedStatement = + connection.prepareStatement( + "create or replace table test_uuid_with_bind(c1 number, c2 string)")) { + preparedStatement.execute(); + queryId1 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); + } + try (PreparedStatement preparedStatement = + connection.prepareStatement("insert into test_uuid_with_bind values (?, ?)")) { + assertFalse( + preparedStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + preparedStatement.setInt(1, 5); + preparedStatement.setString(2, "hello"); + preparedStatement.addBatch(); + preparedStatement.setInt(1, 7); + preparedStatement.setString(2, "hello1"); + preparedStatement.addBatch(); + String queryId2 = + preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); + // These query IDs should not match because they are from 2 different prepared statements + assertNotEquals(queryId1, queryId2); + preparedStatement.executeBatch(); + String queryId3 = preparedStatement.unwrap(SnowflakePreparedStatement.class).getQueryID(); + // Another execute call was created, so prepared statement has new query ID + assertNotEquals(queryId2, queryId3); + // Calling getMetadata() should no longer require an additional server call because we + // have + // the + // metadata form the executeUpdate + String queryId4 = + preparedStatement.getMetaData().unwrap(SnowflakeResultSetMetaData.class).getQueryID(); + // Assert the query IDs for the 2 identical getMetadata() calls are the same. They should + // match + // since metadata no longer gets overwritten after successive query calls. + assertEquals(queryId2, queryId4); + connection.createStatement().execute("drop table if exists test_uuid_with_bind"); + } + } } @Test public void testAlreadyDescribedMultipleResults() throws SQLException { - Connection connection = init(); - PreparedStatement prepStatement = connection.prepareStatement(insertSQL); - bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); - prepStatement.execute(); - // The statement above has already been described since it has been executed - assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - prepStatement = connection.prepareStatement(selectSQL); - // Assert the statement, once it has been re-created, has already described set to false - assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - prepStatement.setInt(1, 1); - ResultSet rs = prepStatement.executeQuery(); - assertTrue(rs.next()); - assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - prepStatement = connection.prepareStatement(selectAllSQL); - // Assert the statement, once it has been re-created, has already described set to false - assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - rs = prepStatement.executeQuery(); - assertTrue(rs.next()); - assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + try (Connection connection = init()) { + try (PreparedStatement prepStatement = connection.prepareStatement(insertSQL)) { + bindOneParamSet(prepStatement, 1, 1.22222, (float) 1.2, "test", 12121212121L, (short) 12); + prepStatement.execute(); + // The statement above has already been described since it has been executed + assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + } + try (PreparedStatement prepStatement = connection.prepareStatement(selectSQL)) { + // Assert the statement, once it has been re-created, has already described set to false + assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + prepStatement.setInt(1, 1); + try (ResultSet rs = prepStatement.executeQuery()) { + assertTrue(rs.next()); + assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + } + } + try (PreparedStatement prepStatement = connection.prepareStatement(selectAllSQL)) { + // Assert the statement, once it has been re-created, has already described set to false + assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + try (ResultSet rs = prepStatement.executeQuery()) { + assertTrue(rs.next()); + assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + } + } + } } /** @@ -333,40 +344,48 @@ public void testAlreadyDescribedMultipleResults() throws SQLException { */ @Test public void testConsecutiveBatchInsertError() throws SQLException { - try (Connection connection = init()) { - connection - .createStatement() - .execute("create or replace table testStageArrayBind(c1 integer, c2 string)"); - PreparedStatement prepStatement = - connection.prepareStatement("insert into testStageArrayBind values (?, ?)"); - // Assert to begin with that before the describe call, array binding is not supported - assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); - assertFalse(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); - // Insert enough rows to hit the default binding array threshold - for (int i = 0; i < 35000; i++) { - prepStatement.setInt(1, i); - prepStatement.setString(2, "test" + i); - prepStatement.addBatch(); - } - prepStatement.executeBatch(); - // After executing the first batch, verify that array bind support is still true - assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); - for (int i = 0; i < 35000; i++) { - prepStatement.setInt(1, i); - prepStatement.setString(2, "test" + i); - prepStatement.addBatch(); + try (Connection connection = init(); + Statement statement = connection.createStatement()) { + try { + statement.execute("create or replace table testStageArrayBind(c1 integer, c2 string)"); + try (PreparedStatement prepStatement = + connection.prepareStatement("insert into testStageArrayBind values (?, ?)")) { + // Assert to begin with that before the describe call, array binding is not supported + assertFalse( + prepStatement.unwrap(SnowflakePreparedStatementV1.class).isAlreadyDescribed()); + assertFalse( + prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); + // Insert enough rows to hit the default binding array threshold + for (int i = 0; i < 35000; i++) { + prepStatement.setInt(1, i); + prepStatement.setString(2, "test" + i); + prepStatement.addBatch(); + } + prepStatement.executeBatch(); + // After executing the first batch, verify that array bind support is still true + assertTrue( + prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); + for (int i = 0; i < 35000; i++) { + prepStatement.setInt(1, i); + prepStatement.setString(2, "test" + i); + prepStatement.addBatch(); + } + prepStatement.executeBatch(); + // After executing the second batch, verify that array bind support is still true + assertTrue( + prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); + } + } finally { + statement.execute("drop table if exists testStageArrayBind"); } - prepStatement.executeBatch(); - // After executing the second batch, verify that array bind support is still true - assertTrue(prepStatement.unwrap(SnowflakePreparedStatementV1.class).isArrayBindSupported()); } } @Test public void testToString() throws SQLException { - try (Connection connection = init()) { - PreparedStatement prepStatement = - connection.prepareStatement("select current_version() --testing toString()"); + try (Connection connection = init(); + PreparedStatement prepStatement = + connection.prepareStatement("select current_version() --testing toString()")) { // Query ID is going to be null since we didn't execute the statement yet assertEquals( diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatementFeatureNotSupportedIT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatementFeatureNotSupportedIT.java index e3ec67b83..f80a00528 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatementFeatureNotSupportedIT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatementFeatureNotSupportedIT.java @@ -14,8 +14,8 @@ public class PreparedStatementFeatureNotSupportedIT extends BaseJDBCTest { @Test public void testFeatureNotSupportedException() throws Throwable { - try (Connection connection = getConnection()) { - PreparedStatement preparedStatement = connection.prepareStatement("select ?"); + try (Connection connection = getConnection(); + PreparedStatement preparedStatement = connection.prepareStatement("select ?")) { expectFeatureNotSupportedException( () -> preparedStatement.setAsciiStream(1, new BaseJDBCTest.FakeInputStream())); expectFeatureNotSupportedException( diff --git a/src/test/java/net/snowflake/client/jdbc/PreparedStatementLargeUpdateLatestIT.java b/src/test/java/net/snowflake/client/jdbc/PreparedStatementLargeUpdateLatestIT.java index a1dfbb81c..883fe0c4d 100644 --- a/src/test/java/net/snowflake/client/jdbc/PreparedStatementLargeUpdateLatestIT.java +++ b/src/test/java/net/snowflake/client/jdbc/PreparedStatementLargeUpdateLatestIT.java @@ -9,6 +9,7 @@ import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.SQLException; +import java.sql.Statement; import java.util.Map; import net.snowflake.client.ConditionalIgnoreRule; import net.snowflake.client.RunningOnGithubAction; @@ -29,26 +30,31 @@ public class PreparedStatementLargeUpdateLatestIT extends BaseJDBCTest { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testLargeUpdate() throws Throwable { - try (Connection con = getConnection()) { - long expectedUpdateRows = (long) Integer.MAX_VALUE + 10L; - con.createStatement().execute("create or replace table test_large_update(c1 boolean)"); - PreparedStatement st = - con.prepareStatement( - "insert into test_large_update select true from table(generator(rowcount=>" - + expectedUpdateRows - + "))"); - PreparedStatement spyp = spy(st); - // Mock internal method which returns rowcount - Mockito.doReturn(expectedUpdateRows) - .when((SnowflakePreparedStatementV1) spyp) - .executeUpdateInternal( - Mockito.any(String.class), - Mockito.any(Map.class), - Mockito.any(boolean.class), - Mockito.any(ExecTimeTelemetryData.class)); - long updatedRows = spyp.executeLargeUpdate(); - assertEquals(expectedUpdateRows, updatedRows); - con.createStatement().execute("drop table if exists test_large_update"); + try (Connection con = getConnection(); + Statement statement = con.createStatement()) { + try { + long expectedUpdateRows = (long) Integer.MAX_VALUE + 10L; + statement.execute("create or replace table test_large_update(c1 boolean)"); + try (PreparedStatement st = + con.prepareStatement( + "insert into test_large_update select true from table(generator(rowcount=>" + + expectedUpdateRows + + "))"); + PreparedStatement spyp = spy(st)) { + // Mock internal method which returns rowcount + Mockito.doReturn(expectedUpdateRows) + .when((SnowflakePreparedStatementV1) spyp) + .executeUpdateInternal( + Mockito.any(String.class), + Mockito.any(Map.class), + Mockito.any(boolean.class), + Mockito.any(ExecTimeTelemetryData.class)); + long updatedRows = spyp.executeLargeUpdate(); + assertEquals(expectedUpdateRows, updatedRows); + } + } finally { + statement.execute("drop table if exists test_large_update"); + } } } @@ -60,26 +66,30 @@ public void testLargeUpdate() throws Throwable { @Test @ConditionalIgnoreRule.ConditionalIgnore(condition = RunningOnGithubAction.class) public void testExecuteLargeBatchOverIntMax() throws SQLException { - try (Connection connection = getConnection()) { - connection - .createStatement() - .execute("create or replace table over_int_table (val string, id int)"); - PreparedStatement pstmt = connection.prepareStatement("UPDATE over_int_table SET ID=200"); - PreparedStatement spyp = spy(pstmt); - long numRows = Integer.MAX_VALUE + 10L; - // Mock internal method which returns rowcount - Mockito.doReturn(numRows) - .when((SnowflakePreparedStatementV1) spyp) - .executeUpdateInternal( - Mockito.any(String.class), - Mockito.any(Map.class), - Mockito.any(boolean.class), - Mockito.any(ExecTimeTelemetryData.class)); - pstmt.addBatch(); - long[] queryResult = spyp.executeLargeBatch(); - assertEquals(1, queryResult.length); - assertEquals(numRows, queryResult[0]); - connection.createStatement().execute("drop table if exists over_int_table"); + try (Connection connection = getConnection(); + Statement statement = connection.createStatement()) { + try { + statement.execute("create or replace table over_int_table (val string, id int)"); + try (PreparedStatement pstmt = + connection.prepareStatement("UPDATE over_int_table SET ID=200"); + PreparedStatement spyp = spy(pstmt)) { + long numRows = Integer.MAX_VALUE + 10L; + // Mock internal method which returns rowcount + Mockito.doReturn(numRows) + .when((SnowflakePreparedStatementV1) spyp) + .executeUpdateInternal( + Mockito.any(String.class), + Mockito.any(Map.class), + Mockito.any(boolean.class), + Mockito.any(ExecTimeTelemetryData.class)); + pstmt.addBatch(); + long[] queryResult = spyp.executeLargeBatch(); + assertEquals(1, queryResult.length); + assertEquals(numRows, queryResult[0]); + } + } finally { + statement.execute("drop table if exists over_int_table"); + } } } }