예제 #1
0
    def test_fetch_no_analytics(self):
        """ Confirm fetch* methods do not have analytics sample rate metric """
        with self.override_config(
                'dbapi2',
                dict(analytics_enabled=True)
        ):
            cursor = self.cursor
            cursor.rowcount = 0
            cursor.fetchone.return_value = '__result__'
            pin = Pin('pin_name', tracer=self.tracer)
            traced_cursor = FetchTracedCursor(cursor, pin)
            assert '__result__' == traced_cursor.fetchone('arg_1', kwarg1='kwarg1')

            span = self.tracer.writer.pop()[0]
            self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))

            cursor = self.cursor
            cursor.rowcount = 0
            cursor.fetchall.return_value = '__result__'
            pin = Pin('pin_name', tracer=self.tracer)
            traced_cursor = FetchTracedCursor(cursor, pin)
            assert '__result__' == traced_cursor.fetchall('arg_1', kwarg1='kwarg1')

            span = self.tracer.writer.pop()[0]
            self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))

            cursor = self.cursor
            cursor.rowcount = 0
            cursor.fetchmany.return_value = '__result__'
            pin = Pin('pin_name', tracer=self.tracer)
            traced_cursor = FetchTracedCursor(cursor, pin)
            assert '__result__' == traced_cursor.fetchmany('arg_1', kwarg1='kwarg1')

            span = self.tracer.writer.pop()[0]
            self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))
    def test_pin_find(self):
        # ensure Pin will find the first available pin

        # Override service
        obj_a = self.Obj()
        pin = Pin(service='service-a')
        pin.onto(obj_a)

        # Override service
        obj_b = self.Obj()
        pin = Pin(service='service-b')
        pin.onto(obj_b)

        # No Pin set
        obj_c = self.Obj()

        # We find the first pin (obj_b)
        pin = Pin._find(obj_c, obj_b, obj_a)
        assert pin is not None
        assert pin.service == 'service-b'

        # We find the first pin (obj_a)
        pin = Pin._find(obj_a, obj_b, obj_c)
        assert pin is not None
        assert pin.service == 'service-a'

        # We don't find a pin if none is there
        pin = Pin._find(obj_c, obj_c, obj_c)
        assert pin is None
    def _traced_session(self):
        tracer = get_dummy_tracer()
        # pin the global Cluster to test if they will conflict
        Pin(service='not-%s' % self.TEST_SERVICE).onto(Cluster)
        self.cluster = Cluster(port=CASSANDRA_CONFIG['port'])

        Pin(service=self.TEST_SERVICE, tracer=tracer).onto(self.cluster)
        return self.cluster.connect(self.TEST_KEYSPACE), tracer
예제 #4
0
    def get_tracer_and_connect(self):
        tracer = get_dummy_tracer()
        # Set a connect-level service, to check that we properly override it
        Pin(service='not-%s' % self.TEST_SERVICE).onto(mongoengine.connect)
        client = mongoengine.connect(port=MONGO_CONFIG['port'])
        Pin(service=self.TEST_SERVICE, tracer=tracer).onto(client)

        return tracer
