From 79e7dd602403768d4ff5043d79441f26d792d5e4 Mon Sep 17 00:00:00 2001 From: Leighton Chen Date: Tue, 3 Oct 2023 15:28:03 -0700 Subject: [PATCH 1/5] sem --- CHANGELOG.md | 5 ++ .../instrumentation/instrumentor.py | 6 +++ .../opentelemetry/instrumentation/utils.py | 53 +++++++++++++++++++ 3 files changed, 64 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1206844e55..ebe9a47c24 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## Unreleased +### Added + +- `opentelemetry-instrumentation` Added Otel semantic convention opt-in mechanism + ([#1901](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/1901)) + ## Version 1.20.0/0.41b0 (2023-09-01) ### Fixed diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py index 7f05e7f30a..37ed9d5638 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py @@ -25,6 +25,9 @@ DependencyConflict, get_dependency_conflicts, ) +from opentelemetry.instrumentation.utils import ( + _OpenTelemetrySemanticConventionStability, +) _LOG = getLogger(__name__) @@ -104,6 +107,9 @@ def instrument(self, **kwargs): if conflict: _LOG.error(conflict) return None + + # initialize semantic conventions opt-in if needed + _OpenTelemetrySemanticConventionStability._initialize() result = self._instrument( # pylint: disable=assignment-from-no-return **kwargs diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py index 35a55a1279..5c83642e49 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py @@ -12,6 +12,8 @@ # See the License for the specific language governing permissions and # limitations under the License. +import os +import threading import urllib.parse from re import escape, sub from typing import Dict, Sequence @@ -152,3 +154,54 @@ def _python_path_without_directory(python_path, directory, path_separator): "", python_path, ) + +_OTEL_SEMCONV_STABILITY_OPT_IN_KEY = "OTEL_SEMCONV_STABILITY_OPT_IN" + +class _OpenTelemetryStabilitySignalType: + HTTP = "http" + +class _OpenTelemetryStabilityMode: + # http - emit the new, stable HTTP and networking conventions ONLY + HTTP = "http" + # http/dup - emit both the old and the stable HTTP and networking conventions + HTTP_DUP = "http/dup" + # default - continue emitting old experimental HTTP and networking conventions + DEFAULT = "default" + +class _OpenTelemetrySemanticConventionStability: + _initialized = False + _lock = threading.Lock() + _OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING = {} + + @classmethod + def _initialize(cls): + with _OpenTelemetrySemanticConventionStability._lock: + if not _OpenTelemetrySemanticConventionStability._initialized: + # Users can pass in comma delimited string for opt-in options + # Only values for http stability are supported for now + opt_in = os.environ.get(_OTEL_SEMCONV_STABILITY_OPT_IN_KEY, "") + opt_in_list = [] + if opt_in: + opt_in_list = [ + s.strip() for s in opt_in.split(",") + ] + http_opt_in = _OpenTelemetryStabilityMode.DEFAULT + if opt_in_list: + # Process http opt-in + # http/dup takes priority over http + if _OpenTelemetryStabilityMode.HTTP_DUP in opt_in_list: + http_opt_in = _OpenTelemetryStabilityMode.HTTP_DUP + elif _OpenTelemetryStabilityMode.HTTP in opt_in_list: + http_opt_in = _OpenTelemetryStabilityMode.HTTP + _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING[ + _OpenTelemetryStabilitySignalType.HTTP + ] = http_opt_in + _OpenTelemetrySemanticConventionStability._initialized = True + + + @classmethod + def _get_opentelemetry_stability_opt_in(type: _OpenTelemetryStabilitySignalType) -> _OpenTelemetryStabilityMode: + with _OpenTelemetrySemanticConventionStability._lock: + return _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING.get( + type, _OpenTelemetryStabilityMode.DEFAULT + ) From df71baf4e0a7de573217bddbae64663081f4375a Mon Sep 17 00:00:00 2001 From: Leighton Chen Date: Tue, 3 Oct 2023 16:04:23 -0700 Subject: [PATCH 2/5] lint --- CHANGELOG.md | 2 +- .../opentelemetry/instrumentation/instrumentor.py | 2 +- .../src/opentelemetry/instrumentation/utils.py | 13 ++++++++----- 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ebe9a47c24..72f22fe6d7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,7 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added - `opentelemetry-instrumentation` Added Otel semantic convention opt-in mechanism - ([#1901](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/1901)) + ([#1987](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/1987)) ## Version 1.20.0/0.41b0 (2023-09-01) diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py index 37ed9d5638..6c6f86fd51 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/instrumentor.py @@ -107,7 +107,7 @@ def instrument(self, **kwargs): if conflict: _LOG.error(conflict) return None - + # initialize semantic conventions opt-in if needed _OpenTelemetrySemanticConventionStability._initialize() diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py index 5c83642e49..cb4c57e67c 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py @@ -155,11 +155,14 @@ def _python_path_without_directory(python_path, directory, path_separator): python_path, ) + _OTEL_SEMCONV_STABILITY_OPT_IN_KEY = "OTEL_SEMCONV_STABILITY_OPT_IN" + class _OpenTelemetryStabilitySignalType: HTTP = "http" + class _OpenTelemetryStabilityMode: # http - emit the new, stable HTTP and networking conventions ONLY HTTP = "http" @@ -168,6 +171,7 @@ class _OpenTelemetryStabilityMode: # default - continue emitting old experimental HTTP and networking conventions DEFAULT = "default" + class _OpenTelemetrySemanticConventionStability: _initialized = False _lock = threading.Lock() @@ -182,9 +186,7 @@ def _initialize(cls): opt_in = os.environ.get(_OTEL_SEMCONV_STABILITY_OPT_IN_KEY, "") opt_in_list = [] if opt_in: - opt_in_list = [ - s.strip() for s in opt_in.split(",") - ] + opt_in_list = [s.strip() for s in opt_in.split(",")] http_opt_in = _OpenTelemetryStabilityMode.DEFAULT if opt_in_list: # Process http opt-in @@ -198,9 +200,10 @@ def _initialize(cls): ] = http_opt_in _OpenTelemetrySemanticConventionStability._initialized = True - @classmethod - def _get_opentelemetry_stability_opt_in(type: _OpenTelemetryStabilitySignalType) -> _OpenTelemetryStabilityMode: + def _get_opentelemetry_stability_opt_in( + type: _OpenTelemetryStabilitySignalType + ) -> _OpenTelemetryStabilityMode: with _OpenTelemetrySemanticConventionStability._lock: return _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING.get( type, _OpenTelemetryStabilityMode.DEFAULT From 571f9e2ca0b48fd5453fd390cee7e8f469b2e6f2 Mon Sep 17 00:00:00 2001 From: Leighton Chen Date: Thu, 5 Oct 2023 15:49:52 -0700 Subject: [PATCH 3/5] Update utils.py --- .../src/opentelemetry/instrumentation/utils.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py index cb4c57e67c..0b0397a8df 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py @@ -198,11 +198,11 @@ def _initialize(cls): _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING[ _OpenTelemetryStabilitySignalType.HTTP ] = http_opt_in - _OpenTelemetrySemanticConventionStability._initialized = True + _OpenTelemetrySemanticConventionStability._initialized = True @classmethod def _get_opentelemetry_stability_opt_in( - type: _OpenTelemetryStabilitySignalType + type: _OpenTelemetryStabilitySignalType, ) -> _OpenTelemetryStabilityMode: with _OpenTelemetrySemanticConventionStability._lock: return _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING.get( From fb34c86b8636c403846b82a1e7bb1df071caf525 Mon Sep 17 00:00:00 2001 From: jeremydvoss Date: Tue, 17 Oct 2023 13:56:27 -0700 Subject: [PATCH 4/5] Using enum --- .../src/opentelemetry/instrumentation/utils.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py index 0b0397a8df..1cce80bde7 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py @@ -15,6 +15,7 @@ import os import threading import urllib.parse +from enum import Enum from re import escape, sub from typing import Dict, Sequence @@ -163,7 +164,7 @@ class _OpenTelemetryStabilitySignalType: HTTP = "http" -class _OpenTelemetryStabilityMode: +class _OpenTelemetryStabilityMode(Enum): # http - emit the new, stable HTTP and networking conventions ONLY HTTP = "http" # http/dup - emit both the old and the stable HTTP and networking conventions @@ -191,9 +192,9 @@ def _initialize(cls): if opt_in_list: # Process http opt-in # http/dup takes priority over http - if _OpenTelemetryStabilityMode.HTTP_DUP in opt_in_list: + if _OpenTelemetryStabilityMode.HTTP_DUP.value in opt_in_list: http_opt_in = _OpenTelemetryStabilityMode.HTTP_DUP - elif _OpenTelemetryStabilityMode.HTTP in opt_in_list: + elif _OpenTelemetryStabilityMode.HTTP.value in opt_in_list: http_opt_in = _OpenTelemetryStabilityMode.HTTP _OpenTelemetrySemanticConventionStability._OTEL_SEMCONV_STABILITY_SIGNAL_MAPPING[ _OpenTelemetryStabilitySignalType.HTTP From edfa99e0aa0a8fd4d8b26c2e9afc9ff32dafb153 Mon Sep 17 00:00:00 2001 From: jeremydvoss Date: Tue, 17 Oct 2023 17:46:31 -0700 Subject: [PATCH 5/5] lint --- .../src/opentelemetry/instrumentation/utils.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py index 1cce80bde7..e4f9b37c37 100644 --- a/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py +++ b/opentelemetry-instrumentation/src/opentelemetry/instrumentation/utils.py @@ -192,7 +192,10 @@ def _initialize(cls): if opt_in_list: # Process http opt-in # http/dup takes priority over http - if _OpenTelemetryStabilityMode.HTTP_DUP.value in opt_in_list: + if ( + _OpenTelemetryStabilityMode.HTTP_DUP.value + in opt_in_list + ): http_opt_in = _OpenTelemetryStabilityMode.HTTP_DUP elif _OpenTelemetryStabilityMode.HTTP.value in opt_in_list: http_opt_in = _OpenTelemetryStabilityMode.HTTP