diff --git a/.kokoro/build.sh b/.kokoro/build.sh
index 605555ecae..f5f585bcd0 100755
--- a/.kokoro/build.sh
+++ b/.kokoro/build.sh
@@ -33,6 +33,7 @@ retry_with_backoff 3 10 \
-DskipTests=true \
-Dclirr.skip=true \
-Denforcer.skip=true \
+ -Dcheckstyle.skip=true \
-Dmaven.javadoc.skip=true \
-Dgcloud.download.skip=true \
-T 1C
@@ -66,7 +67,8 @@ integration)
-DtrimStackTrace=false \
-Dclirr.skip=true \
-Denforcer.skip=true \
- -fae \
+ -Dcheckstyle.skip=true \
+ -DskipUnitTests=true \
verify
RETURN_CODE=$?
;;
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 0a450e7cae..974ce8dd2d 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,18 @@
# Changelog
+## [2.49.0](https://github.com/googleapis/java-bigtable/compare/v2.48.0...v2.49.0) (2024-12-03)
+
+
+### Features
+
+* Add support for table deletion protection ([#2430](https://github.com/googleapis/java-bigtable/issues/2430)) ([687b6df](https://github.com/googleapis/java-bigtable/commit/687b6df14b743358e8207cda26022dfc75338d55))
+
+
+### Bug Fixes
+
+* Allow factory to export to different projects ([#2374](https://github.com/googleapis/java-bigtable/issues/2374)) ([06b912c](https://github.com/googleapis/java-bigtable/commit/06b912cc5d63436757008e79edfa8286b2ccac18))
+* Send priming requests on the channel directly ([#2435](https://github.com/googleapis/java-bigtable/issues/2435)) ([b76698d](https://github.com/googleapis/java-bigtable/commit/b76698dfb2c8552185f34e01e924ecc80798ba4f))
+
## [2.48.0](https://github.com/googleapis/java-bigtable/compare/v2.47.0...v2.48.0) (2024-11-19)
diff --git a/README.md b/README.md
index d114930c70..837665a4aa 100644
--- a/README.md
+++ b/README.md
@@ -56,13 +56,13 @@ implementation 'com.google.cloud:google-cloud-bigtable'
If you are using Gradle without BOM, add this to your dependencies:
```Groovy
-implementation 'com.google.cloud:google-cloud-bigtable:2.48.0'
+implementation 'com.google.cloud:google-cloud-bigtable:2.49.0'
```
If you are using SBT, add this to your dependencies:
```Scala
-libraryDependencies += "com.google.cloud" % "google-cloud-bigtable" % "2.48.0"
+libraryDependencies += "com.google.cloud" % "google-cloud-bigtable" % "2.49.0"
```
## Authentication
@@ -543,7 +543,7 @@ Java is a registered trademark of Oracle and/or its affiliates.
[kokoro-badge-link-5]: http://storage.googleapis.com/cloud-devrel-public/java/badges/java-bigtable/java11.html
[stability-image]: https://img.shields.io/badge/stability-stable-green
[maven-version-image]: https://img.shields.io/maven-central/v/com.google.cloud/google-cloud-bigtable.svg
-[maven-version-link]: https://central.sonatype.com/artifact/com.google.cloud/google-cloud-bigtable/2.48.0
+[maven-version-link]: https://central.sonatype.com/artifact/com.google.cloud/google-cloud-bigtable/2.49.0
[authentication]: https://github.com/googleapis/google-cloud-java#authentication
[auth-scopes]: https://developers.google.com/identity/protocols/oauth2/scopes
[predefined-iam-roles]: https://cloud.google.com/iam/docs/understanding-roles#predefined_roles
diff --git a/google-cloud-bigtable-bom/pom.xml b/google-cloud-bigtable-bom/pom.xml
index fe5ae44bf1..e241a11534 100644
--- a/google-cloud-bigtable-bom/pom.xml
+++ b/google-cloud-bigtable-bom/pom.xml
@@ -3,7 +3,7 @@
4.0.0
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
com.google.cloud
@@ -63,37 +63,37 @@
com.google.cloud
google-cloud-bigtable
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.cloud
google-cloud-bigtable-emulator
- 0.185.1-SNAPSHOT
+ 0.186.0
com.google.cloud
google-cloud-bigtable-emulator-core
- 0.185.1-SNAPSHOT
+ 0.186.0
com.google.api.grpc
grpc-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
grpc-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
proto-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
proto-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
diff --git a/google-cloud-bigtable-deps-bom/pom.xml b/google-cloud-bigtable-deps-bom/pom.xml
index 90aaf3d691..8e59114a52 100644
--- a/google-cloud-bigtable-deps-bom/pom.xml
+++ b/google-cloud-bigtable-deps-bom/pom.xml
@@ -13,7 +13,7 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
diff --git a/google-cloud-bigtable-emulator-core/pom.xml b/google-cloud-bigtable-emulator-core/pom.xml
index 25b50d954e..e320a64d24 100644
--- a/google-cloud-bigtable-emulator-core/pom.xml
+++ b/google-cloud-bigtable-emulator-core/pom.xml
@@ -7,11 +7,11 @@
google-cloud-bigtable-parent
com.google.cloud
- 2.48.1-SNAPSHOT
+ 2.49.0
google-cloud-bigtable-emulator-core
- 0.185.1-SNAPSHOT
+ 0.186.0
A Java wrapper for the Cloud Bigtable emulator.
diff --git a/google-cloud-bigtable-emulator/pom.xml b/google-cloud-bigtable-emulator/pom.xml
index 2af777c013..ec853bf2a9 100644
--- a/google-cloud-bigtable-emulator/pom.xml
+++ b/google-cloud-bigtable-emulator/pom.xml
@@ -5,7 +5,7 @@
4.0.0
google-cloud-bigtable-emulator
- 0.185.1-SNAPSHOT
+ 0.186.0
Google Cloud Java - Bigtable Emulator
https://github.com/googleapis/java-bigtable
@@ -14,7 +14,7 @@
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
scm:git:git@github.com:googleapis/java-bigtable.git
@@ -81,14 +81,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
@@ -99,7 +99,7 @@
com.google.cloud
google-cloud-bigtable-emulator-core
- 0.185.1-SNAPSHOT
+ 0.186.0
diff --git a/google-cloud-bigtable/pom.xml b/google-cloud-bigtable/pom.xml
index 7d027c995c..b4be0a9ef5 100644
--- a/google-cloud-bigtable/pom.xml
+++ b/google-cloud-bigtable/pom.xml
@@ -2,7 +2,7 @@
4.0.0
google-cloud-bigtable
- 2.48.1-SNAPSHOT
+ 2.49.0
jar
Google Cloud Bigtable
https://github.com/googleapis/java-bigtable
@@ -12,11 +12,11 @@
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
- 2.48.1-SNAPSHOT
+ 2.49.0
google-cloud-bigtable
@@ -52,14 +52,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
@@ -709,7 +709,6 @@
grpc-auth is not directly used transitively, but is pulled to align with other grpc parts
opencensus-impl-core is brought in transitively through opencensus-impl
-->
- io.grpc:grpc-auth
io.opencensus:opencensus-impl-core
diff --git a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/Version.java b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/Version.java
index ff7568bbd6..21bdfd5e09 100644
--- a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/Version.java
+++ b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/Version.java
@@ -20,6 +20,6 @@
@InternalApi("For internal use only")
public final class Version {
// {x-version-update-start:google-cloud-bigtable:current}
- public static String VERSION = "2.48.1-SNAPSHOT";
+ public static String VERSION = "2.49.0";
// {x-version-update-end}
}
diff --git a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimer.java b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimer.java
index ecbef85be5..7495ca6ceb 100644
--- a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimer.java
+++ b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimer.java
@@ -16,18 +16,27 @@
package com.google.cloud.bigtable.data.v2.stub;
import com.google.api.core.BetaApi;
-import com.google.api.gax.core.FixedCredentialsProvider;
-import com.google.api.gax.core.InstantiatingExecutorProvider;
+import com.google.api.core.SettableApiFuture;
import com.google.api.gax.grpc.ChannelPrimer;
-import com.google.api.gax.grpc.GrpcTransportChannel;
-import com.google.api.gax.rpc.FixedTransportChannelProvider;
import com.google.auth.Credentials;
+import com.google.bigtable.v2.BigtableGrpc;
+import com.google.bigtable.v2.InstanceName;
import com.google.bigtable.v2.PingAndWarmRequest;
-import com.google.cloud.bigtable.data.v2.internal.NameUtil;
-import com.google.common.base.Preconditions;
+import com.google.bigtable.v2.PingAndWarmResponse;
+import io.grpc.CallCredentials;
+import io.grpc.CallOptions;
+import io.grpc.ClientCall;
+import io.grpc.Deadline;
import io.grpc.ManagedChannel;
+import io.grpc.Metadata;
+import io.grpc.Status;
+import io.grpc.auth.MoreCallCredentials;
import java.io.IOException;
-import java.util.concurrent.ExecutionException;
+import java.io.UnsupportedEncodingException;
+import java.net.URLEncoder;
+import java.util.Map;
+import java.util.concurrent.TimeUnit;
+import java.util.logging.Level;
import java.util.logging.Logger;
/**
@@ -41,27 +50,40 @@
class BigtableChannelPrimer implements ChannelPrimer {
private static Logger LOG = Logger.getLogger(BigtableChannelPrimer.class.toString());
- private final EnhancedBigtableStubSettings settingsTemplate;
+ static final Metadata.Key REQUEST_PARAMS =
+ Metadata.Key.of("x-goog-request-params", Metadata.ASCII_STRING_MARSHALLER);
+ private final PingAndWarmRequest request;
+ private final CallCredentials callCredentials;
+ private final Map headers;
static BigtableChannelPrimer create(
- Credentials credentials, String projectId, String instanceId, String appProfileId) {
- EnhancedBigtableStubSettings.Builder builder =
- EnhancedBigtableStubSettings.newBuilder()
- .setProjectId(projectId)
- .setInstanceId(instanceId)
- .setAppProfileId(appProfileId)
- .setCredentialsProvider(FixedCredentialsProvider.create(credentials))
- // Disable refreshing channel here to avoid creating settings in a loop
- .setRefreshingChannel(false)
- .setExecutorProvider(
- InstantiatingExecutorProvider.newBuilder().setExecutorThreadCount(1).build());
-
- return new BigtableChannelPrimer(builder.build());
+ String projectId,
+ String instanceId,
+ String appProfileId,
+ Credentials credentials,
+ Map headers) {
+ return new BigtableChannelPrimer(projectId, instanceId, appProfileId, credentials, headers);
}
- private BigtableChannelPrimer(EnhancedBigtableStubSettings settingsTemplate) {
- Preconditions.checkNotNull(settingsTemplate, "settingsTemplate can't be null");
- this.settingsTemplate = settingsTemplate;
+ BigtableChannelPrimer(
+ String projectId,
+ String instanceId,
+ String appProfileId,
+ Credentials credentials,
+ Map headers) {
+ if (credentials != null) {
+ callCredentials = MoreCallCredentials.from(credentials);
+ } else {
+ callCredentials = null;
+ }
+
+ request =
+ PingAndWarmRequest.newBuilder()
+ .setName(InstanceName.format(projectId, instanceId))
+ .setAppProfileId(appProfileId)
+ .build();
+
+ this.headers = headers;
}
@Override
@@ -69,8 +91,7 @@ public void primeChannel(ManagedChannel managedChannel) {
try {
primeChannelUnsafe(managedChannel);
} catch (IOException | RuntimeException e) {
- LOG.warning(
- String.format("Unexpected error while trying to prime a channel: %s", e.getMessage()));
+ LOG.log(Level.WARNING, "Unexpected error while trying to prime a channel", e);
}
}
@@ -78,35 +99,64 @@ private void primeChannelUnsafe(ManagedChannel managedChannel) throws IOExceptio
sendPrimeRequests(managedChannel);
}
- private void sendPrimeRequests(ManagedChannel managedChannel) throws IOException {
- // Wrap the channel in a temporary stub
- EnhancedBigtableStubSettings primingSettings =
- settingsTemplate
- .toBuilder()
- .setTransportChannelProvider(
- FixedTransportChannelProvider.create(GrpcTransportChannel.create(managedChannel)))
- .build();
+ private void sendPrimeRequests(ManagedChannel managedChannel) {
+ try {
+ ClientCall clientCall =
+ managedChannel.newCall(
+ BigtableGrpc.getPingAndWarmMethod(),
+ CallOptions.DEFAULT
+ .withCallCredentials(callCredentials)
+ .withDeadline(Deadline.after(1, TimeUnit.MINUTES)));
- try (EnhancedBigtableStub stub = EnhancedBigtableStub.create(primingSettings)) {
- PingAndWarmRequest request =
- PingAndWarmRequest.newBuilder()
- .setName(
- NameUtil.formatInstanceName(
- primingSettings.getProjectId(), primingSettings.getInstanceId()))
- .setAppProfileId(primingSettings.getAppProfileId())
- .build();
-
- try {
- stub.pingAndWarmCallable().call(request);
- } catch (Throwable e) {
- // TODO: Not sure if we should swallow the error here. We are pre-emptively swapping
- // channels if the new
- // channel is bad.
- if (e instanceof ExecutionException) {
- e = e.getCause();
- }
- LOG.warning(String.format("Failed to prime channel: %s", e));
- }
+ SettableApiFuture future = SettableApiFuture.create();
+ clientCall.start(
+ new ClientCall.Listener() {
+ PingAndWarmResponse response;
+
+ @Override
+ public void onMessage(PingAndWarmResponse message) {
+ response = message;
+ }
+
+ @Override
+ public void onClose(Status status, Metadata trailers) {
+ if (status.isOk()) {
+ future.set(response);
+ } else {
+ future.setException(status.asException());
+ }
+ }
+ },
+ createMetadata(headers, request));
+ clientCall.sendMessage(request);
+ clientCall.halfClose();
+ clientCall.request(Integer.MAX_VALUE);
+
+ future.get(1, TimeUnit.MINUTES);
+ } catch (Throwable e) {
+ // TODO: Not sure if we should swallow the error here. We are pre-emptively swapping
+ // channels if the new
+ // channel is bad.
+ LOG.log(Level.WARNING, "Failed to prime channel", e);
}
}
+
+ private static Metadata createMetadata(Map headers, PingAndWarmRequest request) {
+ Metadata metadata = new Metadata();
+
+ headers.forEach(
+ (k, v) -> metadata.put(Metadata.Key.of(k, Metadata.ASCII_STRING_MARSHALLER), v));
+ try {
+ metadata.put(
+ REQUEST_PARAMS,
+ String.format(
+ "name=%s&app_profile_id=%s",
+ URLEncoder.encode(request.getName(), "UTF-8"),
+ URLEncoder.encode(request.getAppProfileId(), "UTF-8")));
+ } catch (UnsupportedEncodingException e) {
+ LOG.log(Level.WARNING, "Failed to encode request params", e);
+ }
+
+ return metadata;
+ }
}
diff --git a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableClientContext.java b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableClientContext.java
index a8e18f364e..a2587b0dd9 100644
--- a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableClientContext.java
+++ b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/BigtableClientContext.java
@@ -100,10 +100,11 @@ public static BigtableClientContext create(EnhancedBigtableStubSettings settings
if (builder.isRefreshingChannel()) {
transportProvider.setChannelPrimer(
BigtableChannelPrimer.create(
+ builder.getProjectId(),
+ builder.getInstanceId(),
+ builder.getAppProfileId(),
credentials,
- settings.getProjectId(),
- settings.getInstanceId(),
- settings.getAppProfileId()));
+ builder.getHeaderProvider().getHeaders()));
}
builder.setTransportChannelProvider(transportProvider.build());
diff --git a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStub.java b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStub.java
index 5cab91c92c..46377fbc41 100644
--- a/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStub.java
+++ b/google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStub.java
@@ -61,8 +61,6 @@
import com.google.bigtable.v2.GenerateInitialChangeStreamPartitionsResponse;
import com.google.bigtable.v2.MutateRowsRequest;
import com.google.bigtable.v2.MutateRowsResponse;
-import com.google.bigtable.v2.PingAndWarmRequest;
-import com.google.bigtable.v2.PingAndWarmResponse;
import com.google.bigtable.v2.ReadChangeStreamRequest;
import com.google.bigtable.v2.ReadChangeStreamResponse;
import com.google.bigtable.v2.ReadRowsRequest;
@@ -188,7 +186,6 @@ public class EnhancedBigtableStub implements AutoCloseable {
private final UnaryCallable externalBulkMutateRowsCallable;
private final UnaryCallable checkAndMutateRowCallable;
private final UnaryCallable readModifyWriteRowCallable;
- private final UnaryCallable pingAndWarmCallable;
private final ServerStreamingCallable
generateInitialChangeStreamPartitionsCallable;
@@ -321,7 +318,6 @@ public EnhancedBigtableStub(
createGenerateInitialChangeStreamPartitionsCallable();
readChangeStreamCallable =
createReadChangeStreamCallable(new DefaultChangeStreamRecordAdapter());
- pingAndWarmCallable = createPingAndWarmCallable();
executeQueryCallable = createExecuteQueryCallable();
}
@@ -1252,28 +1248,6 @@ ServerStreamingCallSettings convertUnaryToServerStreamingSettings(
.build();
}
- private UnaryCallable createPingAndWarmCallable() {
- UnaryCallable pingAndWarm =
- GrpcRawCallableFactory.createUnaryCallable(
- GrpcCallSettings.newBuilder()
- .setMethodDescriptor(BigtableGrpc.getPingAndWarmMethod())
- .setParamsExtractor(
- new RequestParamsExtractor() {
- @Override
- public Map extract(PingAndWarmRequest request) {
- return ImmutableMap.of(
- "name", request.getName(),
- "app_profile_id", request.getAppProfileId());
- }
- })
- .build(),
- Collections.emptySet());
- return pingAndWarm.withDefaultCallContext(
- clientContext
- .getDefaultCallContext()
- .withRetrySettings(settings.pingAndWarmSettings().getRetrySettings()));
- }
-
private UnaryCallable withRetries(
UnaryCallable innerCallable, UnaryCallSettings, ?> unaryCallSettings) {
UnaryCallable retrying;
@@ -1381,10 +1355,6 @@ public ExecuteQueryCallable executeQueryCallable() {
return executeQueryCallable;
}
- UnaryCallable pingAndWarmCallable() {
- return pingAndWarmCallable;
- }
-
//
private SpanName getSpanName(String methodName) {
diff --git a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/it/BuiltinMetricsIT.java b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/it/BuiltinMetricsIT.java
index 2438d7e9c6..d929627e12 100644
--- a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/it/BuiltinMetricsIT.java
+++ b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/it/BuiltinMetricsIT.java
@@ -70,6 +70,7 @@
import org.junit.After;
import org.junit.Before;
import org.junit.ClassRule;
+import org.junit.Ignore;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.Timeout;
@@ -78,6 +79,7 @@
import org.threeten.bp.Duration;
import org.threeten.bp.Instant;
+@Ignore("Temporarily disable flaky test")
@RunWith(JUnit4.class)
public class BuiltinMetricsIT {
@ClassRule public static TestEnvRule testEnvRule = new TestEnvRule();
diff --git a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimerTest.java b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimerTest.java
index e1f22bebbd..709b482477 100644
--- a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimerTest.java
+++ b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/BigtableChannelPrimerTest.java
@@ -24,6 +24,7 @@
import com.google.bigtable.v2.PingAndWarmRequest;
import com.google.bigtable.v2.PingAndWarmResponse;
import com.google.cloud.bigtable.data.v2.FakeServiceBuilder;
+import com.google.common.collect.ImmutableMap;
import io.grpc.ManagedChannel;
import io.grpc.ManagedChannelBuilder;
import io.grpc.Metadata;
@@ -69,10 +70,11 @@ public void setup() throws IOException {
primer =
BigtableChannelPrimer.create(
- OAuth2Credentials.create(new AccessToken(TOKEN_VALUE, null)),
"fake-project",
"fake-instance",
- "fake-app-profile");
+ "fake-app-profile",
+ OAuth2Credentials.create(new AccessToken(TOKEN_VALUE, null)),
+ ImmutableMap.of("bigtable-feature", "fake-feature"));
channel =
ManagedChannelBuilder.forAddress("localhost", server.getPort()).usePlaintext().build();
@@ -133,7 +135,7 @@ public PingAndWarmResponse apply(PingAndWarmRequest pingAndWarmRequest) {
assertThat(logHandler.logs).hasSize(1);
for (LogRecord log : logHandler.logs) {
- assertThat(log.getMessage()).contains("FAILED_PRECONDITION");
+ assertThat(log.getThrown().getMessage()).contains("FAILED_PRECONDITION");
}
}
@@ -146,7 +148,21 @@ public void testChannelErrorsAreLogged() {
assertThat(logHandler.logs).hasSize(1);
for (LogRecord log : logHandler.logs) {
- assertThat(log.getMessage()).contains("UnsupportedOperationException");
+ assertThat(log.getThrown()).isInstanceOf(UnsupportedOperationException.class);
+ }
+ }
+
+ @Test
+ public void testHeadersAreSent() {
+ primer.primeChannel(channel);
+
+ for (Metadata metadata : metadataInterceptor.metadataList) {
+ assertThat(metadata.get(BigtableChannelPrimer.REQUEST_PARAMS))
+ .isEqualTo(
+ "name=projects%2Ffake-project%2Finstances%2Ffake-instance&app_profile_id=fake-app-profile");
+ assertThat(
+ metadata.get(Metadata.Key.of("bigtable-feature", Metadata.ASCII_STRING_MARSHALLER)))
+ .isEqualTo("fake-feature");
}
}
diff --git a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStubTest.java b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStubTest.java
index 67ac3f24d9..fcdb4a0624 100644
--- a/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStubTest.java
+++ b/google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/EnhancedBigtableStubTest.java
@@ -84,8 +84,10 @@
import com.google.cloud.bigtable.data.v2.models.TableId;
import com.google.cloud.bigtable.data.v2.models.sql.ResultSetMetadata;
import com.google.cloud.bigtable.data.v2.models.sql.Statement;
+import com.google.cloud.bigtable.data.v2.stub.metrics.NoopMetricsProvider;
import com.google.cloud.bigtable.data.v2.stub.sql.ExecuteQueryCallable;
import com.google.cloud.bigtable.data.v2.stub.sql.SqlServerStream;
+import com.google.common.base.Preconditions;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Queues;
import com.google.common.io.BaseEncoding;
@@ -97,7 +99,6 @@
import io.grpc.CallOptions;
import io.grpc.Context;
import io.grpc.Deadline;
-import io.grpc.ManagedChannel;
import io.grpc.ManagedChannelBuilder;
import io.grpc.Metadata;
import io.grpc.Metadata.Key;
@@ -172,6 +173,7 @@ public void setUp() throws IOException, IllegalAccessException, InstantiationExc
.setInstanceId(INSTANCE_ID)
.setAppProfileId(APP_PROFILE_ID)
.setCredentialsProvider(NoCredentialsProvider.create())
+ .setMetricsProvider(NoopMetricsProvider.INSTANCE)
.build()
.getStubSettings();
@@ -187,9 +189,6 @@ public void tearDown() {
@Test
public void testJwtAudience()
throws InterruptedException, IOException, NoSuchAlgorithmException, ExecutionException {
- // close default stub - need to create custom one
- enhancedBigtableStub.close();
-
// Create fake jwt creds
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
KeyPair keyPair = keyGen.genKeyPair();
@@ -210,9 +209,10 @@ public void testJwtAudience()
.setJwtAudienceMapping(ImmutableMap.of("localhost", expectedAudience))
.setCredentialsProvider(FixedCredentialsProvider.create(jwtCreds))
.build();
- enhancedBigtableStub = EnhancedBigtableStub.create(settings);
+ try (EnhancedBigtableStub stub = EnhancedBigtableStub.create(settings)) {
+ stub.readRowCallable().futureCall(Query.create("fake-table")).get();
+ }
// Send rpc and grab the credentials sent
- enhancedBigtableStub.readRowCallable().futureCall(Query.create("fake-table")).get();
Metadata metadata = metadataInterceptor.headers.take();
String authValue = metadata.get(Key.of("Authorization", Metadata.ASCII_STRING_MARSHALLER));
@@ -226,9 +226,6 @@ public void testJwtAudience()
@Test
public void testBatchJwtAudience()
throws InterruptedException, IOException, NoSuchAlgorithmException, ExecutionException {
- // close default stub - need to create custom one
- enhancedBigtableStub.close();
-
// Create fake jwt creds
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
KeyPair keyPair = keyGen.genKeyPair();
@@ -241,31 +238,30 @@ public void testBatchJwtAudience()
.setPrivateKeyId("fake-private-key")
.build();
- // Create a fixed channel that will ignore the default endpoint and connect to the emulator
- ManagedChannel emulatorChannel =
- ManagedChannelBuilder.forAddress("localhost", server.getPort()).usePlaintext().build();
+ EnhancedBigtableStubSettings settings =
+ EnhancedBigtableStubSettings.newBuilder()
+ .setProjectId("fake-project")
+ .setInstanceId("fake-instance")
+ .setEndpoint("batch-bigtable.googleapis.com:443")
+ .setCredentialsProvider(FixedCredentialsProvider.create(jwtCreds))
+ .setMetricsProvider(NoopMetricsProvider.INSTANCE)
+ // Use a fixed channel that will ignore the default endpoint and connect to the emulator
+ .setTransportChannelProvider(
+ FixedTransportChannelProvider.create(
+ GrpcTransportChannel.create(
+ ManagedChannelBuilder.forAddress("localhost", server.getPort())
+ .usePlaintext()
+ .build())))
+ // Channel refreshing doesn't work with FixedTransportChannelProvider. Disable it for
+ // the test
+ .setRefreshingChannel(false)
+ .build();
Metadata metadata;
- try {
- EnhancedBigtableStubSettings settings =
- EnhancedBigtableStubSettings.newBuilder()
- .setProjectId("fake-project")
- .setInstanceId("fake-instance")
- .setEndpoint("batch-bigtable.googleapis.com:443")
- .setCredentialsProvider(FixedCredentialsProvider.create(jwtCreds))
- .setTransportChannelProvider(
- FixedTransportChannelProvider.create(
- GrpcTransportChannel.create(emulatorChannel)))
- // Channel refreshing doesn't work with FixedTransportChannelProvider. Disable it for
- // the test
- .setRefreshingChannel(false)
- .build();
- enhancedBigtableStub = EnhancedBigtableStub.create(settings);
+ try (EnhancedBigtableStub stub = EnhancedBigtableStub.create(settings)) {
// Send rpc and grab the credentials sent
- enhancedBigtableStub.readRowCallable().futureCall(Query.create("fake-table")).get();
+ stub.readRowCallable().futureCall(Query.create("fake-table")).get();
metadata = metadataInterceptor.headers.take();
- } finally {
- emulatorChannel.shutdown();
}
String authValue = metadata.get(Key.of("Authorization", Metadata.ASCII_STRING_MARSHALLER));
@@ -278,7 +274,6 @@ public void testBatchJwtAudience()
@Test
public void testFeatureFlags() throws InterruptedException, IOException, ExecutionException {
-
enhancedBigtableStub.readRowCallable().futureCall(Query.create("fake-table")).get();
Metadata metadata = metadataInterceptor.headers.take();
@@ -291,6 +286,28 @@ public void testFeatureFlags() throws InterruptedException, IOException, Executi
assertThat(featureFlags.getLastScannedRowResponses()).isTrue();
}
+ @Test
+ public void testPingAndWarmFeatureFlags()
+ throws InterruptedException, IOException, ExecutionException {
+ EnhancedBigtableStubSettings settings =
+ defaultSettings.toBuilder().setRefreshingChannel(true).build();
+ try (EnhancedBigtableStub ignored = EnhancedBigtableStub.create(settings)) {
+ Preconditions.checkState(
+ !fakeDataService.pingRequests.isEmpty(), "Ping request was not sent during setup");
+ Metadata metadata = metadataInterceptor.headers.take();
+
+ String encodedFeatureFlags =
+ metadata.get(Key.of("bigtable-features", Metadata.ASCII_STRING_MARSHALLER));
+ FeatureFlags featureFlags =
+ FeatureFlags.parseFrom(BaseEncoding.base64Url().decode(encodedFeatureFlags));
+
+ assertThat(featureFlags.getReverseScans()).isTrue();
+ assertThat(featureFlags.getLastScannedRowResponses()).isTrue();
+ assertThat(featureFlags.getRoutingCookie()).isTrue();
+ assertThat(featureFlags.getRetryInfo()).isTrue();
+ }
+ }
+
@Test
public void testCheckAndMutateRequestResponseConversion()
throws ExecutionException, InterruptedException {
diff --git a/grpc-google-cloud-bigtable-admin-v2/pom.xml b/grpc-google-cloud-bigtable-admin-v2/pom.xml
index dbe05980c8..94231ba7fa 100644
--- a/grpc-google-cloud-bigtable-admin-v2/pom.xml
+++ b/grpc-google-cloud-bigtable-admin-v2/pom.xml
@@ -4,13 +4,13 @@
4.0.0
com.google.api.grpc
grpc-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
grpc-google-cloud-bigtable-admin-v2
GRPC library for grpc-google-cloud-bigtable-admin-v2
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
@@ -18,14 +18,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
diff --git a/grpc-google-cloud-bigtable-v2/pom.xml b/grpc-google-cloud-bigtable-v2/pom.xml
index 0fdb146424..b09f14695d 100644
--- a/grpc-google-cloud-bigtable-v2/pom.xml
+++ b/grpc-google-cloud-bigtable-v2/pom.xml
@@ -4,13 +4,13 @@
4.0.0
com.google.api.grpc
grpc-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
grpc-google-cloud-bigtable-v2
GRPC library for grpc-google-cloud-bigtable-v2
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
@@ -18,14 +18,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
diff --git a/pom.xml b/pom.xml
index 74b75c2576..0a945a3853 100644
--- a/pom.xml
+++ b/pom.xml
@@ -4,7 +4,7 @@
google-cloud-bigtable-parent
pom
- 2.48.1-SNAPSHOT
+ 2.49.0
Google Cloud Bigtable Parent
https://github.com/googleapis/java-bigtable
@@ -153,27 +153,27 @@
com.google.api.grpc
proto-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
proto-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
grpc-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.api.grpc
grpc-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
com.google.cloud
google-cloud-bigtable
- 2.48.1-SNAPSHOT
+ 2.49.0
diff --git a/proto-google-cloud-bigtable-admin-v2/pom.xml b/proto-google-cloud-bigtable-admin-v2/pom.xml
index ca3f645d65..48f59de7e1 100644
--- a/proto-google-cloud-bigtable-admin-v2/pom.xml
+++ b/proto-google-cloud-bigtable-admin-v2/pom.xml
@@ -4,13 +4,13 @@
4.0.0
com.google.api.grpc
proto-google-cloud-bigtable-admin-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
proto-google-cloud-bigtable-admin-v2
PROTO library for proto-google-cloud-bigtable-admin-v2
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
@@ -18,14 +18,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
diff --git a/proto-google-cloud-bigtable-v2/pom.xml b/proto-google-cloud-bigtable-v2/pom.xml
index 437d9ca5b2..9b61631b52 100644
--- a/proto-google-cloud-bigtable-v2/pom.xml
+++ b/proto-google-cloud-bigtable-v2/pom.xml
@@ -4,13 +4,13 @@
4.0.0
com.google.api.grpc
proto-google-cloud-bigtable-v2
- 2.48.1-SNAPSHOT
+ 2.49.0
proto-google-cloud-bigtable-v2
PROTO library for proto-google-cloud-bigtable-v2
com.google.cloud
google-cloud-bigtable-parent
- 2.48.1-SNAPSHOT
+ 2.49.0
@@ -18,14 +18,14 @@
com.google.cloud
google-cloud-bigtable-deps-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
com.google.cloud
google-cloud-bigtable-bom
- 2.48.1-SNAPSHOT
+ 2.49.0
pom
import
diff --git a/samples/snapshot/pom.xml b/samples/snapshot/pom.xml
index d80ffd9c8a..30a503385d 100644
--- a/samples/snapshot/pom.xml
+++ b/samples/snapshot/pom.xml
@@ -28,7 +28,7 @@
com.google.cloud
google-cloud-bigtable
- 2.48.1-SNAPSHOT
+ 2.49.0
diff --git a/test-proxy/pom.xml b/test-proxy/pom.xml
index 10506e2020..1bd83d098a 100644
--- a/test-proxy/pom.xml
+++ b/test-proxy/pom.xml
@@ -12,11 +12,11 @@
google-cloud-bigtable-parent
com.google.cloud
- 2.48.1-SNAPSHOT
+ 2.49.0
- 2.48.1-SNAPSHOT
+ 2.49.0
diff --git a/versions.txt b/versions.txt
index 85e102bdd3..021d20cb62 100644
--- a/versions.txt
+++ b/versions.txt
@@ -1,10 +1,10 @@
# Format:
# module:released-version:current-version
-google-cloud-bigtable:2.48.0:2.48.1-SNAPSHOT
-grpc-google-cloud-bigtable-admin-v2:2.48.0:2.48.1-SNAPSHOT
-grpc-google-cloud-bigtable-v2:2.48.0:2.48.1-SNAPSHOT
-proto-google-cloud-bigtable-admin-v2:2.48.0:2.48.1-SNAPSHOT
-proto-google-cloud-bigtable-v2:2.48.0:2.48.1-SNAPSHOT
-google-cloud-bigtable-emulator:0.185.0:0.185.1-SNAPSHOT
-google-cloud-bigtable-emulator-core:0.185.0:0.185.1-SNAPSHOT
+google-cloud-bigtable:2.49.0:2.49.0
+grpc-google-cloud-bigtable-admin-v2:2.49.0:2.49.0
+grpc-google-cloud-bigtable-v2:2.49.0:2.49.0
+proto-google-cloud-bigtable-admin-v2:2.49.0:2.49.0
+proto-google-cloud-bigtable-v2:2.49.0:2.49.0
+google-cloud-bigtable-emulator:0.186.0:0.186.0
+google-cloud-bigtable-emulator-core:0.186.0:0.186.0