Skip to content

Commit 371ba8f

Browse files
feat: bigtable-proxy add gfe debug headers (#9753)
1 parent 89865ff commit 371ba8f

File tree

1 file changed

+59
-7
lines changed
  • bigtable/bigtable-proxy/src/main/java/com/google/cloud/bigtable/examples/proxy/channelpool

1 file changed

+59
-7
lines changed

bigtable/bigtable-proxy/src/main/java/com/google/cloud/bigtable/examples/proxy/channelpool/DataChannel.java

Lines changed: 59 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -35,9 +35,9 @@
3535
import io.grpc.ManagedChannel;
3636
import io.grpc.ManagedChannelBuilder;
3737
import io.grpc.Metadata;
38+
import io.grpc.Metadata.Key;
3839
import io.grpc.MethodDescriptor;
3940
import io.grpc.Status;
40-
import io.grpc.StatusRuntimeException;
4141
import java.time.Duration;
4242
import java.util.List;
4343
import java.util.Optional;
@@ -58,6 +58,11 @@
5858
public class DataChannel extends ManagedChannel {
5959
private static final Logger LOGGER = LoggerFactory.getLogger(DataChannel.class);
6060

61+
private static final Metadata.Key<String> GFE_DEBUG_REQ_HEADER =
62+
Key.of("X-Return-Encrypted-Headers", Metadata.ASCII_STRING_MARSHALLER);
63+
private static final Metadata.Key<String> GFE_DEBUG_RESP_HEADER =
64+
Key.of("X-Encrypted-Debug-Headers", Metadata.ASCII_STRING_MARSHALLER);
65+
6166
private static final Duration WARM_PERIOD = Duration.ofMinutes(3);
6267
private static final Duration MAX_JITTER = Duration.ofSeconds(10);
6368

@@ -152,10 +157,11 @@ private void warm() {
152157
future.get();
153158
successCount++;
154159
} catch (ExecutionException e) {
155-
// All permenant errors are ignored and treated as a success
160+
// All permanent errors are ignored and treated as a success
156161
// The priming request for that generated the error will be dropped
157-
if (e.getCause() instanceof StatusRuntimeException) {
158-
StatusRuntimeException se = (StatusRuntimeException) e.getCause();
162+
if (e.getCause() instanceof PingAndWarmException) {
163+
PingAndWarmException se = (PingAndWarmException) e.getCause();
164+
159165
switch (se.getStatus().getCode()) {
160166
case INTERNAL:
161167
case PERMISSION_DENIED:
@@ -168,8 +174,15 @@ private void warm() {
168174
default:
169175
// noop
170176
}
177+
LOGGER.warn(
178+
"Failed to prime channel with request: {}, status: {}, debug response headers: {}",
179+
request,
180+
se.getStatus(),
181+
Optional.ofNullable(se.getDebugHeaders()).orElse("<missing>"));
182+
} else {
183+
LOGGER.warn("Unexpected failure priming channel with request: {}", request, e.getCause());
171184
}
172-
LOGGER.warn("Failed to prime channel with request: {}", request, e.getCause());
185+
173186
failures++;
174187
} catch (InterruptedException e) {
175188
throw new RuntimeException("Interrupted while priming channel with request: " + request, e);
@@ -182,7 +195,9 @@ private void warm() {
182195

183196
private ListenableFuture<PingAndWarmResponse> sendPingAndWarm(PrimingKey primingKey) {
184197
Metadata metadata = primingKey.composeMetadata();
198+
metadata.put(GFE_DEBUG_REQ_HEADER, "gfe_response_only");
185199
PingAndWarmRequest request = primingKey.composeProto();
200+
request = request.toBuilder().setName(request.getName()).build();
186201

187202
CallLabels callLabels = CallLabels.create(BigtableGrpc.getPingAndWarmMethod(), metadata);
188203
Tracer tracer = new Tracer(metrics, callLabels);
@@ -199,6 +214,8 @@ private ListenableFuture<PingAndWarmResponse> sendPingAndWarm(PrimingKey priming
199214
SettableFuture<PingAndWarmResponse> f = SettableFuture.create();
200215
call.start(
201216
new Listener<>() {
217+
String debugHeaders = null;
218+
202219
@Override
203220
public void onMessage(PingAndWarmResponse response) {
204221
if (!f.set(response)) {
@@ -207,14 +224,22 @@ public void onMessage(PingAndWarmResponse response) {
207224
}
208225
}
209226

227+
@Override
228+
public void onHeaders(Metadata headers) {
229+
debugHeaders = headers.get(GFE_DEBUG_RESP_HEADER);
230+
}
231+
210232
@Override
211233
public void onClose(Status status, Metadata trailers) {
212234
tracer.onCallFinished(status);
213235

214236
if (status.isOk()) {
215-
f.setException(new IllegalStateException("PingAndWarm was missing a response"));
237+
f.setException(
238+
new PingAndWarmException(
239+
"PingAndWarm was missing a response", debugHeaders, trailers, status));
216240
} else {
217-
f.setException(status.asRuntimeException());
241+
f.setException(
242+
new PingAndWarmException("PingAndWarm failed", debugHeaders, trailers, status));
218243
}
219244
}
220245
},
@@ -226,6 +251,33 @@ public void onClose(Status status, Metadata trailers) {
226251
return f;
227252
}
228253

254+
static class PingAndWarmException extends RuntimeException {
255+
256+
private final String debugHeaders;
257+
private final Metadata trailers;
258+
private final Status status;
259+
260+
public PingAndWarmException(
261+
String message, String debugHeaders, Metadata trailers, Status status) {
262+
super(String.format("PingAndWarm failed, status: " + status));
263+
this.debugHeaders = debugHeaders;
264+
this.trailers = trailers;
265+
this.status = status;
266+
}
267+
268+
public String getDebugHeaders() {
269+
return debugHeaders;
270+
}
271+
272+
public Metadata getTrailers() {
273+
return trailers;
274+
}
275+
276+
public Status getStatus() {
277+
return status;
278+
}
279+
}
280+
229281
@Override
230282
public ManagedChannel shutdown() {
231283
final boolean closing;

0 commit comments

Comments
 (0)