예제 #5
0
    def test_blueprint_add_url_rule(self):
        """
        When we call ``flask.Blueprint.add_url_rule``
            When the ``Blueprint`` has a ``Pin`` attached
                We clone the Blueprint's ``Pin`` to the view
            When the ``Blueprint`` does not have a ``Pin`` attached
                We do not attach a ``Pin`` to the func
        """
        # When the Blueprint has a Pin attached
        bp = flask.Blueprint('pinned', __name__)
        Pin(service='flask-bp', tracer=self.tracer).onto(bp)

        @bp.route('/')
        def test_view():
            pass

        # Assert the view func has a `Pin` attached with the Blueprint's service name
        pin = Pin.get_from(test_view)
        self.assertIsNotNone(pin)
        self.assertEqual(pin.service, 'flask-bp')

        # When the Blueprint does not have a Pin attached
        bp = flask.Blueprint('not-pinned', __name__)

        @bp.route('/')
        def test_view():
            pass

        # Assert the view does not have a `Pin` attached
        pin = Pin.get_from(test_view)
        self.assertIsNone(pin)
    def test_s3_put(self):
        s3 = boto.s3.connect_to_region('us-east-1')

        writer = self.tracer.writer
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(s3)
        s3.create_bucket('mybucket')
        bucket = s3.get_bucket('mybucket')
        k = boto.s3.key.Key(bucket)
        k.key = 'foo'
        k.set_contents_from_string('bar')

        spans = writer.pop()
        assert spans
        # create bucket
        self.assertEqual(len(spans), 3)
        self.assertEqual(spans[0].get_tag('aws.operation'), 'create_bucket')
        self.assertEqual(spans[0].get_tag(http.STATUS_CODE), '200')
        self.assertEqual(spans[0].service, 'test-boto-tracing.s3')
        self.assertEqual(spans[0].resource, 's3.put')
        # get bucket
        self.assertEqual(spans[1].get_tag('aws.operation'), 'head_bucket')
        self.assertEqual(spans[1].resource, 's3.head')
        # put object
        self.assertEqual(spans[2].get_tag('aws.operation'), '_send_file_internal')
        self.assertEqual(spans[2].resource, 's3.put')
예제 #7
0
    def get_tracer_and_connect(self):
        tracer = TestMongoEnginePatchConnectDefault.get_tracer_and_connect(
            self)
        Pin(service=self.TEST_SERVICE, tracer=tracer).onto(mongoengine.connect)
        mongoengine.connect(port=MONGO_CONFIG['port'])

        return tracer
예제 #8
0
    def test_correct_span_names(self):
        cursor = self.cursor
        tracer = self.tracer
        cursor.rowcount = 0
        pin = Pin('pin_name', tracer=tracer)
        traced_cursor = TracedCursor(cursor, pin)

        traced_cursor.execute('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='sql.query'))
        self.reset()

        traced_cursor.executemany('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='sql.query'))
        self.reset()

        traced_cursor.callproc('arg_1', 'arg2')
        self.assert_structure(dict(name='sql.query'))
        self.reset()

        traced_cursor.fetchone('arg_1', kwarg1='kwarg1')
        self.assert_has_no_spans()

        traced_cursor.fetchmany('arg_1', kwarg1='kwarg1')
        self.assert_has_no_spans()

        traced_cursor.fetchall('arg_1', kwarg1='kwarg1')
        self.assert_has_no_spans()
    def test_ec2_client(self):
        ec2 = boto.ec2.connect_to_region('us-west-2')
        writer = self.tracer.writer
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(ec2)

        ec2.get_all_instances()
        spans = writer.pop()
        assert spans
        self.assertEqual(len(spans), 1)
        span = spans[0]
        self.assertEqual(span.get_tag('aws.operation'), 'DescribeInstances')
        self.assertEqual(span.get_tag(http.STATUS_CODE), '200')
        self.assertEqual(span.get_tag(http.METHOD), 'POST')
        self.assertEqual(span.get_tag('aws.region'), 'us-west-2')
        self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))

        # Create an instance
        ec2.run_instances(21)
        spans = writer.pop()
        assert spans
        self.assertEqual(len(spans), 1)
        span = spans[0]
        self.assertEqual(span.get_tag('aws.operation'), 'RunInstances')
        self.assertEqual(span.get_tag(http.STATUS_CODE), '200')
        self.assertEqual(span.get_tag(http.METHOD), 'POST')
        self.assertEqual(span.get_tag('aws.region'), 'us-west-2')
        self.assertEqual(span.service, 'test-boto-tracing.ec2')
        self.assertEqual(span.resource, 'ec2.runinstances')
        self.assertEqual(span.name, 'ec2.command')
        self.assertEqual(span.span_type, 'boto')
