Repository: open-telemetry/opentelemetry-python

Issue:
Add _NoOpTracer and _NoOpTracerProvider classes
As per @ocelotl's comment [here](https://github.com/open-telemetry/opentelemetry-python/pull/2354#discussion_r781542722) the name _Default* doesn't make it clear what the behaviour is. This issue suggests creating new classes (_NoOpTracer and _NoOpTracerProvider) and marking _DefaultTracer & _DefaultTracerProvider as deprecated.


Discussion:

Resolving patch:
diff --git a/opentelemetry-api/src/opentelemetry/trace/__init__.py b/opentelemetry-api/src/opentelemetry/trace/__init__.py
--- a/opentelemetry-api/src/opentelemetry/trace/__init__.py
+++ b/opentelemetry-api/src/opentelemetry/trace/__init__.py
@@ -82,6 +82,8 @@
 from logging import getLogger
 from typing import Iterator, Optional, Sequence, cast
 
+from deprecated import deprecated
+
 from opentelemetry import context as context_api
 from opentelemetry.attributes import BoundedAttributes  # type: ignore
 from opentelemetry.context.context import Context
@@ -216,7 +218,7 @@ def get_tracer(
         """
 
 
-class _DefaultTracerProvider(TracerProvider):
+class NoOpTracerProvider(TracerProvider):
     """The default TracerProvider, used when no implementation is available.
 
     All operations are no-op.
@@ -229,7 +231,15 @@ def get_tracer(
         schema_url: typing.Optional[str] = None,
     ) -> "Tracer":
         # pylint:disable=no-self-use,unused-argument
-        return _DefaultTracer()
+        return NoOpTracer()
+
+
+@deprecated(version="1.9.0", reason="You should use NoOpTracerProvider")  # type: ignore
+class _DefaultTracerProvider(NoOpTracerProvider):
+    """The default TracerProvider, used when no implementation is available.
+
+    All operations are no-op.
+    """
 
 
 class ProxyTracerProvider(TracerProvider):
@@ -393,7 +403,7 @@ def __init__(
         self._instrumenting_library_version = instrumenting_library_version
         self._schema_url = schema_url
         self._real_tracer: Optional[Tracer] = None
-        self._noop_tracer = _DefaultTracer()
+        self._noop_tracer = NoOpTracer()
 
     @property
     def _tracer(self) -> Tracer:
@@ -416,7 +426,7 @@ def start_as_current_span(self, *args, **kwargs) -> Span:  # type: ignore
         return self._tracer.start_as_current_span(*args, **kwargs)  # type: ignore
 
 
-class _DefaultTracer(Tracer):
+class NoOpTracer(Tracer):
     """The default Tracer, used when no Tracer implementation is available.
 
     All operations are no-op.
@@ -453,6 +463,14 @@ def start_as_current_span(
         yield INVALID_SPAN
 
 
+@deprecated(version="1.9.0", reason="You should use NoOpTracer")  # type: ignore
+class _DefaultTracer(NoOpTracer):
+    """The default Tracer, used when no Tracer implementation is available.
+
+    All operations are no-op.
+    """
+
+
 _TRACER_PROVIDER_SET_ONCE = Once()
 _TRACER_PROVIDER: Optional[TracerProvider] = None
 _PROXY_TRACER_PROVIDER = ProxyTracerProvider()


Test patch:
diff --git a/opentelemetry-api/tests/test_implementation.py b/opentelemetry-api/tests/test_implementation.py
--- a/opentelemetry-api/tests/test_implementation.py
+++ b/opentelemetry-api/tests/test_implementation.py
@@ -33,8 +33,7 @@ def test_tracer(self):
             trace.TracerProvider()  # type:ignore
 
     def test_default_tracer(self):
-        # pylint: disable=protected-access
-        tracer_provider = trace._DefaultTracerProvider()
+        tracer_provider = trace.NoOpTracerProvider()
         tracer = tracer_provider.get_tracer(__name__)
         with tracer.start_span("test") as span:
             self.assertEqual(
diff --git a/opentelemetry-api/tests/trace/test_globals.py b/opentelemetry-api/tests/trace/test_globals.py
--- a/opentelemetry-api/tests/trace/test_globals.py
+++ b/opentelemetry-api/tests/trace/test_globals.py
@@ -83,11 +83,10 @@ def do_concurrently() -> Mock:
 
 class TestTracer(unittest.TestCase):
     def setUp(self):
-        # pylint: disable=protected-access
-        self.tracer = trace._DefaultTracer()
+        self.tracer = trace.NoOpTracer()
 
     def test_get_current_span(self):
-        """_DefaultTracer's start_span will also
+        """NoOpTracer's start_span will also
         be retrievable via get_current_span
         """
         self.assertEqual(trace.get_current_span(), trace.INVALID_SPAN)
diff --git a/opentelemetry-api/tests/trace/test_proxy.py b/opentelemetry-api/tests/trace/test_proxy.py
--- a/opentelemetry-api/tests/trace/test_proxy.py
+++ b/opentelemetry-api/tests/trace/test_proxy.py
@@ -21,7 +21,7 @@
 from opentelemetry.trace.span import INVALID_SPAN_CONTEXT, NonRecordingSpan
 
 
-class TestProvider(trace._DefaultTracerProvider):
+class TestProvider(trace.NoOpTracerProvider):
     def get_tracer(
         self,
         instrumenting_module_name: str,
@@ -31,7 +31,7 @@ def get_tracer(
         return TestTracer()
 
 
-class TestTracer(trace._DefaultTracer):
+class TestTracer(trace.NoOpTracer):
     def start_span(self, *args, **kwargs):
         return TestSpan(INVALID_SPAN_CONTEXT)
 
diff --git a/opentelemetry-api/tests/trace/test_tracer.py b/opentelemetry-api/tests/trace/test_tracer.py
--- a/opentelemetry-api/tests/trace/test_tracer.py
+++ b/opentelemetry-api/tests/trace/test_tracer.py
@@ -19,8 +19,7 @@
 
 class TestTracer(unittest.TestCase):
     def setUp(self):
-        # pylint: disable=protected-access
-        self.tracer = trace._DefaultTracer()
+        self.tracer = trace.NoOpTracer()
 
     def test_start_span(self):
         with self.tracer.start_span("") as span: