Skip to content

Commit c4b8c03

Browse files
authored
fix: The metadata could be returned in trailer or header depends on i… (#1337)
* fix: The metadata could be returned in trailer or header depends on if sidecar is enabled. Check both for now. * fix * fix npe * fix NPE when metadata is null
1 parent 98b3349 commit c4b8c03

File tree

4 files changed

+75
-25
lines changed

4 files changed

+75
-25
lines changed

google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/metrics/BigtableTracerStreamingCallable.java

Lines changed: 36 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -104,11 +104,24 @@ public void onError(Throwable t) {
104104
Long latency = Util.getGfeLatency(metadata);
105105
tracer.recordGfeMetadata(latency, t);
106106
try {
107-
byte[] trailers =
108-
metadata.get(Metadata.Key.of(Util.RESPONSE_PRAMS_KEY, Metadata.BINARY_BYTE_MARSHALLER));
109-
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
110-
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
111-
} catch (NullPointerException | InvalidProtocolBufferException e) {
107+
// Check both headers and trailers because in different environments the metadata
108+
// could be returned in headers or trailers
109+
if (metadata != null) {
110+
byte[] trailers = metadata.get(Util.METADATA_KEY);
111+
if (trailers == null) {
112+
Metadata trailingMetadata = responseMetadata.getTrailingMetadata();
113+
if (trailingMetadata != null) {
114+
trailers = trailingMetadata.get(Util.METADATA_KEY);
115+
}
116+
}
117+
// If the response is terminated abnormally and we didn't get location information in
118+
// trailers or headers, skip setting the locations
119+
if (trailers != null) {
120+
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
121+
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
122+
}
123+
}
124+
} catch (InvalidProtocolBufferException e) {
112125
}
113126

114127
outerObserver.onError(t);
@@ -120,11 +133,24 @@ public void onComplete() {
120133
Long latency = Util.getGfeLatency(metadata);
121134
tracer.recordGfeMetadata(latency, null);
122135
try {
123-
byte[] trailers =
124-
metadata.get(Metadata.Key.of(Util.RESPONSE_PRAMS_KEY, Metadata.BINARY_BYTE_MARSHALLER));
125-
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
126-
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
127-
} catch (NullPointerException | InvalidProtocolBufferException e) {
136+
// Check both headers and trailers because in different environments the metadata
137+
// could be returned in headers or trailers
138+
if (metadata != null) {
139+
byte[] trailers = metadata.get(Util.METADATA_KEY);
140+
if (trailers == null) {
141+
Metadata trailingMetadata = responseMetadata.getTrailingMetadata();
142+
if (trailingMetadata != null) {
143+
trailers = trailingMetadata.get(Util.METADATA_KEY);
144+
}
145+
}
146+
// If the response is terminated abnormally and we didn't get location information in
147+
// trailers or headers, skip setting the locations
148+
if (trailers != null) {
149+
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
150+
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
151+
}
152+
}
153+
} catch (InvalidProtocolBufferException e) {
128154
}
129155

130156
outerObserver.onComplete();

google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/metrics/BigtableTracerUnaryCallable.java

Lines changed: 36 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -83,11 +83,24 @@ public void onFailure(Throwable throwable) {
8383
Long latency = Util.getGfeLatency(metadata);
8484
tracer.recordGfeMetadata(latency, throwable);
8585
try {
86-
byte[] trailers =
87-
metadata.get(Metadata.Key.of(Util.RESPONSE_PRAMS_KEY, Metadata.BINARY_BYTE_MARSHALLER));
88-
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
89-
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
90-
} catch (NullPointerException | InvalidProtocolBufferException e) {
86+
// Check both headers and trailers because in different environments the metadata
87+
// could be returned in headers or trailers
88+
if (metadata != null) {
89+
byte[] trailers = metadata.get(Util.METADATA_KEY);
90+
if (trailers == null) {
91+
Metadata trailingMetadata = responseMetadata.getTrailingMetadata();
92+
if (trailingMetadata != null) {
93+
trailers = trailingMetadata.get(Util.METADATA_KEY);
94+
}
95+
}
96+
// If the response is terminated abnormally and we didn't get location information in
97+
// trailers or headers, skip setting the locations
98+
if (trailers != null) {
99+
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
100+
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
101+
}
102+
}
103+
} catch (InvalidProtocolBufferException e) {
91104
}
92105
}
93106

@@ -97,11 +110,24 @@ public void onSuccess(ResponseT response) {
97110
Long latency = Util.getGfeLatency(metadata);
98111
tracer.recordGfeMetadata(latency, null);
99112
try {
100-
byte[] trailers =
101-
metadata.get(Metadata.Key.of(Util.RESPONSE_PRAMS_KEY, Metadata.BINARY_BYTE_MARSHALLER));
102-
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
103-
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
104-
} catch (NullPointerException | InvalidProtocolBufferException e) {
113+
// Check both headers and trailers because in different environments the metadata
114+
// could be returned in headers or trailers
115+
if (metadata != null) {
116+
byte[] trailers = metadata.get(Util.METADATA_KEY);
117+
if (trailers == null) {
118+
Metadata trailingMetadata = responseMetadata.getTrailingMetadata();
119+
if (trailingMetadata != null) {
120+
trailers = trailingMetadata.get(Util.METADATA_KEY);
121+
}
122+
}
123+
// If the response is terminated abnormally and we didn't get location information in
124+
// trailers or headers, skip setting the locations
125+
if (trailers != null) {
126+
ResponseParams decodedTrailers = ResponseParams.parseFrom(trailers);
127+
tracer.setLocations(decodedTrailers.getZoneId(), decodedTrailers.getClusterId());
128+
}
129+
}
130+
} catch (InvalidProtocolBufferException e) {
105131
}
106132
}
107133
}

google-cloud-bigtable/src/main/java/com/google/cloud/bigtable/data/v2/stub/metrics/Util.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -57,8 +57,8 @@ public class Util {
5757
private static final Metadata.Key<String> SERVER_TIMING_HEADER_KEY =
5858
Metadata.Key.of("server-timing", Metadata.ASCII_STRING_MARSHALLER);
5959
private static final Pattern SERVER_TIMING_HEADER_PATTERN = Pattern.compile(".*dur=(?<dur>\\d+)");
60-
61-
static final String RESPONSE_PRAMS_KEY = "x-goog-ext-425905942-bin";
60+
static final Metadata.Key<byte[]> METADATA_KEY =
61+
Metadata.Key.of("x-goog-ext-425905942-bin", Metadata.BINARY_BYTE_MARSHALLER);
6262

6363
/** Convert an exception into a value that can be used to create an OpenCensus tag value. */
6464
static String extractStatus(@Nullable Throwable error) {

google-cloud-bigtable/src/test/java/com/google/cloud/bigtable/data/v2/stub/metrics/BuiltinMetricsTracerTest.java

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -127,9 +127,7 @@ public void sendHeaders(Metadata headers) {
127127
ResponseParams params =
128128
ResponseParams.newBuilder().setZoneId(ZONE).setClusterId(CLUSTER).build();
129129
byte[] byteArray = params.toByteArray();
130-
headers.put(
131-
Metadata.Key.of(Util.RESPONSE_PRAMS_KEY, Metadata.BINARY_BYTE_MARSHALLER),
132-
byteArray);
130+
headers.put(Util.METADATA_KEY, byteArray);
133131

134132
super.sendHeaders(headers);
135133
}

0 commit comments

Comments
 (0)