mirror of
https://github.com/open-telemetry/opentelemetry-python-contrib.git
synced 2025-07-31 14:11:50 +08:00
59 lines
2.3 KiB
Python
59 lines
2.3 KiB
Python
import gevent
|
|
import gevent.pool as gpool
|
|
|
|
from .provider import CONTEXT_ATTR
|
|
|
|
GEVENT_VERSION = gevent.version_info[0:3]
|
|
|
|
|
|
class TracingMixin(object):
|
|
def __init__(self, *args, **kwargs):
|
|
# get the current Context if available
|
|
current_g = gevent.getcurrent()
|
|
ctx = getattr(current_g, CONTEXT_ATTR, None)
|
|
|
|
# create the Greenlet as usual
|
|
super(TracingMixin, self).__init__(*args, **kwargs)
|
|
|
|
# the context is always available made exception of the main greenlet
|
|
if ctx:
|
|
# create a new context that inherits the current active span
|
|
new_ctx = ctx.clone()
|
|
setattr(self, CONTEXT_ATTR, new_ctx)
|
|
|
|
|
|
class TracedGreenlet(TracingMixin, gevent.Greenlet):
|
|
"""
|
|
``Greenlet`` class that is used to replace the original ``gevent``
|
|
class. This class is supposed to do ``Context`` replacing operation, so
|
|
that any greenlet inherits the context from the parent Greenlet.
|
|
When a new greenlet is spawned from the main greenlet, a new instance
|
|
of ``Context`` is created. The main greenlet is not affected by this behavior.
|
|
|
|
There is no need to inherit this class to create or optimize greenlets
|
|
instances, because this class replaces ``gevent.greenlet.Greenlet``
|
|
through the ``patch()`` method. After the patch, extending the gevent
|
|
``Greenlet`` class means extending automatically ``TracedGreenlet``.
|
|
"""
|
|
def __init__(self, *args, **kwargs):
|
|
super(TracedGreenlet, self).__init__(*args, **kwargs)
|
|
|
|
|
|
class TracedIMapUnordered(TracingMixin, gpool.IMapUnordered):
|
|
def __init__(self, *args, **kwargs):
|
|
super(TracedIMapUnordered, self).__init__(*args, **kwargs)
|
|
|
|
|
|
if GEVENT_VERSION >= (1, 3) or GEVENT_VERSION < (1, 1):
|
|
# For gevent <1.1 and >=1.3, IMap is its own class, so we derive
|
|
# from TracingMixin
|
|
class TracedIMap(TracingMixin, gpool.IMap):
|
|
def __init__(self, *args, **kwargs):
|
|
super(TracedIMap, self).__init__(*args, **kwargs)
|
|
else:
|
|
# For gevent >=1.1 and <1.3, IMap derives from IMapUnordered, so we derive
|
|
# from TracedIMapUnordered and get tracing that way
|
|
class TracedIMap(gpool.IMap, TracedIMapUnordered):
|
|
def __init__(self, *args, **kwargs):
|
|
super(TracedIMap, self).__init__(*args, **kwargs)
|