예제 #10
0
    def test_when_pin_disabled_then_no_tracing(self):
        cursor = self.cursor
        tracer = self.tracer
        cursor.rowcount = 0
        cursor.execute.return_value = '__result__'
        cursor.executemany.return_value = '__result__'

        tracer.enabled = False
        pin = Pin('pin_name', tracer=tracer)
        traced_cursor = FetchTracedCursor(cursor, pin)

        assert '__result__' == traced_cursor.execute('arg_1', kwarg1='kwarg1')
        assert len(tracer.writer.pop()) == 0

        assert '__result__' == traced_cursor.executemany('arg_1', kwarg1='kwarg1')
        assert len(tracer.writer.pop()) == 0

        cursor.callproc.return_value = 'callproc'
        assert 'callproc' == traced_cursor.callproc('arg_1', 'arg_2')
        assert len(tracer.writer.pop()) == 0

        cursor.fetchone.return_value = 'fetchone'
        assert 'fetchone' == traced_cursor.fetchone('arg_1', 'arg_2')
        assert len(tracer.writer.pop()) == 0

        cursor.fetchmany.return_value = 'fetchmany'
        assert 'fetchmany' == traced_cursor.fetchmany('arg_1', 'arg_2')
        assert len(tracer.writer.pop()) == 0

        cursor.fetchall.return_value = 'fetchall'
        assert 'fetchall' == traced_cursor.fetchall('arg_1', 'arg_2')
        assert len(tracer.writer.pop()) == 0
