feat(gapic): add OpenTelemetry channel tracing to generator templates - #18342
feat(gapic): add OpenTelemetry channel tracing to generator templates#18342chalmerlowe wants to merge 68 commits into
Conversation
There was a problem hiding this comment.
Code Review
This pull request adds OpenTelemetry tracing capabilities (Tier 3 observability) for gRPC channels in the GAPIC generator and google-api-core. It integrates client-side span creation and attribute extraction for non-streaming gRPC calls. The review feedback highlights two important improvements: handling potential ValueError exceptions gracefully when parsing malformed ports from api_endpoint in _observability.py, and supporting client_options when passed as a dictionary when resolving the custom tracer_provider in method.py.
5f64897 to
daeed98
Compare
84d77b0 to
cdd5eb8
Compare
| # Note: ClientInterceptor was added in google-api-core 2.25.0+; fallback for older versions | ||
| try: | ||
| from google.api_core.grpc_helpers import ClientInterceptor # type: ignore[attr-defined] | ||
| except ImportError: # pragma: NO COVER |
There was a problem hiding this comment.
Added do-not-merge
Until the most recent version of google-api-core is published to PyPI, the ClientInterceptor object is unavailable. While working on this PR, this is a temporary workaround to enable testing, etc. Will be removed before merge.
daeed98 to
c68dab6
Compare
c6a30e5 to
52176ce
Compare
8775743 to
d6307d6
Compare
52176ce to
59ae00b
Compare
|
We have not yet re-generated the Goldens, thus these are both failing:
The goldens are forth coming. |
… application - Use _observability.create_channel_with_otel in SecretManagerServiceClient - Use grpc_helpers.apply_interceptors in SecretManagerServiceGrpcTransport - Add unit tests for channel injection and interceptor wiring
…ing enabled - Use functools.partial to bind create_channel_with_otel with Transport.create_channel and client_options - Eliminate manual extraction of host, credentials, scopes, and quota_project_id in client - Update unit tests to verify functools.partial factory binding and lazy transport kwargs
…t mocks for older google-api-core
…ort unit test and add reviewer note
- Use functools.partial for _start_span_fn, eliminating redundant instance attributes on _GapicCallable - Let OpenTelemetry context manager automatically record escaping exceptions to prevent duplicates - Streamline _extract_status_code with parallel docstrings/comments and unify _extract_error_attributes - Remove unnecessary runtime type checks on strictly typed method_name - Defer async method tracing to follow-up PR, restoring method_async.py to main
Simplify domain, reason, and metadata checks in _extract_error_attributes by relying on standard truthiness checks.
Remove obsolete _BASE_SPAN_ATTRIBUTES alias and reuse _DEFAULT_SPAN_ATTRIBUTES across custom client options and no-service method tests.
… hook - Add rpc.system.name: 'grpc' - Extract server.address and server.port from client options endpoint - Extract gcp.grpc.resend_count from request resend count - Extract gcp.resource.destination.id from request name or parent - Add _client_response_hook for status code, error.type, and status.message - Plumb response_hook into get_otel_interceptor and get_otel_async_interceptor
- Test endpoint attribute parsing across host/port variations - Test destination id and resend count extraction - Test client request and response hooks covering all status and error cases - Test interceptor creation and custom endpoint attribute propagation - Achieve 100% statement and branch coverage on _observability.py
…and hooks - Rename _extract_t4_attributes to _extract_grpc_request_attributes - Rename _make_client_request_hook to _make_grpc_client_request_hook - Rename _client_request_hook to _grpc_client_request_hook - Rename _client_response_hook to _grpc_client_response_hook - Preserve generic _extract_endpoint_attributes for shared transport usage
…ntion - Rename test_extract_t4_attributes to test_extract_grpc_request_attributes - Rename test_client_request_hook to test_grpc_client_request_hook - Rename test_client_response_hook to test_grpc_client_response_hook - Update interceptor hook references to _grpc_client_* hooks
- Add url.domain extraction from universe_domain or default to googleapis.com - Add _extract_error_attributes helper to extract gcp.errors.domain and gcp.errors.metadata.<key> - Omit server.port when port matches scheme defaults (443 for https/grpc, 80 for http) - Remove redundant _grpc_client_response_hook and _STATUS_CODE_NAMES - Deduplicate name and parent resource lookup for gcp.resource.destination.id - Add comprehensive parametrized unit tests and update interceptor test suites
…tem attribute - Strip leading slash from gRPC attempt span names via span.update_name - Set rpc.method to the fully qualified method name per PRD specification - Retain rpc.system.name: 'grpc' and remove legacy rpc.system attribute to avoid duplication - Update unit tests to verify span name normalization and attribute deduplication
- Remove gcp.resource.destination.id extraction from _extract_grpc_request_attributes - Update unit tests to reflect attribute removal per July Strategy Update
…ments without grpc
…and fix mypy comment
d6307d6 to
b3931e9
Compare
86b7b10 to
72ad56d
Compare
b3931e9 to
99a4d3d
Compare
Problem
Generated client libraries currently lack OpenTelemetry tracing interceptor support for gRPC channels. When OpenTelemetry is configured in client options, generated clients cannot automatically create and pass interceptors down to their transport and gRPC channel.
Solution
Updates the code in the following ways:
ClientInterceptorin the gRPC transport template and updates the transport initializer signature and docstrings to accept channel interceptors.google.api_core._observabilityand pass them into the gRPC transport arguments.Notes for Reviewers
feat/otel-tracing-t4-resource-attributesbranch which introduces the required core observability helpers.