Skip to content

Commit 70f7c13

Browse files
authored
tests: run integration tests against emulator (#172)
* tests: run integration tests against emulator * test: run integration tests against emulator * chore: update name of workflow * test: skip test when there are no credentials * test: change to docker based emulator tests
1 parent 0c5a9c6 commit 70f7c13

File tree

8 files changed

+115
-15
lines changed

8 files changed

+115
-15
lines changed
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
on:
2+
push:
3+
branches:
4+
- master
5+
pull_request:
6+
name: Integration tests against emulator
7+
jobs:
8+
units:
9+
runs-on: ubuntu-latest
10+
11+
services:
12+
emulator:
13+
image: gcr.io/cloud-spanner-emulator/emulator:latest
14+
ports:
15+
- 9010:9010
16+
- 9020:9020
17+
18+
steps:
19+
- uses: actions/checkout@v2
20+
- uses: actions/setup-java@v1
21+
with:
22+
java-version: 8
23+
- run: java -version
24+
- run: .kokoro/build.sh
25+
- run: mvn -B -Dspanner.testenv.instance="" -Penable-integration-tests -DtrimStackTrace=false -Dclirr.skip=true -Denforcer.skip=true -fae verify
26+
env:
27+
JOB_TYPE: test
28+
SPANNER_EMULATOR_HOST: localhost:9010
29+
GOOGLE_CLOUD_PROJECT: emulator-test-project

src/test/java/com/google/cloud/spanner/jdbc/ITAbstractJdbcTest.java

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
import com.google.cloud.spanner.IntegrationTest;
2222
import com.google.cloud.spanner.IntegrationTestEnv;
2323
import com.google.cloud.spanner.connection.AbstractSqlScriptVerifier;
24+
import com.google.cloud.spanner.connection.ConnectionOptions;
2425
import com.google.cloud.spanner.connection.ITAbstractSpannerTest;
2526
import com.google.cloud.spanner.jdbc.JdbcSqlScriptVerifier.JdbcGenericConnection;
2627
import com.google.common.base.Preconditions;
@@ -34,6 +35,7 @@
3435
import java.sql.ResultSet;
3536
import java.sql.SQLException;
3637
import java.util.concurrent.ExecutionException;
38+
import org.junit.AfterClass;
3739
import org.junit.Before;
3840
import org.junit.BeforeClass;
3941
import org.junit.ClassRule;
@@ -57,7 +59,16 @@ public JdbcGenericConnection getConnection() {
5759
}
5860
}
5961

60-
@ClassRule public static IntegrationTestEnv env = new IntegrationTestEnv();
62+
@ClassRule
63+
public static IntegrationTestEnv env =
64+
new IntegrationTestEnv() {
65+
@Override
66+
protected void after() {
67+
super.after();
68+
ConnectionOptions.closeSpanner();
69+
}
70+
};
71+
6172
private static final String DEFAULT_KEY_FILE = null;
6273
private static Database database;
6374

@@ -82,6 +93,11 @@ public static void setup() throws IOException, InterruptedException, ExecutionEx
8293
database = env.getTestHelper().createTestDatabase();
8394
}
8495

