Example #1
0
def test_broken_500_handler_with_middleware(django_elasticapm_client, client):
    with override_settings(BREAK_THAT_500=True):
        client.handler = MockMiddleware(MockClientHandler())

        with override_settings(**middleware_setting(django.VERSION, [])):
            with pytest.raises(Exception):
                client.get(reverse('elasticapm-raise-exc'))

        assert len(django_elasticapm_client.events) == 2
        event = django_elasticapm_client.events.pop(0)['errors'][0]

        assert 'exception' in event
        exc = event['exception']
        assert exc['type'] == 'Exception'
        assert exc['message'] == 'Exception: view exception'
        assert event['culprit'] == 'tests.contrib.django.testapp.views.raise_exc'

        event = django_elasticapm_client.events.pop(0)['errors'][0]

        assert 'exception' in event
        exc = event['exception']
        assert exc['type'] == 'ValueError'
        assert exc['message'] == 'ValueError: handler500'
        assert event['culprit'] == 'tests.contrib.django.testapp.urls.handler500'
        assert event['handled'] is False
Example #2
0
def test_transaction_request_response_data(django_elasticapm_client, client):
    client.cookies = SimpleCookie({'foo': 'bar'})
    django_elasticapm_client.instrumentation_store.get_all()
    with override_settings(**middleware_setting(
            django.VERSION, ['elasticapm.contrib.django.middleware.TracingMiddleware']
    )):
        client.get(reverse('elasticapm-no-error'))
    assert len(django_elasticapm_client.instrumentation_store) == 1
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert len(transactions) == 1
    transaction = transactions[0]
    assert transaction['result'] == 'HTTP 2xx'
    assert 'request' in transaction['context']
    request = transaction['context']['request']
    assert request['method'] == 'GET'
    assert 'headers' in request
    headers = request['headers']
    assert headers['cookie'] == ' foo=bar'
    env = request['env']
    assert 'SERVER_NAME' in env, env.keys()
    assert env['SERVER_NAME'] == 'testserver'
    assert 'SERVER_PORT' in env, env.keys()
    assert env['SERVER_PORT'] == '80'

    assert 'response' in transaction['context']
    response = transaction['context']['response']
    assert response['status_code'] == 200
    assert response['headers']['my-header'] == 'foo'