예제 #11
0
    def test_correct_span_names_can_be_overridden_by_pin(self):
        cursor = self.cursor
        tracer = self.tracer
        cursor.rowcount = 0
        pin = Pin('pin_name', app='changed', tracer=tracer)
        traced_cursor = FetchTracedCursor(cursor, pin)

        traced_cursor.execute('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='changed.query'))
        self.reset()

        traced_cursor.executemany('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='changed.query'))
        self.reset()

        traced_cursor.callproc('arg_1', 'arg2')
        self.assert_structure(dict(name='changed.query'))
        self.reset()

        traced_cursor.fetchone('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='changed.query.fetchone'))
        self.reset()

        traced_cursor.fetchmany('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='changed.query.fetchmany'))
        self.reset()

        traced_cursor.fetchall('arg_1', kwarg1='kwarg1')
        self.assert_structure(dict(name='changed.query.fetchall'))
        self.reset()
    def test_s3_client(self):
        s3 = self.session.create_client('s3', region_name='us-west-2')
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(s3)

        s3.list_buckets()
        s3.list_buckets()

        spans = self.get_spans()
        assert spans
        span = spans[0]
        self.assertEqual(len(spans), 2)
        self.assertEqual(span.get_tag('aws.operation'), 'ListBuckets')
        self.assertEqual(span.get_tag(http.STATUS_CODE), '200')
        self.assertEqual(span.service, 'test-botocore-tracing.s3')
        self.assertEqual(span.resource, 's3.listbuckets')

        # testing for span error
        self.reset()
        try:
            s3.list_objects(bucket='mybucket')
        except Exception:
            spans = self.get_spans()
            assert spans
            span = spans[0]
            self.assertEqual(span.error, 1)
            self.assertEqual(span.resource, 's3.listobjects')
예제 #13
0
 def test_fetchmany_wrapped_is_called_and_returned(self):
     cursor = self.cursor
     cursor.rowcount = 0
     cursor.fetchmany.return_value = '__result__'
     pin = Pin('pin_name', tracer=self.tracer)
     traced_cursor = TracedCursor(cursor, pin)
     assert '__result__' == traced_cursor.fetchmany('arg_1', kwarg1='kwarg1')
     cursor.fetchmany.assert_called_once_with('arg_1', kwarg1='kwarg1')
예제 #14
0
 def test_rollback_is_traced(self):
     connection = self.connection
     tracer = self.tracer
     connection.rollback.return_value = None
     pin = Pin('pin_name', tracer=tracer)
     traced_connection = TracedConnection(connection, pin)
     traced_connection.rollback()
     assert tracer.writer.pop()[0].name == 'mock.connection.rollback'
     connection.rollback.assert_called_with()
예제 #15
0
    def test_execute_wrapped_is_called_and_returned(self):
        cursor = self.cursor
        cursor.rowcount = 0
        cursor.execute.return_value = '__result__'

        pin = Pin('pin_name', tracer=self.tracer)
        traced_cursor = FetchTracedCursor(cursor, pin)
        assert '__result__' == traced_cursor.execute('__query__', 'arg_1', kwarg1='kwarg1')
        cursor.execute.assert_called_once_with('__query__', 'arg_1', kwarg1='kwarg1')
def patch_conn(conn):

    tags = {t: getattr(conn, a) for t, a in CONN_ATTR_BY_TAG.items() if getattr(conn, a, '') != ''}
    pin = Pin(service='mysql', app='mysql', app_type=AppTypes.db, tags=tags)

    # grab the metadata from the conn
    wrapped = TracedConnection(conn, pin=pin)
    pin.onto(wrapped)
    return wrapped
    def test_pin(self):
        # ensure a Pin can be attached to an instance
        obj = self.Obj()
        pin = Pin(service='metrics')
        pin.onto(obj)

        got = Pin.get_from(obj)
        assert got.service == pin.service
        assert got is pin
예제 #18
0
    def test_executemany_wrapped_is_called_and_returned(self):
        cursor = self.cursor
        cursor.rowcount = 0
        cursor.executemany.return_value = '__result__'

        pin = Pin('pin_name', tracer=self.tracer)
        traced_cursor = TracedCursor(cursor, pin)
        # DEV: We always pass through the result
        assert '__result__' == traced_cursor.executemany('__query__', 'arg_1', kwarg1='kwarg1')
        cursor.executemany.assert_called_once_with('__query__', 'arg_1', kwarg1='kwarg1')
예제 #19
0
    def test_patch_unpatch(self):
        # Test patch idempotence
        patch()
        patch()

        es = elasticsearch.Elasticsearch(port=ELASTICSEARCH_CONFIG['port'])
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(es.transport)

        # Test index creation
        es.indices.create(index=self.ES_INDEX, ignore=400)

        spans = self.get_spans()
        self.reset()
        assert spans, spans
        assert len(spans) == 1

        # Test unpatch
        self.reset()
        unpatch()

        es = elasticsearch.Elasticsearch(port=ELASTICSEARCH_CONFIG['port'])

        # Test index creation
        es.indices.create(index=self.ES_INDEX, ignore=400)

        spans = self.get_spans()
        self.reset()
        assert not spans, spans

        # Test patch again
        self.reset()
        patch()

        es = elasticsearch.Elasticsearch(port=ELASTICSEARCH_CONFIG['port'])
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(es.transport)

        # Test index creation
        es.indices.create(index=self.ES_INDEX, ignore=400)

        spans = self.get_spans()
        self.reset()
        assert spans, spans
        assert len(spans) == 1
    def test_unpatch(self):
        kinesis = self.session.create_client('kinesis',
                                             region_name='us-east-1')
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(kinesis)

        unpatch()

        kinesis.list_streams()
        spans = self.get_spans()
        assert not spans, spans
def _patch_server():
    if getattr(constants.GRPC_PIN_MODULE_SERVER, '__opentelemetry_patch',
               False):
        return
    setattr(constants.GRPC_PIN_MODULE_SERVER, '__opentelemetry_patch', True)

    Pin(service=config.grpc_server.service_name).onto(
        constants.GRPC_PIN_MODULE_SERVER)

    _w('grpc', 'server', _server_constructor_interceptor)
    def test_cant_pin_with_slots(self):
        # ensure a Pin can't be attached if the __slots__ is defined
        class Obj(object):
            __slots__ = ['value']

        obj = Obj()
        obj.value = 1

        Pin(service='metrics').onto(obj)
        got = Pin.get_from(obj)
        assert got is None
예제 #23
0
    def setUp(self):
        super(CeleryBaseTestCase, self).setUp()

        # instrument Celery and create an app with Broker and Result backends
        patch()
        self.pin = Pin(service='celery-unittest', tracer=self.tracer)
        self.app = Celery('celery.test_app',
                          broker=BROKER_URL,
                          backend=BACKEND_URL)
        # override pins to use our Dummy Tracer
        Pin.override(self.app, tracer=self.tracer)
    def test_unpatch(self):
        lamb = boto.awslambda.connect_to_region('us-east-2')

        writer = self.tracer.writer
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(lamb)
        unpatch()

        # multiple calls
        lamb.list_functions()
        spans = writer.pop()
        assert not spans, spans
예제 #25
0
    def test_cursor_analytics_default(self):
        cursor = self.cursor
        cursor.rowcount = 0
        cursor.execute.return_value = '__result__'

        pin = Pin('pin_name', tracer=self.tracer)
        traced_cursor = TracedCursor(cursor, pin)
        # DEV: We always pass through the result
        assert '__result__' == traced_cursor.execute('__query__', 'arg_1', kwarg1='kwarg1')

        span = self.tracer.writer.pop()[0]
        self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))
    def test_double_patch(self):
        sqs = self.session.create_client('sqs', region_name='us-east-1')
        Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(sqs)

        patch()
        patch()

        sqs.list_queues()

        spans = self.get_spans()
        assert spans
        self.assertEqual(len(spans), 1)
def _patch_client():
    if getattr(constants.GRPC_PIN_MODULE_CLIENT, '__opentelemetry_patch',
               False):
        return
    setattr(constants.GRPC_PIN_MODULE_CLIENT, '__opentelemetry_patch', True)

    Pin(service=config.grpc.service_name).onto(
        constants.GRPC_PIN_MODULE_CLIENT)

    _w('grpc', 'insecure_channel', _client_channel_interceptor)
    _w('grpc', 'secure_channel', _client_channel_interceptor)
    _w('grpc', 'intercept_channel', intercept_channel)
    def test_traced_client_analytics(self):
        with self.override_config(
                'botocore',
                dict(analytics_enabled=True, analytics_sample_rate=0.5)):
            ec2 = self.session.create_client('ec2', region_name='us-west-2')
            Pin(service=self.TEST_SERVICE, tracer=self.tracer).onto(ec2)
            ec2.describe_instances()

        spans = self.get_spans()
        assert spans
        span = spans[0]
        self.assertEqual(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY), 0.5)
예제 #29
0
def patch_conn(conn, *args, **kwargs):
    tags = {
        t: kwargs[k] if k in kwargs else args[p]
        for t, (k, p) in KWPOS_BY_TAG.items() if k in kwargs or len(args) > p
    }
    tags[net.TARGET_PORT] = conn.port
    pin = Pin(service='mysql', app='mysql', app_type=AppTypes.db, tags=tags)

    # grab the metadata from the conn
    wrapped = TracedConnection(conn, pin=pin)
    pin.onto(wrapped)
    return wrapped
예제 #30
0
 def test_connection_analytics_with_rate(self):
     with self.override_config(
             'dbapi2',
             dict(analytics_enabled=True, analytics_sample_rate=0.5)
     ):
         connection = self.connection
         tracer = self.tracer
         connection.commit.return_value = None
         pin = Pin('pin_name', tracer=tracer)
         traced_connection = TracedConnection(connection, pin)
         traced_connection.commit()
         span = tracer.writer.pop()[0]
         self.assertIsNone(span.get_metric(ANALYTICS_SAMPLE_RATE_KEY))