96+
@AfterClass
97+
public static void teardown() {
98+
ConnectionOptions.closeSpanner();
99+
}
100+
85101
/**
86102
* Creates a new default JDBC connection to a test database. Use the method {@link
87103
* ITAbstractJdbcTest#appendConnectionUri(StringBuilder)} to append additional connection options

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcConnectTest.java

Lines changed: 28 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
import com.google.cloud.spanner.jdbc.ITAbstractJdbcTest;
2727
import com.google.cloud.spanner.jdbc.JdbcDataSource;
2828
import java.io.FileInputStream;
29+
import java.io.IOException;
2930
import java.sql.Connection;
3031
import java.sql.DriverManager;
3132
import java.sql.ResultSet;
@@ -53,8 +54,14 @@
5354
public class ITJdbcConnectTest extends ITAbstractJdbcTest {
5455

5556
private String createBaseUrl() {
56-
StringBuilder url =
57-
new StringBuilder("jdbc:cloudspanner:/").append(getDatabase().getId().getName());
57+
StringBuilder url = new StringBuilder("jdbc:cloudspanner:");
58+
if (env.getTestHelper().isEmulator()) {
59+
url.append("//").append(System.getenv("SPANNER_EMULATOR_HOST"));
60+
}
61+
url.append("/").append(getDatabase().getId().getName());
62+
if (env.getTestHelper().isEmulator()) {
63+
url.append(";usePlainText=true");
64+
}
5865
return url.toString();
5966
}
6067

@@ -99,7 +106,7 @@ public void testConnectWithURLWithDefaultValues() throws SQLException {
99106
@Test
100107
public void testConnectWithURLWithNonDefaultValues() throws SQLException {
101108
String url = createBaseUrl();
102-
url = url + "?autocommit=false;readonly=true;retryAbortsInternally=false";
109+
url = url + ";autocommit=false;readonly=true;retryAbortsInternally=false";
103110
if (hasValidKeyFile()) {
104111
url = url + ";credentials=" + getKeyFile();
105112
}
@@ -138,7 +145,7 @@ public void testConnectWithPropertiesWithNonDefaultValues() throws SQLException
138145
@Test
139146
public void testConnectWithPropertiesWithConflictingValues() throws SQLException {
140147
String url = createBaseUrl();
141-
url = url + "?autocommit=false;readonly=true;retryAbortsInternally=false";
148+
url = url + ";autocommit=false;readonly=true;retryAbortsInternally=false";
142149
if (hasValidKeyFile()) {
143150
url = url + ";credentials=" + getKeyFile();
144151
}
@@ -167,7 +174,7 @@ public void testConnectWithDataSourceWithDefaultValues() throws SQLException {
167174
public void testConnectWithDataSourceWithNonDefaultValues() throws SQLException {
168175
JdbcDataSource ds = new JdbcDataSource();
169176
ds.setUrl(createBaseUrl());
170-
if (hasValidKeyFile()) {
177+
if (hasValidKeyFile() && !env.getTestHelper().isEmulator()) {
171178
ds.setCredentials(getKeyFile());
172179
}
173180
ds.setAutocommit(false);
@@ -183,7 +190,7 @@ public void testConnectWithDataSourceWithConflictingValues() throws SQLException
183190
// Try with non-default values in URL and default values in data source. The values in the URL
184191
// should take precedent.
185192
String url = createBaseUrl();
186-
url = url + "?autocommit=false;readonly=true;retryAbortsInternally=false";
193+
url = url + ";autocommit=false;readonly=true;retryAbortsInternally=false";
187194
if (hasValidKeyFile()) {
188195
url = url + ";credentials=" + getKeyFile();
189196
}
@@ -203,14 +210,21 @@ public void testConnectWithOAuthToken() throws Exception {
203210
if (hasValidKeyFile()) {
204211
credentials = GoogleCredentials.fromStream(new FileInputStream(getKeyFile()));
205212
} else {
206-
credentials = GoogleCredentials.getApplicationDefault();
207-
}
208-
credentials = credentials.createScoped(SpannerOptions.getDefaultInstance().getScopes());
209-
AccessToken token = credentials.refreshAccessToken();
210-
String urlWithOAuth = createBaseUrl() + "?OAuthToken=" + token.getTokenValue();
211-
try (Connection connectionWithOAuth = DriverManager.getConnection(urlWithOAuth)) {
212-
// Try to do a query using the connection created with an OAuth token.
213-
testDefaultConnection(connectionWithOAuth);
213+
try {
214+
credentials = GoogleCredentials.getApplicationDefault();
215+
} catch (IOException e) {
216+
credentials = null;
217+
}
218+
}
219+
// Skip this test if there are no credentials set for the test case or environment.
220+
if (credentials != null) {
221+
credentials = credentials.createScoped(SpannerOptions.getDefaultInstance().getScopes());
222+
AccessToken token = credentials.refreshAccessToken();
223+
String urlWithOAuth = createBaseUrl() + ";OAuthToken=" + token.getTokenValue();
224+
try (Connection connectionWithOAuth = DriverManager.getConnection(urlWithOAuth)) {
225+
// Try to do a query using the connection created with an OAuth token.
226+
testDefaultConnection(connectionWithOAuth);
227+
}
214228
}
215229
}
216230
}

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcDatabaseMetaDataTest.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
import static org.hamcrest.CoreMatchers.notNullValue;
2222
import static org.hamcrest.CoreMatchers.nullValue;
2323
import static org.hamcrest.MatcherAssert.assertThat;
24+
import static org.junit.Assume.assumeFalse;
2425

2526
import com.google.cloud.spanner.IntegrationTest;
2627
import com.google.cloud.spanner.jdbc.ITAbstractJdbcTest;
@@ -31,6 +32,7 @@
3132
import java.sql.Types;
3233
import java.util.Arrays;
3334
import java.util.List;
35+
import org.junit.BeforeClass;
3436
import org.junit.Test;
3537
import org.junit.experimental.categories.Category;
3638
import org.junit.runner.RunWith;
@@ -49,6 +51,11 @@ public class ITJdbcDatabaseMetaDataTest extends ITAbstractJdbcTest {
4951
private static final String TABLE_WITH_ALL_COLS = "TableWithAllColumnTypes";
5052
private static final String TABLE_WITH_REF = "TableWithRef";
5153

54+
@BeforeClass
55+
public static void skipOnEmulator() {
56+
assumeFalse("foreign keys are not supported on the emulator", env.getTestHelper().isEmulator());
57+
}
58+
5259
@Override
5360
protected boolean doCreateMusicTables() {
5461
return true;

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcPreparedStatementTest.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
import static org.hamcrest.CoreMatchers.nullValue;
2323
import static org.hamcrest.MatcherAssert.assertThat;
2424
import static org.junit.Assert.fail;
25+
import static org.junit.Assume.assumeFalse;
2526

2627
import com.google.api.client.util.Base64;
2728
import com.google.cloud.spanner.IntegrationTest;
@@ -45,6 +46,7 @@
4546
import java.util.List;
4647
import java.util.Scanner;
4748
import java.util.TimeZone;
49+
import org.junit.BeforeClass;
4850
import org.junit.FixMethodOrder;
4951
import org.junit.Test;
5052
import org.junit.experimental.categories.Category;
@@ -254,6 +256,11 @@ private List<Concert> createConcerts() {
254256
return res;
255257
}
256258

259+
@BeforeClass
260+
public static void notOnEmulator() {
261+
assumeFalse("foreign keys are not supported on the emulator", env.getTestHelper().isEmulator());
262+
}
263+
257264
@Override
258265
protected boolean doCreateMusicTables() {
259266
return true;

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcQueryOptionsTest.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818

1919
import static com.google.common.truth.Truth.assertThat;
2020
import static org.junit.Assert.fail;
21+
import static org.junit.Assume.assumeFalse;
2122

2223
import com.google.cloud.spanner.IntegrationTest;
2324
import com.google.cloud.spanner.SpannerOptions;
@@ -95,6 +96,7 @@ public void connectionUrl() throws SQLException {
9596

9697
@Test
9798
public void connectionUrlWithInvalidOptimizerVersion() throws SQLException {
99+
assumeFalse("optimizer version is ignored on emulator", env.getTestHelper().isEmulator());
98100
this.connectionUriSuffix = ";optimizerVersion=9999999";
99101
try (Connection connection = createConnection()) {
100102
try (ResultSet rs = connection.createStatement().executeQuery("SELECT 1")) {
@@ -137,6 +139,7 @@ public void setLatestOptimizerVersion() throws SQLException {
137139

138140
@Test
139141
public void setInvalidOptimizerVersion() throws SQLException {
142+
assumeFalse("optimizer version is ignored on emulator", env.getTestHelper().isEmulator());
140143
try (Connection connection = createConnection()) {
141144
connection.createStatement().execute("SET OPTIMIZER_VERSION='9999999'");
142145
try (ResultSet rs = connection.createStatement().executeQuery("SELECT 1")) {
@@ -151,6 +154,9 @@ public void setInvalidOptimizerVersion() throws SQLException {
151154

152155
@Test
153156
public void optimizerVersionInQueryHint() throws SQLException {
157+
assumeFalse(
158+
"optimizer version in query hint is not supported on emulator",
159+
env.getTestHelper().isEmulator());
154160
try (Connection connection = createConnection()) {
155161
verifyOptimizerVersion(connection, "");
156162
try (ResultSet rs =
@@ -170,6 +176,7 @@ public void optimizerVersionInQueryHint() throws SQLException {
170176

171177
@Test
172178
public void optimizerVersionInEnvironment() throws SQLException {
179+
assumeFalse("optimizer version is ignored on emulator", env.getTestHelper().isEmulator());
173180
try {
174181
SpannerOptions.useEnvironment(
175182
new SpannerOptions.SpannerEnvironment() {

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcReadOnlyTest.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818

1919
import com.google.cloud.spanner.IntegrationTest;
2020
import com.google.cloud.spanner.Mutation;
21+
import com.google.cloud.spanner.connection.ConnectionOptions;
2122
import com.google.cloud.spanner.connection.SqlScriptVerifier;
2223
import com.google.cloud.spanner.jdbc.CloudSpannerJdbcConnection;
2324
import com.google.cloud.spanner.jdbc.ITAbstractJdbcTest;
@@ -28,6 +29,7 @@
2829
import java.util.concurrent.ExecutorService;
2930
import java.util.concurrent.Executors;
3031
import java.util.concurrent.TimeUnit;
32+
import org.junit.After;
3133
import org.junit.Before;
3234
import org.junit.Test;
3335
import org.junit.experimental.categories.Category;
@@ -82,6 +84,11 @@ public void createTestTables() throws Exception {
8284
}
8385
}
8486

87+
@After
88+
public void closeSpanner() {
89+
ConnectionOptions.closeSpanner();
90+
}
91+
8592
@Test
8693
public void testSqlScript() throws Exception {
8794
// Wait 100ms to ensure that staleness tests in the script succeed.

src/test/java/com/google/cloud/spanner/jdbc/it/ITJdbcSqlScriptTest.java

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,13 +21,15 @@
2121
import static org.hamcrest.CoreMatchers.nullValue;
2222
import static org.hamcrest.MatcherAssert.assertThat;
2323

24+
import com.google.cloud.spanner.ErrorCode;
2425
import com.google.cloud.spanner.IntegrationTest;
2526
import com.google.cloud.spanner.connection.SqlScriptVerifier;
2627
import com.google.cloud.spanner.jdbc.ITAbstractJdbcTest;
2728
import com.google.cloud.spanner.jdbc.JdbcSqlScriptVerifier;
2829
import com.google.cloud.spanner.jdbc.JdbcSqlScriptVerifier.JdbcGenericConnection;
2930
import java.sql.Connection;
3031
import java.sql.ResultSet;
32+
import java.sql.SQLException;
3133
import java.sql.Statement;
3234
import org.junit.FixMethodOrder;
3335
import org.junit.Test;
@@ -85,6 +87,12 @@ public void test02_InsertTestData() throws Exception {
8587
JdbcGenericConnection.of(connection),
8688
INSERT_AND_VERIFY_TEST_DATA,
8789
SqlScriptVerifier.class);
90+
} catch (SQLException e) {
91+
if (env.getTestHelper().isEmulator()
92+
&& e.getErrorCode() == ErrorCode.ALREADY_EXISTS.getGrpcStatusCode().value()) {
93+
// Ignore, this is expected as errors during a read/write transaction are sticky on the
94+
// emulator.
95+
}
8896
}
8997
}
9098

@@ -101,6 +109,11 @@ public void test04_TestGetCommitTimestamp() throws Exception {
101109
try (Connection connection = createConnection()) {
102110
verifier.verifyStatementsInFile(
103111
JdbcGenericConnection.of(connection), TEST_GET_COMMIT_TIMESTAMP, SqlScriptVerifier.class);
112+
} catch (SQLException e) {
113+
if (env.getTestHelper().isEmulator()
114+
&& e.getErrorCode() == ErrorCode.INVALID_ARGUMENT.getGrpcStatusCode().value()) {
115+
// Ignore as errors during read/write transactions are sticky on the emulator.
116+
}
104117
}
105118
}
106119

0 commit comments

Comments
 (0)