Пример #1
0
def traced_init(wrapped, instance, args, kwargs):
    wrapped(*args, **kwargs)

    service = config._get_service(default="bottle")

    plugin = TracePlugin(service=service)
    instance.install(plugin)
Пример #2
0
def trace_app(app, tracer, service="aiohttp-web"):
    """
    Tracing function that patches the ``aiohttp`` application so that it will be
    traced using the given ``tracer``.

    :param app: aiohttp application to trace
    :param tracer: tracer instance to use
    :param service: service name of tracer
    """

    # safe-guard: don't trace an application twice
    if getattr(app, "__datadog_trace", False):
        return
    setattr(app, "__datadog_trace", True)

    # configure datadog settings
    app[CONFIG_KEY] = {
        "tracer": tracer,
        "service": config._get_service(default=service),
        "distributed_tracing_enabled": True,
        "analytics_enabled": None,
        "analytics_sample_rate": 1.0,
    }

    # the tracer must work with asynchronous Context propagation
    tracer.configure(context_provider=context_provider)

    # add the async tracer middleware as a first middleware
    # and be sure that the on_prepare signal is the last one
    app.middlewares.insert(0, trace_middleware)
    app.on_response_prepare.append(on_prepare)
Пример #3
0
def traced_init(wrapped, instance, args, kwargs):
    mw = kwargs.pop("middleware", [])
    service = config._get_service(default="falcon")

    mw.insert(0, TraceMiddleware(tracer, service))
    kwargs["middleware"] = mw

    wrapped(*args, **kwargs)
Пример #4
0
def traced_init(wrapped, instance, args, kwargs):
    mw = kwargs.pop("middleware", [])
    service = config._get_service(default="falcon")
    distributed_tracing = asbool(
        get_env("falcon", "distributed_tracing", default=True))

    mw.insert(0, TraceMiddleware(tracer, service, distributed_tracing))
    kwargs["middleware"] = mw

    wrapped(*args, **kwargs)
Пример #5
0
def traced_init(wrapped, instance, args, kwargs):
    wrapped(*args, **kwargs)

    # set tracing options and create the TraceMiddleware
    service = config._get_service(default="pylons")
    distributed_tracing = asbool(get_env('pylons', 'distributed_tracing', default=True))
    Pin(service=service, tracer=tracer).onto(instance)
    traced_app = PylonsTraceMiddleware(instance, tracer, service=service, distributed_tracing=distributed_tracing)

    # re-order the middleware stack so that the first middleware is ours
    traced_app.app = instance.app
    instance.app = traced_app
Пример #6
0
 def test_service_name_legacy_DD_SERVICE_NAME(self):
     """
     When DD_SERVICE_NAME is provided
         It should not be used by default
         It should be used with config._get_service()
     """
     from ddtrace import config
     assert config.service is None
     with self.start_span("") as s:
         s.assert_matches(service=None)
     with self.start_span("", service=config._get_service()) as s:
         s.assert_matches(service="mysvc")
Пример #7
0
def tracer_config(__init__, app, args, kwargs):
    """
    Wrap Tornado web application so that we can configure services info and
    tracing settings after the initialization.
    """
    # call the Application constructor
    __init__(*args, **kwargs)

    # default settings
    settings = {
        'tracer': ddtrace.tracer,
        'default_service': config._get_service("tornado-web"),
        'distributed_tracing': True,
        'analytics_enabled': None
    }

    # update defaults with users settings
    user_settings = app.settings.get(CONFIG_KEY)
    if user_settings:
        settings.update(user_settings)

    app.settings[CONFIG_KEY] = settings
    tracer = settings['tracer']
    service = settings['default_service']

    # extract extra settings
    extra_settings = settings.get('settings', {})

    # the tracer must use the right Context propagation and wrap executor;
    # this action is done twice because the patch() method uses the
    # global tracer while here we can have a different instance (even if
    # this is not usual).
    tracer.configure(
        context_provider=context_provider,
        wrap_executor=decorators.wrap_executor,
        enabled=settings.get('enabled', None),
        hostname=settings.get('agent_hostname', None),
        port=settings.get('agent_port', None),
        settings=extra_settings,
    )

    # set global tags if any
    tags = settings.get('tags', None)
    if tags:
        tracer.set_tags(tags)

    # configure the PIN object for template rendering
    ddtrace.Pin(app='tornado', service=service, tracer=tracer).onto(template)
