3535
3636import com .google .api .client .http .HttpTransport ;
3737import com .google .api .gax .core .NoCredentialsProvider ;
38- import com .google .api .gax .rpc . StatusCode ;
38+ import com .google .api .gax .retrying . RetrySettings ;
3939import com .google .api .gax .rpc .TransportChannelProvider ;
4040import com .google .api .gax .rpc .UnavailableException ;
4141import com .google .api .gax .tracing .GoldenSignalsMetricsTracerFactory ;
4242import com .google .api .gax .tracing .ObservabilityAttributes ;
4343import com .google .common .collect .ImmutableList ;
44- import com .google .rpc .Status ;
4544import com .google .showcase .v1beta1 .EchoClient ;
4645import com .google .showcase .v1beta1 .EchoRequest ;
47- import com .google .showcase .v1beta1 .EchoResponse ;
4846import com .google .showcase .v1beta1 .EchoSettings ;
4947import com .google .showcase .v1beta1 .it .util .TestClientInitializer ;
5048import com .google .showcase .v1beta1 .stub .EchoStubSettings ;
5149import io .grpc .CallOptions ;
5250import io .grpc .Channel ;
5351import io .grpc .ClientCall ;
5452import io .grpc .ClientInterceptor ;
55- import io .grpc .MethodDescriptor ;
5653import io .grpc .Metadata ;
54+ import io .grpc .MethodDescriptor ;
5755import io .opentelemetry .api .common .AttributeKey ;
5856import io .opentelemetry .sdk .OpenTelemetrySdk ;
5957import io .opentelemetry .sdk .metrics .SdkMeterProvider ;
@@ -103,7 +101,8 @@ void testMetrics_successfulEcho_grpc() throws Exception {
103101
104102 // The end of an operation is tracked in a separate thread.
105103 // Add a small sleep to make sure the tracking is completed.
106- // This is implemented by adding a TraceFinisher to ApiFuture as a callback in TracedUnaryCallable,
104+ // This is implemented by adding a TraceFinisher to ApiFuture as a callback in
105+ // TracedUnaryCallable,
107106 // which could be executed in a different thread.
108107 Thread .sleep (100 );
109108 Collection <MetricData > metrics = metricReader .collectAllMetrics ();
@@ -122,22 +121,27 @@ void testMetrics_successfulEcho_grpc() throws Exception {
122121 durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
123122
124123 assertThat (
125- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .SERVER_ADDRESS_ATTRIBUTE )))
124+ attributes .get (
125+ AttributeKey .stringKey (ObservabilityAttributes .SERVER_ADDRESS_ATTRIBUTE )))
126126 .isEqualTo (SHOWCASE_SERVER_ADDRESS );
127127 assertThat (
128128 attributes .get (AttributeKey .longKey (ObservabilityAttributes .SERVER_PORT_ATTRIBUTE )))
129129 .isEqualTo (SHOWCASE_SERVER_PORT );
130130 assertThat (
131- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_SYSTEM_NAME_ATTRIBUTE )))
131+ attributes .get (
132+ AttributeKey .stringKey (ObservabilityAttributes .RPC_SYSTEM_NAME_ATTRIBUTE )))
132133 .isEqualTo ("grpc" );
133134 assertThat (
134- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .GCP_CLIENT_SERVICE_ATTRIBUTE )))
135+ attributes .get (
136+ AttributeKey .stringKey (ObservabilityAttributes .GCP_CLIENT_SERVICE_ATTRIBUTE )))
135137 .isEqualTo ("showcase" );
136138 assertThat (
137- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .GRPC_RPC_METHOD_ATTRIBUTE )))
139+ attributes .get (
140+ AttributeKey .stringKey (ObservabilityAttributes .GRPC_RPC_METHOD_ATTRIBUTE )))
138141 .isEqualTo ("google.showcase.v1beta1.Echo/Echo" );
139142 assertThat (
140- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
143+ attributes .get (
144+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
141145 .isEqualTo ("OK" );
142146 }
143147 }
@@ -201,7 +205,8 @@ public void sendMessage(ReqT message) {}
201205 durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
202206
203207 assertThat (
204- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
208+ attributes .get (
209+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
205210 .isEqualTo ("UNAVAILABLE" );
206211 assertThat (
207212 attributes .get (AttributeKey .stringKey (ObservabilityAttributes .ERROR_TYPE_ATTRIBUTE )))
@@ -236,29 +241,36 @@ void testMetrics_successfulEcho_httpjson() throws Exception {
236241 durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
237242
238243 assertThat (
239- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .SERVER_ADDRESS_ATTRIBUTE )))
244+ attributes .get (
245+ AttributeKey .stringKey (ObservabilityAttributes .SERVER_ADDRESS_ATTRIBUTE )))
240246 .isEqualTo (SHOWCASE_SERVER_ADDRESS );
241247 assertThat (
242248 attributes .get (AttributeKey .longKey (ObservabilityAttributes .SERVER_PORT_ATTRIBUTE )))
243249 .isEqualTo (SHOWCASE_SERVER_PORT );
244250 assertThat (
245- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_SYSTEM_NAME_ATTRIBUTE )))
251+ attributes .get (
252+ AttributeKey .stringKey (ObservabilityAttributes .RPC_SYSTEM_NAME_ATTRIBUTE )))
246253 .isEqualTo ("http" );
247254 assertThat (
248- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .GCP_CLIENT_SERVICE_ATTRIBUTE )))
255+ attributes .get (
256+ AttributeKey .stringKey (ObservabilityAttributes .GCP_CLIENT_SERVICE_ATTRIBUTE )))
249257 .isEqualTo ("showcase" );
250258 assertThat (
251- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
259+ attributes .get (
260+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
252261 .isEqualTo ("OK" );
253262 assertThat (
254- attributes .get (AttributeKey .longKey (ObservabilityAttributes .HTTP_RESPONSE_STATUS_ATTRIBUTE )))
263+ attributes .get (
264+ AttributeKey .longKey (ObservabilityAttributes .HTTP_RESPONSE_STATUS_ATTRIBUTE )))
255265 .isEqualTo (200L );
256266 assertThat (
257- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .URL_TEMPLATE_ATTRIBUTE )))
267+ attributes .get (
268+ AttributeKey .stringKey (ObservabilityAttributes .URL_TEMPLATE_ATTRIBUTE )))
258269 .isEqualTo ("v1beta1/echo:echo" );
259270 assertThat (
260- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .GRPC_RPC_METHOD_ATTRIBUTE )))
261- .isEqualTo ("google.showcase.v1beta1.Echo/Echo" );
271+ attributes .get (
272+ AttributeKey .stringKey (ObservabilityAttributes .GRPC_RPC_METHOD_ATTRIBUTE )))
273+ .isEqualTo ("google.showcase.v1beta1.Echo/Echo" );
262274 }
263275 }
264276
@@ -369,14 +381,106 @@ public String getHeaderValue(int index) {
369381 durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
370382
371383 assertThat (
372- attributes .get (AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
384+ attributes .get (
385+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
373386 .isEqualTo ("UNAVAILABLE" );
374387 assertThat (
375- attributes .get (AttributeKey .longKey (ObservabilityAttributes .HTTP_RESPONSE_STATUS_ATTRIBUTE )))
388+ attributes .get (
389+ AttributeKey .longKey (ObservabilityAttributes .HTTP_RESPONSE_STATUS_ATTRIBUTE )))
376390 .isEqualTo (503L );
377391 assertThat (
378392 attributes .get (AttributeKey .stringKey (ObservabilityAttributes .ERROR_TYPE_ATTRIBUTE )))
379393 .isEqualTo ("503" );
380394 }
381395 }
396+
397+ @ Test
398+ void testMetrics_zeroDeadline_grpc () throws Exception {
399+ GoldenSignalsMetricsTracerFactory tracerFactory =
400+ new GoldenSignalsMetricsTracerFactory (openTelemetrySdk );
401+
402+ // Using 1ms as 0ms might be rejected by some validation or trigger immediate failure before
403+ // metrics
404+ RetrySettings zeroRetrySettings =
405+ RetrySettings .newBuilder ()
406+ .setInitialRpcTimeout (org .threeten .bp .Duration .ofMillis (1 ))
407+ .setMaxRpcTimeout (org .threeten .bp .Duration .ofMillis (1 ))
408+ .setTotalTimeout (org .threeten .bp .Duration .ofMillis (1 ))
409+ .setMaxAttempts (1 )
410+ .build ();
411+
412+ try (EchoClient client =
413+ TestClientInitializer .createGrpcEchoClientOpentelemetryWithRetrySettings (
414+ tracerFactory , zeroRetrySettings )) {
415+
416+ assertThrows (
417+ Exception .class ,
418+ () -> client .echo (EchoRequest .newBuilder ().setContent ("metrics-test" ).build ()));
419+
420+ Thread .sleep (100 );
421+ Collection <MetricData > metrics = metricReader .collectAllMetrics ();
422+ assertThat (metrics ).isNotEmpty ();
423+
424+ MetricData durationMetric =
425+ metrics .stream ()
426+ .filter (m -> m .getName ().equals ("gcp.client.request.duration" ))
427+ .findFirst ()
428+ .orElseThrow (() -> new AssertionError ("Duration metric not found" ));
429+
430+ io .opentelemetry .api .common .Attributes attributes =
431+ durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
432+
433+ assertThat (
434+ attributes .get (
435+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
436+ .isEqualTo ("DEADLINE_EXCEEDED" );
437+ assertThat (
438+ attributes .get (AttributeKey .stringKey (ObservabilityAttributes .ERROR_TYPE_ATTRIBUTE )))
439+ .isEqualTo ("DEADLINE_EXCEEDED" );
440+ }
441+ }
442+
443+ @ Test
444+ void testMetrics_zeroDeadline_httpjson () throws Exception {
445+ GoldenSignalsMetricsTracerFactory tracerFactory =
446+ new GoldenSignalsMetricsTracerFactory (openTelemetrySdk );
447+
448+ RetrySettings zeroRetrySettings =
449+ RetrySettings .newBuilder ()
450+ .setInitialRpcTimeout (org .threeten .bp .Duration .ofMillis (1 ))
451+ .setMaxRpcTimeout (org .threeten .bp .Duration .ofMillis (1 ))
452+ .setTotalTimeout (org .threeten .bp .Duration .ofMillis (1 ))
453+ .setMaxAttempts (1 )
454+ .build ();
455+
456+ try (EchoClient client =
457+ TestClientInitializer .createHttpJsonEchoClientOpentelemetryWithRetrySettings (
458+ tracerFactory , zeroRetrySettings )) {
459+
460+ assertThrows (
461+ Exception .class ,
462+ () -> client .echo (EchoRequest .newBuilder ().setContent ("metrics-test" ).build ()));
463+
464+ Thread .sleep (100 );
465+ Collection <MetricData > metrics = metricReader .collectAllMetrics ();
466+ assertThat (metrics ).isNotEmpty ();
467+
468+ MetricData durationMetric =
469+ metrics .stream ()
470+ .filter (m -> m .getName ().equals ("gcp.client.request.duration" ))
471+ .findFirst ()
472+ .orElseThrow (() -> new AssertionError ("Duration metric not found" ));
473+
474+ io .opentelemetry .api .common .Attributes attributes =
475+ durationMetric .getHistogramData ().getPoints ().iterator ().next ().getAttributes ();
476+
477+ assertThat (
478+ attributes .get (
479+ AttributeKey .stringKey (ObservabilityAttributes .RPC_RESPONSE_STATUS_ATTRIBUTE )))
480+ .isEqualTo ("DEADLINE_EXCEEDED" );
481+ assertThat (
482+ attributes .get (AttributeKey .stringKey (ObservabilityAttributes .ERROR_TYPE_ATTRIBUTE )))
483+ .isEqualTo ("504" );
484+ }
485+ }
382486}
0 commit comments