From a3c4a5b08beac06c217b720cc8766658bc7bf496 Mon Sep 17 00:00:00 2001 From: haphungw Date: Wed, 3 Jun 2026 22:35:37 +0000 Subject: [PATCH 1/3] feat(o11y): add record_polling_attributes macro --- src/lro/src/internal/tracing.rs | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/src/lro/src/internal/tracing.rs b/src/lro/src/internal/tracing.rs index 4d054b8bbf..48f009f80b 100644 --- a/src/lro/src/internal/tracing.rs +++ b/src/lro/src/internal/tracing.rs @@ -98,6 +98,21 @@ impl LroRecorder { } } +/// Injects LRO-specific telemetry attributes into the active span. +#[macro_export] +#[doc(hidden)] +macro_rules! record_polling_attributes { + ($span:expr) => { + #[cfg(google_cloud_unstable_tracing)] + { + if let Ok(attempt) = $crate::POLL_ATTEMPT_COUNT.try_with(|c| *c) { + $span.record("gcp.longrunning.poll_attempt_count", attempt); + $span.record("gcp.longrunning.done", false); + } + } + }; +} + /// Decorate a poller with tracing information. #[derive(Clone, Debug)] pub struct Tracing

{ From c6c4d38896b744695b7eb171b968df631ff7b884 Mon Sep 17 00:00:00 2001 From: haphungw Date: Wed, 3 Jun 2026 22:41:48 +0000 Subject: [PATCH 2/3] bind span expression to avoid multiple evaluation --- src/lro/src/internal/tracing.rs | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/lro/src/internal/tracing.rs b/src/lro/src/internal/tracing.rs index 48f009f80b..8e53398331 100644 --- a/src/lro/src/internal/tracing.rs +++ b/src/lro/src/internal/tracing.rs @@ -105,11 +105,18 @@ macro_rules! record_polling_attributes { ($span:expr) => { #[cfg(google_cloud_unstable_tracing)] { - if let Ok(attempt) = $crate::POLL_ATTEMPT_COUNT.try_with(|c| *c) { - $span.record("gcp.longrunning.poll_attempt_count", attempt); - $span.record("gcp.longrunning.done", false); + if let Some(recorder) = $crate::LroRecorder::current() { + if let Some(attempt) = recorder.attempt_count() { + let span = &$span; + span.record("gcp.longrunning.poll_attempt_count", attempt); + span.record("gcp.longrunning.done", false); + } } } + #[cfg(not(google_cloud_unstable_tracing))] + { + let _ = &$span; + } }; } From 9b46cbc280db110daa205f712a49a6253a8d4d8f Mon Sep 17 00:00:00 2001 From: haphungw Date: Thu, 4 Jun 2026 20:06:54 +0000 Subject: [PATCH 3/3] feat(o11y): add error extraction to DiscoveryOperation --- src/lro/src/internal/discovery.rs | 6 ++++++ src/lro/src/internal/tracing.rs | 25 +++++++++++++++++++++++++ 2 files changed, 31 insertions(+) diff --git a/src/lro/src/internal/discovery.rs b/src/lro/src/internal/discovery.rs index 98f65319ec..a36ca045c9 100644 --- a/src/lro/src/internal/discovery.rs +++ b/src/lro/src/internal/discovery.rs @@ -27,6 +27,7 @@ use crate::{ Poller, PollingBackoffPolicy, PollingErrorPolicy, PollingResult, Result, sealed::Poller as SealedPoller, }; +use google_cloud_gax::error::rpc::Status; use google_cloud_gax::polling_state::PollingState; use google_cloud_gax::retry_result::RetryResult; use std::sync::Arc; @@ -54,6 +55,11 @@ pub trait DiscoveryOperation { /// /// It may be `None` in which case the polling loop stops. fn name(&self) -> Option<&String>; + + /// Returns the error status of the operation, if any. + fn error(&self) -> Option { + None + } } pub fn new_discovery_poller( diff --git a/src/lro/src/internal/tracing.rs b/src/lro/src/internal/tracing.rs index 8e53398331..7919111609 100644 --- a/src/lro/src/internal/tracing.rs +++ b/src/lro/src/internal/tracing.rs @@ -67,7 +67,32 @@ impl LroRecorder { pub fn attempt_count(&self) -> Option { self.attempt_count } +} +/// Helper macro to record telemetry for Discovery LROs. +#[macro_export] +#[doc(hidden)] +macro_rules! record_discovery_polling_result { + ($span:expr, $op:expr) => { + let span = &$span; + let op = &$op; + let done = $crate::internal::DiscoveryOperation::done(op); + span.record("gcp.longrunning.done", done); + if done { + let error = $crate::internal::DiscoveryOperation::error(op); + let code = error.as_ref().map(|e| e.code as i32).unwrap_or(0); + span.record("gcp.longrunning.status_code", code); + if let Some(status) = error { + span.record("otel.status_code", "ERROR"); + span.record("otel.status_description", &status.message); + span.record("rpc.response.status_code", status.code as i32); + span.record("error.type", status.code.to_string()); + } + } + }; +} + +impl LroRecorder { /// Creates a new clone of `LroRecorder` carrying the specified LRO polling attempt count. /// /// Since `LroRecorder` is immutable to guarantee thread-safety, this updates the context