diff --git a/bigtable-client-core-parent/bigtable-client-core/pom.xml b/bigtable-client-core-parent/bigtable-client-core/pom.xml index 2f6bd4a7eb..dd209d901d 100644 --- a/bigtable-client-core-parent/bigtable-client-core/pom.xml +++ b/bigtable-client-core-parent/bigtable-client-core/pom.xml @@ -214,6 +214,13 @@ limitations under the License. + + com.google.cloud.bigtable + bigtable-internal-test-helper + ${project.version} + test + + com.google.code.gson gson diff --git a/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestAppProfile.java b/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestAppProfile.java index f586a76d5a..d987b0848c 100644 --- a/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestAppProfile.java +++ b/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestAppProfile.java @@ -34,16 +34,15 @@ import com.google.cloud.bigtable.data.v2.models.Query; import com.google.cloud.bigtable.grpc.async.BulkMutation; import com.google.cloud.bigtable.grpc.async.BulkRead; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.base.Preconditions; import com.google.common.collect.Queues; import com.google.protobuf.ByteString; import com.google.rpc.Code; import com.google.rpc.Status; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.concurrent.BlockingQueue; import java.util.concurrent.TimeUnit; import org.junit.After; @@ -65,18 +64,13 @@ public class TestAppProfile { public void setUp() throws IOException { fakeDataService = new FakeDataService(); - final int port; - try (ServerSocket s = new ServerSocket(0)) { - port = s.getLocalPort(); - } - server = ServerBuilder.forPort(port).addService(fakeDataService).build(); - server.start(); + server = TestServerBuilder.newInstance().addService(fakeDataService).buildAndStart(); BigtableOptions opts = BigtableOptions.builder() .setDataHost("localhost") .setAdminHost("localhost") - .setPort(port) + .setPort(server.getPort()) .setProjectId("fake-project") .setInstanceId("fake-instance") .setUserAgent("fake-agent") diff --git a/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestHeaders.java b/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestHeaders.java index 4750b388d1..0769675e2a 100644 --- a/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestHeaders.java +++ b/bigtable-client-core-parent/bigtable-client-core/src/test/java/com/google/cloud/bigtable/grpc/TestHeaders.java @@ -27,16 +27,15 @@ import com.google.cloud.bigtable.config.CredentialOptions; import com.google.cloud.bigtable.config.Logger; import com.google.cloud.bigtable.data.v2.BigtableDataClient; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import io.grpc.ForwardingServerCall; import io.grpc.Metadata; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.ServerCall; import io.grpc.ServerCallHandler; import io.grpc.ServerInterceptor; import io.grpc.ServerInterceptors; import io.grpc.stub.StreamObserver; -import java.net.ServerSocket; import java.util.concurrent.atomic.AtomicBoolean; import java.util.regex.Pattern; import org.junit.After; @@ -87,12 +86,8 @@ public void tearDown() throws Exception { */ @Test public void testCBC_UserAgentUsingPlainTextNegotiation() throws Exception { - ServerSocket serverSocket = new ServerSocket(0); - final int availablePort = serverSocket.getLocalPort(); - serverSocket.close(); - // Creates non-ssl server. - createServer(availablePort); + createServer(); BigtableOptions bigtableOptions = BigtableOptions.builder() @@ -103,7 +98,7 @@ public void testCBC_UserAgentUsingPlainTextNegotiation() throws Exception { .setUserAgent(TEST_USER_AGENT) .setUsePlaintextNegotiation(true) .setCredentialOptions(CredentialOptions.nullCredential()) - .setPort(availablePort) + .setPort(server.getPort()) .build(); xGoogApiPattern = Pattern.compile(".* cbt/.*"); @@ -115,12 +110,8 @@ public void testCBC_UserAgentUsingPlainTextNegotiation() throws Exception { @Test public void testCBC_tracingCookie() throws Exception { - ServerSocket serverSocket = new ServerSocket(0); - final int availablePort = serverSocket.getLocalPort(); - serverSocket.close(); - // Creates non-ssl server. - createServer(availablePort); + createServer(); BigtableOptions bigtableOptions = BigtableOptions.builder() @@ -131,7 +122,7 @@ public void testCBC_tracingCookie() throws Exception { .setUserAgent(TEST_USER_AGENT) .setUsePlaintextNegotiation(true) .setCredentialOptions(CredentialOptions.nullCredential()) - .setPort(availablePort) + .setPort(server.getPort()) .setTracingCookie(TEST_TRACING_COOKIE) .build(); testTracingCookie.set(true); @@ -144,17 +135,17 @@ public void testCBC_tracingCookie() throws Exception { } /** Creates simple server to intercept plainText Negotiation RPCs. */ - private void createServer(int port) throws Exception { + private void createServer() throws Exception { + server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .addService( ServerInterceptors.intercept( new BigtableExtendedImpl(), new HeaderServerInterceptor())) .addService( ServerInterceptors.intercept( new BigtableAdminExtendedImpl(), new HeaderServerInterceptor())) - .build(); - server.start(); + .buildAndStart(); } /** diff --git a/bigtable-client-core-parent/bigtable-hbase/pom.xml b/bigtable-client-core-parent/bigtable-hbase/pom.xml index 467a594a16..68746a4b79 100644 --- a/bigtable-client-core-parent/bigtable-hbase/pom.xml +++ b/bigtable-client-core-parent/bigtable-hbase/pom.xml @@ -175,6 +175,12 @@ limitations under the License. + + com.google.cloud.bigtable + bigtable-internal-test-helper + ${project.version} + test + com.google.api.grpc grpc-google-common-protos diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/classic/TestBigtableClassicApi.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/classic/TestBigtableClassicApi.java index cdb8d4b7fa..57f009ed98 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/classic/TestBigtableClassicApi.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/classic/TestBigtableClassicApi.java @@ -30,13 +30,12 @@ import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; import com.google.cloud.bigtable.hbase.wrappers.BigtableApi; import com.google.cloud.bigtable.hbase.wrappers.BigtableHBaseSettings; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.Queues; import com.google.protobuf.Empty; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.concurrent.BlockingQueue; import java.util.concurrent.TimeUnit; import org.apache.hadoop.conf.Configuration; @@ -59,22 +58,17 @@ public class TestBigtableClassicApi { private static FakeDataService fakeDataService = new FakeDataService(); private static FakeAdminService fakeAdminService = new FakeAdminService(); private static Server server; - private static int port; private BigtableHBaseSettings bigtableHBaseSettings; private BigtableApi bigtableApi; @BeforeClass public static void setUpServer() throws IOException { - try (ServerSocket s = new ServerSocket(0)) { - port = s.getLocalPort(); - } server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .addService(fakeDataService) .addService(fakeAdminService) - .build(); - server.start(); + .buildAndStart(); } @AfterClass @@ -92,7 +86,8 @@ public void setUp() throws IOException { configuration.set(BigtableOptionsFactory.INSTANCE_ID_KEY, TEST_INSTANCE_ID); configuration.set(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, "true"); configuration.set(BigtableOptionsFactory.BIGTABLE_DATA_CHANNEL_COUNT_KEY, "1"); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + port); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + server.getPort()); configuration.setBoolean(BigtableOptionsFactory.BIGTABLE_USE_GCJ_CLIENT, false); bigtableHBaseSettings = BigtableHBaseClassicSettings.create(configuration); bigtableApi = BigtableApi.create(bigtableHBaseSettings); diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/SharedDataClientWrapperFactoryTest.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/SharedDataClientWrapperFactoryTest.java index d4ded1d168..e4bdd8e6ef 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/SharedDataClientWrapperFactoryTest.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/SharedDataClientWrapperFactoryTest.java @@ -21,17 +21,16 @@ import com.google.cloud.bigtable.data.v2.models.RowMutation; import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; import com.google.cloud.bigtable.hbase.wrappers.DataClientWrapper; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import io.grpc.Grpc; import io.grpc.Metadata; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.ServerCall; import io.grpc.ServerCall.Listener; import io.grpc.ServerCallHandler; import io.grpc.ServerInterceptor; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.net.SocketAddress; import java.util.ArrayList; import java.util.Collection; @@ -58,23 +57,17 @@ @RunWith(JUnit4.class) public class SharedDataClientWrapperFactoryTest { private Server server; - private int port; private List remoteCallers; @Before public void setUp() throws IOException { - try (ServerSocket ss = new ServerSocket(0)) { - port = ss.getLocalPort(); - } - remoteCallers = Collections.synchronizedList(new ArrayList()); server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .intercept(new RemoteCallerInterceptor(remoteCallers)) .addService(new FakeBigtable()) - .build(); - server.start(); + .buildAndStart(); } @After @@ -94,7 +87,7 @@ public void testChannelsAreShared() throws Exception { // Manually expand BIGTABLE_EMULATOR_HOST_KEY so that the channel settings are known configuration.set(BigtableOptionsFactory.BIGTABLE_HOST_KEY, "localhost"); - configuration.setInt(BigtableOptionsFactory.BIGTABLE_PORT_KEY, port); + configuration.setInt(BigtableOptionsFactory.BIGTABLE_PORT_KEY, server.getPort()); configuration.setBoolean(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, true); configuration.setBoolean(BigtableOptionsFactory.BIGTABLE_USE_PLAINTEXT_NEGOTIATION, true); diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestAdminClientVeneerApi.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestAdminClientVeneerApi.java index 33524ad7e4..d46aa59521 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestAdminClientVeneerApi.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestAdminClientVeneerApi.java @@ -26,6 +26,7 @@ import com.google.cloud.bigtable.admin.v2.models.Table; import com.google.cloud.bigtable.grpc.BigtableClusterName; import com.google.cloud.bigtable.grpc.BigtableInstanceName; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.Queues; import com.google.longrunning.GetOperationRequest; import com.google.longrunning.Operation; @@ -34,9 +35,7 @@ import com.google.protobuf.ByteString; import com.google.protobuf.Empty; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; -import java.net.ServerSocket; import java.util.Arrays; import java.util.List; import java.util.concurrent.BlockingQueue; @@ -75,20 +74,14 @@ public class TestAdminClientVeneerApi { @Before public void setUp() throws Exception { - final int port; - try (ServerSocket serverSocket = new ServerSocket(0)) { - port = serverSocket.getLocalPort(); - } - server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .addService(fakeOperationsGrpc) .addService(fakeAdminService) - .build(); - server.start(); + .buildAndStart(); adminClientV2 = BigtableTableAdminClient.create( - BigtableTableAdminSettings.newBuilderForEmulator(port) + BigtableTableAdminSettings.newBuilderForEmulator(server.getPort()) .setProjectId(PROJECT_ID) .setInstanceId(INSTANCE_ID) .build()); diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableHBaseVeneerSettings.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableHBaseVeneerSettings.java index 76ceaa11da..dc77e087a2 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableHBaseVeneerSettings.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableHBaseVeneerSettings.java @@ -67,7 +67,6 @@ import com.google.common.base.Optional; import io.grpc.internal.GrpcUtil; import java.io.IOException; -import java.net.ServerSocket; import java.util.Map; import org.apache.hadoop.conf.Configuration; import org.junit.Before; @@ -396,9 +395,9 @@ public void testDefaultThrottlingDisabled() throws IOException { @Test public void testDataSettingsWithEmulator() throws IOException { - ServerSocket serverSocket = new ServerSocket(0); - final int availablePort = serverSocket.getLocalPort(); - serverSocket.close(); + // A real port isn't required for this test; only verifying the configs can be stored and + // retrieved. + final int availablePort = 987654321; String emulatorHost = "localhost:" + availablePort; configuration.set(BIGTABLE_EMULATOR_HOST_KEY, emulatorHost); @@ -413,9 +412,9 @@ public void testDataSettingsWithEmulator() throws IOException { @Test public void testAdminSettingsWithEmulator() throws IOException { - ServerSocket serverSocket = new ServerSocket(0); - final int availablePort = serverSocket.getLocalPort(); - serverSocket.close(); + // A real port isn't required for this test; only verifying the configs can be stored and + // retrieved. + final int availablePort = 987654321; String emulatorHost = "localhost:" + availablePort; configuration.set(BIGTABLE_EMULATOR_HOST_KEY, emulatorHost); diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableVeneerApi.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableVeneerApi.java index 7a15746ca7..fa7e8d9cd2 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableVeneerApi.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBigtableVeneerApi.java @@ -30,13 +30,12 @@ import com.google.cloud.bigtable.hbase.wrappers.BigtableApi; import com.google.cloud.bigtable.hbase.wrappers.BigtableHBaseSettings; import com.google.cloud.bigtable.hbase.wrappers.classic.BigtableHBaseClassicSettings; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.Queues; import com.google.protobuf.Empty; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.concurrent.BlockingQueue; import java.util.concurrent.TimeUnit; import org.apache.hadoop.conf.Configuration; @@ -62,23 +61,19 @@ public class TestBigtableVeneerApi { @Before public void setUp() throws IOException { - final int port; - try (ServerSocket s = new ServerSocket(0)) { - port = s.getLocalPort(); - } server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .addService(fakeDataService) .addService(fakeAdminService) - .build(); - server.start(); + .buildAndStart(); Configuration configuration = new Configuration(false); configuration.set(BigtableOptionsFactory.PROJECT_ID_KEY, TEST_PROJECT_ID); configuration.set(BigtableOptionsFactory.INSTANCE_ID_KEY, TEST_INSTANCE_ID); configuration.set(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, "true"); configuration.set(BigtableOptionsFactory.BIGTABLE_DATA_CHANNEL_COUNT_KEY, "1"); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + port); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + server.getPort()); configuration.set(BigtableOptionsFactory.BIGTABLE_USE_GCJ_CLIENT, "true"); bigtableHBaseSettings = BigtableHBaseClassicSettings.create(configuration); bigtableApi = BigtableApi.create(bigtableHBaseSettings); diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBulkReadVeneerApi.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBulkReadVeneerApi.java index adac3526a5..dd6c2b4ff8 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBulkReadVeneerApi.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/com/google/cloud/bigtable/hbase/wrappers/veneer/TestBulkReadVeneerApi.java @@ -29,12 +29,11 @@ import com.google.cloud.bigtable.data.v2.BigtableDataSettings; import com.google.cloud.bigtable.data.v2.models.Filters; import com.google.cloud.bigtable.hbase.wrappers.BulkReadWrapper; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.protobuf.ByteString; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.ArrayList; import java.util.List; import java.util.concurrent.atomic.AtomicInteger; @@ -58,17 +57,11 @@ public class TestBulkReadVeneerApi { @Before public void setUp() throws IOException { - final int port; - try (ServerSocket s = new ServerSocket(0)) { - port = s.getLocalPort(); - } - fakeDataService = new FakeDataService(); - server = ServerBuilder.forPort(port).addService(fakeDataService).build(); - server.start(); + server = TestServerBuilder.newInstance().addService(fakeDataService).buildAndStart(); settingsBuilder = - BigtableDataSettings.newBuilderForEmulator(port) + BigtableDataSettings.newBuilderForEmulator(server.getPort()) .setProjectId("fake-project") .setInstanceId("fake-instance"); } diff --git a/bigtable-client-core-parent/bigtable-hbase/src/test/java/org/apache/hadoop/hbase/client/TestAbstractBigtableConnection.java b/bigtable-client-core-parent/bigtable-hbase/src/test/java/org/apache/hadoop/hbase/client/TestAbstractBigtableConnection.java index e752bda930..dae02147c3 100644 --- a/bigtable-client-core-parent/bigtable-hbase/src/test/java/org/apache/hadoop/hbase/client/TestAbstractBigtableConnection.java +++ b/bigtable-client-core-parent/bigtable-hbase/src/test/java/org/apache/hadoop/hbase/client/TestAbstractBigtableConnection.java @@ -33,13 +33,13 @@ import com.google.cloud.bigtable.hbase.BigtableHBaseVersion; import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; import com.google.cloud.bigtable.hbase.adapters.SampledRowKeysAdapter; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.ImmutableList; import com.google.common.collect.Queues; import com.google.common.truth.Truth; import io.grpc.Metadata; import io.grpc.Metadata.Key; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.ServerCall; import io.grpc.ServerCall.Listener; import io.grpc.ServerCallHandler; @@ -47,7 +47,6 @@ import io.grpc.internal.GrpcUtil; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.List; import java.util.concurrent.BlockingQueue; import java.util.concurrent.ExecutorService; @@ -86,7 +85,6 @@ public class TestAbstractBigtableConnection { private static final FakeDataService fakeDataService = new FakeDataService(); private static Server server; - private static int port; private ServerHeaderInterceptor headerInterceptor; @Mock private AbstractBigtableAdmin mockBigtableAdmin; @@ -97,23 +95,20 @@ public class TestAbstractBigtableConnection { @Before public void setUp() throws IOException { - try (ServerSocket s = new ServerSocket(0)) { - port = s.getLocalPort(); - } headerInterceptor = new ServerHeaderInterceptor(); server = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .intercept(headerInterceptor) .addService(fakeDataService) - .build(); - server.start(); + .buildAndStart(); Configuration configuration = new Configuration(false); configuration.set(BigtableOptionsFactory.PROJECT_ID_KEY, PROJECT_ID); configuration.set(BigtableOptionsFactory.INSTANCE_ID_KEY, INSTANCE_ID); configuration.set(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, "true"); configuration.set(BigtableOptionsFactory.BIGTABLE_DATA_CHANNEL_COUNT_KEY, "1"); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, HOST_NAME + ":" + port); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, HOST_NAME + ":" + server.getPort()); connection = new TestBigtableConnectionImpl(configuration); } @@ -131,7 +126,8 @@ public void testRegionLocator() throws IOException { assertEquals(regionInfo, connection.getAllRegionInfos(TABLE_NAME).get(0)); List expectedRegionLocations = - ImmutableList.of(new HRegionLocation(regionInfo, ServerName.valueOf(HOST_NAME, port, 0))); + ImmutableList.of( + new HRegionLocation(regionInfo, ServerName.valueOf(HOST_NAME, server.getPort(), 0))); when(mockSampledAdapter.adaptResponse(Mockito.>any())) .thenReturn(expectedRegionLocations); diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/pom.xml b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/pom.xml index 930b8b984c..74162c0deb 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/pom.xml +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/pom.xml @@ -249,6 +249,12 @@ limitations under the License. + + com.google.cloud.bigtable + bigtable-internal-test-helper + ${project.version} + test + diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/src/test/java/com/google/cloud/bigtable/hbase/TestRpcRetryBehavior.java b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/src/test/java/com/google/cloud/bigtable/hbase/TestRpcRetryBehavior.java index 2e7eebe224..62c794b0b5 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/src/test/java/com/google/cloud/bigtable/hbase/TestRpcRetryBehavior.java +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x-integration-tests/src/test/java/com/google/cloud/bigtable/hbase/TestRpcRetryBehavior.java @@ -32,14 +32,13 @@ import com.google.bigtable.v2.ReadRowsRequest; import com.google.bigtable.v2.ReadRowsResponse; import com.google.cloud.bigtable.config.Logger; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.ImmutableMap; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.Status; import io.grpc.StatusRuntimeException; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.Map; import java.util.concurrent.atomic.AtomicInteger; import org.apache.commons.lang.time.StopWatch; @@ -222,12 +221,8 @@ private Server startFake() throws Exception { final BigtableGrpc.BigtableImplBase rpcBase = setupRpcCall(); BigtableGrpc.BigtableImplBase rpcSleepWrapper = setupRpcServerWithSleepHandler(rpcBase); - int portNum; - try (ServerSocket ss = new ServerSocket(0)) { - portNum = ss.getLocalPort(); - } - Server fakeBigtableServer = ServerBuilder.forPort(portNum).addService(rpcSleepWrapper).build(); - fakeBigtableServer.start(); + Server fakeBigtableServer = + TestServerBuilder.newInstance().addService(rpcSleepWrapper).buildAndStart(); return fakeBigtableServer; } diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/pom.xml b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/pom.xml index 76ccae9d57..7dc6975ce5 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/pom.xml +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/pom.xml @@ -148,6 +148,12 @@ limitations under the License. + + com.google.cloud.bigtable + bigtable-internal-test-helper + ${project.version} + test + com.google.truth truth diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/BigtableAdminTest.java b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/BigtableAdminTest.java index fbced4e383..2cfee4d7a4 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/BigtableAdminTest.java +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/BigtableAdminTest.java @@ -22,11 +22,11 @@ import com.google.bigtable.admin.v2.DropRowRangeRequest; import com.google.cloud.bigtable.hbase.BigtableConfiguration; import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.protobuf.ByteString; import com.google.protobuf.Empty; import io.grpc.*; import java.io.IOException; -import java.net.ServerSocket; import java.util.concurrent.ArrayBlockingQueue; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.hbase.ClusterStatus; @@ -54,21 +54,16 @@ public class BigtableAdminTest { @Before public void setup() throws Exception { - final int port; - - try (ServerSocket serverSocket = new ServerSocket(0)) { - port = serverSocket.getLocalPort(); - } - fakeBigtableServer = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .intercept(new RequestInterceptor()) .addService(new BigtableTableAdminGrpc.BigtableTableAdminImplBase() {}) - .build(); - fakeBigtableServer.start(); + .buildAndStart(); Configuration configuration = BigtableConfiguration.configure(PROJECT_ID, INSTANCE_ID); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + port); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, + "localhost:" + fakeBigtableServer.getPort()); connection = new BigtableConnection(configuration); admin = (BigtableAdmin) connection.getAdmin(); } diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableAdmin.java b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableAdmin.java index 740672debe..6b2bf670b6 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableAdmin.java +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableAdmin.java @@ -22,17 +22,16 @@ import com.google.bigtable.admin.v2.DropRowRangeRequest; import com.google.cloud.bigtable.hbase.BigtableConfiguration; import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.protobuf.ByteString; import com.google.protobuf.Empty; import io.grpc.Metadata; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.ServerCall; import io.grpc.ServerCallHandler; import io.grpc.ServerInterceptor; import io.grpc.Status; import java.io.IOException; -import java.net.ServerSocket; import java.util.concurrent.ArrayBlockingQueue; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.hbase.ClusterStatus; @@ -61,21 +60,16 @@ public class TestBigtableAdmin { @Before public void setup() throws Exception { - final int port; - - try (ServerSocket serverSocket = new ServerSocket(0)) { - port = serverSocket.getLocalPort(); - } - fakeBigtableServer = - ServerBuilder.forPort(port) + TestServerBuilder.newInstance() .intercept(new RequestInterceptor()) .addService(new BigtableTableAdminGrpc.BigtableTableAdminImplBase() {}) - .build(); - fakeBigtableServer.start(); + .buildAndStart(); Configuration configuration = BigtableConfiguration.configure(PROJECT_ID, INSTANCE_ID); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + port); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, + "localhost:" + fakeBigtableServer.getPort()); connection = new BigtableConnection(configuration); admin = (BigtableAdmin) connection.getAdmin(); } diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableConnection.java b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableConnection.java index 5a31f033e6..a30c47ab3c 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableConnection.java +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestBigtableConnection.java @@ -24,13 +24,12 @@ import com.google.cloud.bigtable.data.v2.internal.NameUtil; import com.google.cloud.bigtable.hbase.AbstractBigtableTable; import com.google.cloud.bigtable.hbase.BigtableOptionsFactory; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.collect.Queues; import com.google.protobuf.ByteString; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.List; import java.util.concurrent.BlockingQueue; import java.util.concurrent.Executors; @@ -57,7 +56,6 @@ public class TestBigtableConnection { private static final String FULL_TABLE_NAME = NameUtil.formatTableName(TEST_PROJECT_ID, TEST_INSTANCE_ID, TABLE_NAME.getNameAsString()); private static Server server; - private static int dataPort; private static FakeDataService fakeDataService = new FakeDataService(); private Configuration configuration; @@ -65,11 +63,7 @@ public class TestBigtableConnection { @BeforeClass public static void setUpServer() throws IOException { - try (ServerSocket s = new ServerSocket(0)) { - dataPort = s.getLocalPort(); - } - server = ServerBuilder.forPort(dataPort).addService(fakeDataService).build(); - server.start(); + server = TestServerBuilder.newInstance().addService(fakeDataService).buildAndStart(); } @AfterClass @@ -87,7 +81,8 @@ public void setUp() throws IOException { configuration.set(BigtableOptionsFactory.INSTANCE_ID_KEY, TEST_INSTANCE_ID); configuration.set(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, "true"); configuration.set(BigtableOptionsFactory.BIGTABLE_DATA_CHANNEL_COUNT_KEY, "1"); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + dataPort); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + server.getPort()); connection = new BigtableConnection(configuration); } diff --git a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestMetrics.java b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestMetrics.java index cc62f3ffb0..f702238f31 100644 --- a/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestMetrics.java +++ b/bigtable-hbase-1.x-parent/bigtable-hbase-1.x/src/test/java/com/google/cloud/bigtable/hbase1_x/TestMetrics.java @@ -29,18 +29,17 @@ import com.google.cloud.bigtable.metrics.Meter; import com.google.cloud.bigtable.metrics.MetricRegistry; import com.google.cloud.bigtable.metrics.Timer; +import com.google.cloud.bigtable.test.helper.TestServerBuilder; import com.google.common.base.Stopwatch; import com.google.common.collect.Range; import com.google.protobuf.ByteString; import com.google.protobuf.BytesValue; import com.google.protobuf.StringValue; import io.grpc.Server; -import io.grpc.ServerBuilder; import io.grpc.Status; import io.grpc.StatusRuntimeException; import io.grpc.stub.StreamObserver; import java.io.IOException; -import java.net.ServerSocket; import java.util.ArrayList; import java.util.HashMap; import java.util.List; @@ -68,7 +67,6 @@ public class TestMetrics { private final String TEST_INSTANCE_ID = "fake-instance-id"; private final TableName TABLE_NAME = TableName.valueOf("fake-table"); private Server server; - private int dataPort; private FakeMetricRegistry fakeMetricRegistry; private MetricRegistry originalMetricRegistry; @@ -97,11 +95,7 @@ public class TestMetrics { @Before public void setUp() throws IOException { - try (ServerSocket s = new ServerSocket(0)) { - dataPort = s.getLocalPort(); - } - server = ServerBuilder.forPort(dataPort).addService(fakeDataService).build(); - server.start(); + server = TestServerBuilder.newInstance().addService(fakeDataService).buildAndStart(); originalLevelToLog = BigtableClientMetrics.getLevelToLog(); originalMetricRegistry = BigtableClientMetrics.getMetricRegistry(originalLevelToLog); @@ -111,7 +105,8 @@ public void setUp() throws IOException { configuration.set(BigtableOptionsFactory.INSTANCE_ID_KEY, TEST_INSTANCE_ID); configuration.set(BigtableOptionsFactory.BIGTABLE_NULL_CREDENTIAL_ENABLE_KEY, "true"); configuration.set(BigtableOptionsFactory.BIGTABLE_DATA_CHANNEL_COUNT_KEY, "1"); - configuration.set(BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + dataPort); + configuration.set( + BigtableOptionsFactory.BIGTABLE_EMULATOR_HOST_KEY, "localhost:" + server.getPort()); configuration.set(BigtableOptionsFactory.BIGTABLE_USE_GCJ_CLIENT, "true"); fakeMetricRegistry = new FakeMetricRegistry(); diff --git a/bigtable-test/bigtable-internal-test-helper/pom.xml b/bigtable-test/bigtable-internal-test-helper/pom.xml new file mode 100644 index 0000000000..0c8c7a6d76 --- /dev/null +++ b/bigtable-test/bigtable-internal-test-helper/pom.xml @@ -0,0 +1,102 @@ + + + + bigtable-test + com.google.cloud.bigtable + 2.0.0-alpha-1-SNAPSHOT + + 4.0.0 + + bigtable-internal-test-helper + + Module with helper code for Bigtable unit and integration tests. + Not intended to be shared with external users. + + + + + + com.google.cloud + google-cloud-bigtable-bom + ${bigtable.version} + pom + import + + + com.google.cloud + google-cloud-bigtable-deps-bom + ${bigtable.version} + pom + import + + + + + + + io.grpc + grpc-api + + + + + + + + + org.apache.maven.plugins + maven-deploy-plugin + 3.0.0-M1 + + true + + + + org.sonatype.plugins + nexus-staging-maven-plugin + + true + + + + org.apache.maven.plugins + maven-site-plugin + + true + + + + org.apache.maven.plugins + maven-source-plugin + + true + + + + org.apache.maven.plugins + maven-javadoc-plugin + + true + + + + org.apache.maven.plugins + maven-gpg-plugin + + true + + + + org.codehaus.mojo + clirr-maven-plugin + + true + + + + + + + \ No newline at end of file diff --git a/bigtable-test/bigtable-internal-test-helper/src/main/java/com/google/cloud/bigtable/test/helper/TestServerBuilder.java b/bigtable-test/bigtable-internal-test-helper/src/main/java/com/google/cloud/bigtable/test/helper/TestServerBuilder.java new file mode 100644 index 0000000000..436e6795f6 --- /dev/null +++ b/bigtable-test/bigtable-internal-test-helper/src/main/java/com/google/cloud/bigtable/test/helper/TestServerBuilder.java @@ -0,0 +1,121 @@ +/* + * Copyright 2021 Google LLC + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.google.cloud.bigtable.test.helper; + +import io.grpc.BindableService; +import io.grpc.Server; +import io.grpc.ServerBuilder; +import io.grpc.ServerInterceptor; +import io.grpc.ServerServiceDefinition; +import java.io.File; +import java.io.IOException; +import java.net.ServerSocket; +import java.util.ArrayList; +import java.util.List; + +/** + * Wrapper around {@link ServerBuilder} that automatically finds a free port when starting the + * service. + * + *

This wraps the call for getting a random free port (e.g. ServerSocket ss = new + * ServerSocket(0)) into a retry, since it is possible for another process on the host to use the + * port before the caller of the method can. Though it does not happen often, it happens enough to + * cause noticeable test flakes. Retrying the call will minimize the flakes. + */ +public class TestServerBuilder { + private List services = new ArrayList<>(); + private List serverServiceDefinitions = new ArrayList<>(); + private List interceptors = new ArrayList<>(); + private File certChain = null; + private File privateKey = null; + + public static TestServerBuilder newInstance() { + return new TestServerBuilder(); + } + + private TestServerBuilder() {} + + /** See {@link ServerBuilder#addService(BindableService)}. */ + public TestServerBuilder addService(BindableService service) { + services.add(service); + return this; + } + + /** See {@link ServerBuilder#addService(ServerServiceDefinition)}. */ + public TestServerBuilder addService(ServerServiceDefinition serverServiceDefinition) { + serverServiceDefinitions.add(serverServiceDefinition); + return this; + } + + /** See {@link ServerBuilder#intercept(ServerInterceptor)}. */ + public TestServerBuilder intercept(ServerInterceptor interceptor) { + interceptors.add(interceptor); + return this; + } + + /** See {@link ServerBuilder#useTransportSecurity(File, File)}. */ + public TestServerBuilder useTransportSecurity(File certChain, File privateKey) { + this.certChain = certChain; + this.privateKey = privateKey; + return this; + } + + private Server buildServer(int port) { + ServerBuilder builder = ServerBuilder.forPort(port); + + for (BindableService service : services) { + builder.addService(service); + } + for (ServerServiceDefinition serverServiceDefinition : serverServiceDefinitions) { + builder.addService(serverServiceDefinition); + } + for (ServerInterceptor interceptor : interceptors) { + builder.intercept(interceptor); + } + + if (certChain != null || privateKey != null) { + builder.useTransportSecurity(certChain, privateKey); + } + return builder.build(); + } + + /** + * Gets a free port on the host and starts the server, retrying in case the start fails (notably + * if the port is no longer available). + */ + public Server buildAndStart() throws IOException { + IOException lastError = null; + + int maxRetries = 3; + for (int retry = 0; retry < maxRetries; retry++) { + int port; + try (ServerSocket ss = new ServerSocket(0)) { + port = ss.getLocalPort(); + } + + Server server = buildServer(port); + try { + server.start(); + return server; + } catch (IOException e) { + server.shutdown(); + lastError = e; + } + } + + throw lastError; + } +} diff --git a/bigtable-test/pom.xml b/bigtable-test/pom.xml index 974b9cf90f..8fe3cddd6c 100644 --- a/bigtable-test/pom.xml +++ b/bigtable-test/pom.xml @@ -33,5 +33,6 @@ limitations under the License. bigtable-emulator-maven-plugin bigtable-build-helper + bigtable-internal-test-helper