Пример #8
0
from ddtrace.internal.logger import get_logger
from ddtrace.propagation.http import HTTPPropagator
from ddtrace.propagation.utils import from_wsgi_header
from ddtrace.utils.formats import asbool, get_env
from ddtrace.utils.wrappers import unwrap, iswrapped

from .compat import get_resolver, user_is_authenticated
from . import utils, conf

wrap = wrapt.wrap_function_wrapper
log = get_logger(__name__)

config._add(
    "django",
    dict(
        service_name=config._get_service(default="django"),
        cache_service_name=get_env("django", "cache_service_name") or "django",
        database_service_name_prefix=get_env("django",
                                             "database_service_name_prefix",
                                             default=""),
        distributed_tracing_enabled=True,
        instrument_middleware=asbool(
            get_env("django", "instrument_middleware", default=True)),
        instrument_databases=True,
        instrument_caches=True,
        analytics_enabled=
        None,  # None allows the value to be overridden by the global config
        analytics_sample_rate=None,
        trace_query_string=None,  # Default to global config
        include_user_name=True,
        use_handler_resource_format=get_env("django",
Пример #9
0
from ...internal.compat import reraise
from ...internal.logger import get_logger
from .utils import guarantee_single_callable

if TYPE_CHECKING:
    from typing import Any
    from typing import Mapping
    from typing import Optional

    from ddtrace import Span

log = get_logger(__name__)

config._add(
    "asgi",
    dict(service_name=config._get_service(default="asgi"),
         request_span_name="asgi.request",
         distributed_tracing=True),
)

ASGI_VERSION = "asgi.version"
ASGI_SPEC_VERSION = "asgi.spec_version"


def bytes_to_str(str_or_bytes):
    return str_or_bytes.decode() if isinstance(str_or_bytes,
                                               bytes) else str_or_bytes


def _extract_versions_from_scope(scope, integration_config):
    tags = {}
Пример #10
0
from ddtrace import config
from ddtrace.constants import ANALYTICS_SAMPLE_RATE_KEY
from ddtrace.ext import SpanTypes
from ddtrace.ext import http

from .. import trace_utils
from ...internal.compat import reraise
from ...internal.logger import get_logger
from .utils import guarantee_single_callable


log = get_logger(__name__)

config._add(
    "asgi",
    dict(service_name=config._get_service(default="asgi"), request_span_name="asgi.request", distributed_tracing=True),
)

ASGI_VERSION = "asgi.version"
ASGI_SPEC_VERSION = "asgi.spec_version"


def bytes_to_str(str_or_bytes):
    return str_or_bytes.decode() if isinstance(str_or_bytes, bytes) else str_or_bytes


def _extract_versions_from_scope(scope, integration_config):
    tags = {}

    http_version = scope.get("http_version")
    if http_version:
Пример #11
0
import os

import grpc

from ddtrace.vendor.wrapt import wrap_function_wrapper as _w
from ddtrace import config, Pin

from ...utils.wrappers import unwrap as _u

from . import constants
from .client_interceptor import create_client_interceptor, intercept_channel
from .server_interceptor import create_server_interceptor


config._add('grpc_server', dict(
    service_name=config._get_service(default=constants.GRPC_SERVICE_SERVER),
    distributed_tracing_enabled=True,
))


# Precedence for the service name:
# 1) DD_GRPC_SERVICE if defined; or
# 2) For compatibility, the globally set service + "-grpc-client"; or
# 3) The fall-back "grpc-client"
if "DD_GRPC_SERVICE" in os.environ:
    service = os.getenv("DD_GRPC_SERVICE")
elif config._get_service():
    service = "{}-{}".format(config._get_service(), constants.GRPC_SERVICE_CLIENT)
else:
    service = constants.GRPC_SERVICE_CLIENT
Пример #12
0
from ddtrace import config

# Celery Context key
CTX_KEY = "__dd_task_span"

# Span names
PRODUCER_ROOT_SPAN = "celery.apply"
WORKER_ROOT_SPAN = "celery.run"

# Task operations
TASK_TAG_KEY = "celery.action"
TASK_APPLY = "apply"
TASK_APPLY_ASYNC = "apply_async"
TASK_RUN = "run"
TASK_RETRY_REASON_KEY = "celery.retry.reason"

# Service info
PRODUCER_SERVICE = config._get_service(default="celery-producer")
WORKER_SERVICE = config._get_service(default="celery-worker")
Пример #13
0
import grpc

from ddtrace.vendor.wrapt import wrap_function_wrapper as _w
from ddtrace import config, Pin

from ...utils.wrappers import unwrap as _u

from . import constants
from .client_interceptor import create_client_interceptor, intercept_channel
from .server_interceptor import create_server_interceptor

config._add(
    'grpc_server',
    dict(
        service_name=config._get_service(
            default=constants.GRPC_SERVICE_SERVER),
        distributed_tracing_enabled=True,
    ))

# TODO[tbutt]: keeping name for client config unchanged to maintain backwards
# compatibility but should change in future
config._add(
    'grpc',
    dict(
        service_name='{}-{}'.format(config._get_service(),
                                    constants.GRPC_SERVICE_CLIENT)
        if config._get_service() else constants.GRPC_SERVICE_CLIENT,
        distributed_tracing_enabled=True,
    ))

Пример #14
0
from .helpers import get_current_app, get_current_span, simple_tracer, with_instance_pin
from .wrappers import wrap_function, wrap_signal

log = get_logger(__name__)

FLASK_ENDPOINT = 'flask.endpoint'
FLASK_VIEW_ARGS = 'flask.view_args'
FLASK_URL_RULE = 'flask.url_rule'
FLASK_VERSION = 'flask.version'

# Configure default configuration
config._add(
    'flask',
    dict(
        # Flask service configuration
        service_name=config._get_service(default="flask"),
        app='flask',
        collect_view_args=True,
        distributed_tracing_enabled=True,
        template_default_name='<memory>',
        trace_signals=True,

        # We mark 5xx responses as errors, these codes are additional status codes to mark as errors
        # DEV: This is so that if a user wants to see `401` or `403` as an error, they can configure that
        extra_error_codes=set(),
    ))

# Extract flask version into a tuple e.g. (0, 12, 1) or (1, 0, 2)
# DEV: This makes it so we can do `if flask_version >= (0, 12, 0):`
# DEV: Example tests:
#      (0, 10, 0) > (0, 10)
Пример #15
0
import ddtrace
import sanic
from ddtrace import config
from ddtrace.constants import ANALYTICS_SAMPLE_RATE_KEY
from ddtrace.ext import SpanTypes, http
from ddtrace.http import store_request_headers, store_response_headers
from ddtrace.propagation.http import HTTPPropagator
from ddtrace.utils.wrappers import unwrap as _u
from ddtrace.vendor import wrapt
from ddtrace.vendor.wrapt import wrap_function_wrapper as _w

from ...internal.logger import get_logger

log = get_logger(__name__)

config._add("sanic", dict(service=config._get_service(default="sanic"), distributed_tracing=True))


def _extract_tags_from_request(request):
    tags = {}
    tags[http.METHOD] = request.method

    url = "{scheme}://{host}{path}".format(scheme=request.scheme, host=request.host, path=request.path)
    tags[http.URL] = url

    query_string = None
    if config.sanic.trace_query_string:
        query_string = request.query_string
        if isinstance(query_string, bytes):
            query_string = query_string.decode()
        tags[http.QUERY_STRING] = query_string