Example #3
0
def test_request_metrics_301_append_slash(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store

    # enable middleware wrapping
    django_elasticapm_client.config.instrument_django_middleware = True

    from elasticapm.contrib.django.middleware import TracingMiddleware
    TracingMiddleware._elasticapm_instrumented = False

    with override_settings(
        APPEND_SLASH=True,
        **middleware_setting(django.VERSION, [
            'elasticapm.contrib.django.middleware.TracingMiddleware',
            'django.middleware.common.CommonMiddleware',
        ])
    ):
        client.get(reverse('elasticapm-no-error-slash')[:-1])
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['name'] in (
        # django <= 1.8
        'GET django.middleware.common.CommonMiddleware.process_request',
        # django 1.9+
        'GET django.middleware.common.CommonMiddleware.process_response',
    )
    assert transactions[0]['result'] == 'HTTP 3xx'
Example #4
0
def test_user_info(django_elasticapm_client, client):
    user = User(username='******', email='*****@*****.**')
    user.set_password('admin')
    user.save()

    with pytest.raises(Exception):
        client.get(reverse('elasticapm-raise-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert 'user' in event['context']
    user_info = event['context']['user']
    assert 'is_authenticated' in user_info
    assert not user_info['is_authenticated']
    assert user_info['username'] == ''
    assert 'email' not in user_info

    assert client.login(username='******', password='******')

    with pytest.raises(Exception):
        client.get(reverse('elasticapm-raise-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert 'user' in event['context']
    user_info = event['context']['user']
    assert 'is_authenticated' in user_info
    assert user_info['is_authenticated']
    assert 'username' in user_info
    assert user_info['username'] == 'admin'
    assert 'email' in user_info
    assert user_info['email'] == '*****@*****.**'
Example #5
0
def test_request_metrics_404_resolve_error(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store
    with override_settings(
        **middleware_setting(django.VERSION, ['elasticapm.contrib.django.middleware.TracingMiddleware'])
    ):
        client.get('/i-dont-exist/')
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['name'] == ''
Example #6
0
def test_tracing_middleware_uses_test_client(client, django_elasticapm_client):
    with override_settings(**middleware_setting(django.VERSION, [
        'elasticapm.contrib.django.middleware.TracingMiddleware'
    ])):
        client.get('/')
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert len(transactions) == 1
    assert transactions[0]['context']['request']['url']['pathname'] == '/'
Example #7
0
def test_exclude_modules_view(django_elasticapm_client, client):
    django_elasticapm_client.config.exclude_paths = ['tests.views.decorated_raise_exc']
    with pytest.raises(Exception):
        client.get(reverse('elasticapm-raise-exc-decor'))

    assert len(django_elasticapm_client.events) == 1, django_elasticapm_client.events
    event = django_elasticapm_client.events.pop(0)['errors'][0]

    assert event['culprit'] == 'tests.contrib.django.testapp.views.raise_exc'
Example #8
0
def test_user_info_without_auth_middleware_django_2(django_elasticapm_client, client):
    with override_settings(MIDDLEWARE_CLASSES=None, MIDDLEWARE=[
        m for m in settings.MIDDLEWARE
        if m != 'django.contrib.auth.middleware.AuthenticationMiddleware'
    ]):
        with pytest.raises(Exception):
            client.get(reverse('elasticapm-raise-exc'))
    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert event['context']['user'] == {}
Example #9
0
def test_include_modules(django_elasticapm_client, client):
    django_elasticapm_client.config.include_paths = ['django.shortcuts.get_object_or_404']

    with pytest.raises(Exception):
        client.get(reverse('elasticapm-django-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]

    assert event['culprit'] == 'django.shortcuts.get_object_or_404'
Example #10
0
def test_request_metrics_name_override(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store
    with override_settings(
        **middleware_setting(django.VERSION, [
            'elasticapm.contrib.django.middleware.TracingMiddleware',
            'tests.contrib.django.testapp.middleware.MetricsNameOverrideMiddleware',
        ])
    ):
        client.get(reverse('elasticapm-no-error'))
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['name'] == 'GET foobar'
Example #11
0
def test_view_exception(django_elasticapm_client, client):
    with pytest.raises(Exception):
        client.get(reverse('elasticapm-raise-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert 'exception' in event
    exc = event['exception']
    assert exc['type'] == 'Exception'
    assert exc['message'] == 'Exception: view exception'
    assert event['culprit'] == 'tests.contrib.django.testapp.views.raise_exc'
    assert event['handled'] is False
Example #12
0
def test_django_logging_middleware(django_elasticapm_client, client):
    handler = LoggingHandler()

    logger = logging.getLogger('logmiddleware')
    logger.handlers = []
    logger.addHandler(handler)

    with override_settings(**middleware_setting(django.VERSION,
                                                ['elasticapm.contrib.django.middleware.LogMiddleware'])):
        client.get(reverse('elasticapm-logging'))
    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert 'request' in event['context']
    assert event['context']['request']['url']['pathname'] == reverse('elasticapm-logging')
Example #13
0
def test_view_middleware_exception(django_elasticapm_client, client):
    with override_settings(**middleware_setting(django.VERSION,
                                            ['tests.contrib.django.testapp.middleware.BrokenViewMiddleware'])):
        with pytest.raises(ImportError):
            client.get(reverse('elasticapm-raise-exc'))

        assert len(django_elasticapm_client.events) == 1
        event = django_elasticapm_client.events.pop(0)['errors'][0]

        assert 'exception' in event
        exc = event['exception']
        assert exc['type'] == 'ImportError'
        assert exc['message'] == 'ImportError: view'
        assert event['culprit'] == 'tests.contrib.django.testapp.middleware.process_view'
        assert event['handled'] is False
Example #14
0
def test_transaction_metrics(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store
    with override_settings(**middleware_setting(
            django.VERSION, ['elasticapm.contrib.django.middleware.TracingMiddleware']
    )):
        assert len(django_elasticapm_client.instrumentation_store) == 0
        client.get(reverse('elasticapm-no-error'))
        assert len(django_elasticapm_client.instrumentation_store) == 1

        transactions = django_elasticapm_client.instrumentation_store.get_all()

        assert len(transactions) == 1
        transaction = transactions[0]
        assert transaction['duration'] > 0
        assert transaction['result'] == 'HTTP 2xx'
        assert transaction['name'] == 'GET tests.contrib.django.testapp.views.no_error'
Example #15
0
def test_user_info_raises_database_error(django_elasticapm_client, client):
    user = User(username='******', email='*****@*****.**')
    user.set_password('admin')
    user.save()

    assert client.login(username='******', password='******')

    with mock.patch("django.contrib.auth.models.User.is_authenticated") as is_authenticated:
        is_authenticated.side_effect = DatabaseError("Test Exception")
        with pytest.raises(Exception):
            client.get(reverse('elasticapm-raise-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert 'user' in event['context']
    user_info = event['context']['user']
    assert user_info == {}
Example #16
0
def test_response_middlware_exception(django_elasticapm_client, client):
    if django.VERSION[:2] < (1, 3):
        return
    with override_settings(**middleware_setting(django.VERSION,
                                            ['tests.contrib.django.testapp.middleware.BrokenResponseMiddleware'])):
        with pytest.raises(ImportError):
            client.get(reverse('elasticapm-no-error'))

        assert len(django_elasticapm_client.events) == 1
        event = django_elasticapm_client.events.pop(0)['errors'][0]

        assert 'exception' in event
        exc = event['exception']
        assert exc['type'] == 'ImportError'
        assert exc['message'] == 'ImportError: response'
        assert event['culprit'] == 'tests.contrib.django.testapp.middleware.process_response'
        assert event['handled'] is False
Example #17
0
def test_request_metrics_301_prepend_www(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store

    # enable middleware wrapping
    django_elasticapm_client.config.instrument_django_middleware = True

    from elasticapm.contrib.django.middleware import TracingMiddleware
    TracingMiddleware._elasticapm_instrumented = False

    with override_settings(
        PREPEND_WWW=True,
        **middleware_setting(django.VERSION, [
            'elasticapm.contrib.django.middleware.TracingMiddleware',
            'django.middleware.common.CommonMiddleware',
        ])
    ):
        client.get(reverse('elasticapm-no-error'))
    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['name'] == 'GET django.middleware.common.CommonMiddleware.process_request'
    assert transactions[0]['result'] == 'HTTP 3xx'
Example #18
0
def test_user_info_with_custom_user(django_elasticapm_client, client):
    with override_settings(AUTH_USER_MODEL='testapp.MyUser'):
        from django.contrib.auth import get_user_model
        MyUser = get_user_model()
        user = MyUser(my_username='******')
        user.set_password('admin')
        user.save()
        assert client.login(username='******', password='******')
        with pytest.raises(Exception):
            client.get(reverse('elasticapm-raise-exc'))

        assert len(django_elasticapm_client.events) == 1
        event = django_elasticapm_client.events.pop(0)['errors'][0]
        assert 'user' in event['context']
        user_info = event['context']['user']
        assert 'is_authenticated' in user_info
        assert user_info['is_authenticated']
        assert 'username' in user_info
        assert user_info['username'] == 'admin'
        assert 'email' not in user_info
Example #19
0
def test_response_error_id_middleware(django_elasticapm_client, client):
    with override_settings(**middleware_setting(django.VERSION, [
            'elasticapm.contrib.django.middleware.ErrorIdMiddleware',
            'elasticapm.contrib.django.middleware.Catch404Middleware'])):
        resp = client.get('/non-existant-page')
        assert resp.status_code == 404
        headers = dict(resp.items())
        assert 'X-ElasticAPM-ErrorId' in headers
        assert len(django_elasticapm_client.events) == 1
        event = django_elasticapm_client.events.pop(0)['errors'][0]
        assert event['id'] == headers['X-ElasticAPM-ErrorId']
Example #20
0
def test_404_middleware_with_debug(django_elasticapm_client, client):
    django_elasticapm_client.config.debug = False
    with override_settings(
            DEBUG=True,
            **middleware_setting(django.VERSION, [
                'elasticapm.contrib.django.middleware.Catch404Middleware'
            ])
    ):
        resp = client.get('/non-existant-page')
        assert resp.status_code == 404
        assert len(django_elasticapm_client.events) == 0
Example #21
0
def test_user_info_with_non_django_auth(django_elasticapm_client, client):
    with override_settings(INSTALLED_APPS=[
        app for app in settings.INSTALLED_APPS
        if app != 'django.contrib.auth'
    ]) and override_settings(MIDDLEWARE_CLASSES=[
        m for m in settings.MIDDLEWARE_CLASSES
        if m != 'django.contrib.auth.middleware.AuthenticationMiddleware'
    ]):
        with pytest.raises(Exception):
            resp = client.get(reverse('elasticapm-raise-exc'))

    assert len(django_elasticapm_client.events) == 1
    event = django_elasticapm_client.events.pop(0)['errors'][0]
    assert event['context']['user'] == {}
Example #22
0
def test_404_middleware(django_elasticapm_client, client):
    with override_settings(**middleware_setting(django.VERSION,
                                            ['elasticapm.contrib.django.middleware.Catch404Middleware'])):
        resp = client.get('/non-existant-page')
        assert resp.status_code == 404

        assert len(django_elasticapm_client.events) == 1
        event = django_elasticapm_client.events.pop(0)['errors'][0]

        assert event['log']['level'] == 'info'
        assert event['log']['logger_name'] == 'http404'

        assert 'request' in event['context']
        request = event['context']['request']
        assert request['url']['full'] == u'http://testserver/non-existant-page'
        assert request['method'] == 'GET'
        assert request['body'] == None
Example #23
0
def test_stacktrace_filtered_for_elasticapm(client, django_elasticapm_client):
    with mock.patch(
            "elasticapm.traces.TransactionsStore.should_collect") as should_collect:
        should_collect.return_value = False
        with override_settings(**middleware_setting(django.VERSION,
                                                    ['elasticapm.contrib.django.middleware.TracingMiddleware'])):
            resp = client.get(reverse("render-heavy-template"))
    assert resp.status_code == 200

    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['result'] == 'HTTP 2xx'
    spans = transactions[0]['spans']

    expected_signatures = ['transaction', 'list_users.html',
                           'something_expensive']

    assert spans[1]['name'] == 'list_users.html'

    # Top frame should be inside django rendering
    assert spans[1]['stacktrace'][0]['module'].startswith('django.template')
Example #24
0
def test_stacktraces_have_templates(client, django_elasticapm_client):
    # only Django 1.9+ have the necessary information stored on Node/Template
    # instances when TEMPLATE_DEBUG = False

    TEMPLATE_DEBUG = django.VERSION < (1, 9)

    with mock.patch("elasticapm.traces.TransactionsStore.should_collect") as should_collect:
        should_collect.return_value = False
        TEMPLATES_copy = deepcopy(settings.TEMPLATES)
        TEMPLATES_copy[0]['OPTIONS']['debug'] = TEMPLATE_DEBUG
        with override_settings(
            TEMPLATE_DEBUG=TEMPLATE_DEBUG,
            TEMPLATES=TEMPLATES_copy,
            **middleware_setting(django.VERSION, [
                'elasticapm.contrib.django.middleware.TracingMiddleware'
            ])
        ):
            resp = client.get(reverse("render-heavy-template"))
    assert resp.status_code == 200

    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert len(transactions) == 1
    transaction = transactions[0]
    assert transaction['result'] == 'HTTP 2xx'
    spans = transaction['spans']
    assert len(spans) == 2, [t['name'] for t in spans]

    expected_names = {'list_users.html', 'something_expensive'}

    assert {t['name'] for t in spans} == expected_names

    assert spans[0]['name'] == 'something_expensive'

    # Find the template
    for frame in spans[0]['stacktrace']:
        if frame['lineno'] == 4 and frame['filename'].endswith(
                'django/testapp/templates/list_users.html'
        ):
            break
    else:
        assert False is True, "Template was not found"
Example #25
0
def test_request_metrics_contrib_redirect(django_elasticapm_client, client):
    django_elasticapm_client.instrumentation_store.get_all()  # clear the store

    # enable middleware wrapping
    django_elasticapm_client.config.instrument_django_middleware = True
    from elasticapm.contrib.django.middleware import TracingMiddleware
    TracingMiddleware._elasticapm_instrumented = False

    s = Site.objects.get(pk=1)
    Redirect.objects.create(site=s, old_path='/redirect/me/', new_path='/here/')

    with override_settings(
        **middleware_setting(django.VERSION, [
            'elasticapm.contrib.django.middleware.TracingMiddleware',
            'django.contrib.redirects.middleware.RedirectFallbackMiddleware',
        ])
    ):
        response = client.get('/redirect/me/')

    transactions = django_elasticapm_client.instrumentation_store.get_all()
    assert transactions[0]['name'] == 'GET django.contrib.redirects.middleware.RedirectFallbackMiddleware.process_response'
    assert transactions[0]['result'] == 'HTTP 3xx'
Example #26
0
def client_get(client, url):
    return client.get(url)
Example #27
0
def test_view_exception_elasticapm_debug(django_elasticapm_client, client):
    django_elasticapm_client.config.debug = True
    with override_settings(DEBUG=True):
        with pytest.raises(Exception): client.get(reverse('elasticapm-raise-exc'))
    assert len(django_elasticapm_client.events) == 1
Example #28
0
def test_ignored_exception_is_ignored(django_elasticapm_client, client):
    with pytest.raises(IgnoredException):
        client.get(reverse('elasticapm-ignored-exception'))
    assert len(django_elasticapm_client.events) == 0