Skip to content

Commit

Permalink
remove-event-processor (#17)
Browse files Browse the repository at this point in the history
* remove-event-processor

* bump version

Co-authored-by: Matin Tamizi <[email protected]>
  • Loading branch information
Gleekzone and matin authored Aug 26, 2020
1 parent ad8caea commit 0cd3163
Show file tree
Hide file tree
Showing 5 changed files with 53 additions and 77 deletions.
83 changes: 13 additions & 70 deletions sentry_chalice/sentry_chalice.py
Original file line number Diff line number Diff line change
@@ -1,26 +1,14 @@
import sys
import traceback
from datetime import datetime

import chalice
from chalice import Chalice, ChaliceViewError, Response
from chalice.app import EventSourceHandler as ChaliceEventSourceHandler
from sentry_sdk._compat import reraise
from sentry_sdk._types import MYPY
from sentry_sdk.hub import Hub, _should_send_default_pii
from sentry_sdk.hub import Hub
from sentry_sdk.integrations import Integration
from sentry_sdk.integrations._wsgi_common import _filter_headers
from sentry_sdk.integrations.aws_lambda import _get_cloudwatch_logs_url
from sentry_sdk.utils import (
AnnotatedValue,
capture_internal_exceptions,
event_from_exception,
)

if MYPY:
from typing import Any, Optional

from sentry_sdk._types import Event, EventProcessor, Hint
from sentry_sdk.integrations.aws_lambda import _make_request_event_processor
from sentry_sdk.utils import capture_internal_exceptions, event_from_exception


class EventSourceHandler(ChaliceEventSourceHandler):
Expand All @@ -33,8 +21,11 @@ def __call__(self, event, context):
event_obj = self.event_class(event, context)
return self.func(event_obj)
except Exception:
configured_time = context.get_remaining_time_in_millis()
scope.add_event_processor(
_make_request_event_processor(event, context)
_make_request_event_processor(
event, context, configured_time
)
)
exc_info = sys.exc_info()
event, hint = event_from_exception(
Expand Down Expand Up @@ -67,10 +58,15 @@ def _get_view_function_response(app, view_function, function_args):
hub.flush()
except Exception:
with capture_internal_exceptions():
configured_time = (
app.lambda_context.get_remaining_time_in_millis()
)
scope.transaction = app.lambda_context.function_name
scope.add_event_processor(
_make_request_event_processor(
app.current_request, app.lambda_context
app.current_request,
app.lambda_context,
configured_time,
)
)
exc_info = sys.exc_info()
Expand Down Expand Up @@ -110,56 +106,3 @@ def setup_once():
Chalice._get_view_function_response = _get_view_function_response
# for everything else (like events)
chalice.app.EventSourceHandler = EventSourceHandler


def _make_request_event_processor(current_request, lambda_context):
# type: (Any, Any) -> EventProcessor
start_time = datetime.now()

def event_processor(event, hint, start_time=start_time):
# type: (Event, Hint, datetime) -> Optional[Event]

extra = event.setdefault("extra", {})

extra["Chalice-lambda"] = {
"function_name": lambda_context.function_name,
"function_version": lambda_context.function_version,
"Lambda ARN": lambda_context.invoked_function_arn,
"aws_request_id": lambda_context.aws_request_id,
}

extra["cloudwatch info"] = {
"url": _get_cloudwatch_logs_url(lambda_context, start_time),
"log_group": lambda_context.log_group_name,
"log_stream": lambda_context.log_stream_name,
}

request_info = event.get("request", {})

request_info["method"] = current_request.context["httpMethod"]

request_info["query_string"] = current_request.query_params

request_info["headers"] = _filter_headers(current_request.headers)

if current_request._body is None:
request_info["data"] = AnnotatedValue(
"", {"rem": [["!raw", "x", 0, 0]]}
)

if _should_send_default_pii():
user_info = event.setdefault("user", {})

id = current_request.context["identity"]["userArn"]
if id is not None:
user_info.setdefault("id", id)

ip = current_request.context["identity"]["sourceIp"]
if ip is not None:
user_info.setdefault("ip_address", ip)

event["request"] = request_info

return event

return event_processor
2 changes: 1 addition & 1 deletion sentry_chalice/version.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = '0.3.1'
__version__ = '0.3.2'
1 change: 0 additions & 1 deletion setup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,4 @@ ignore_missing_imports = true
[coverage:report]
precision = 2
exclude_lines =
if MYPY:
__version__ =
8 changes: 8 additions & 0 deletions tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -54,3 +54,11 @@ def append_envelope(envelope):
return events

return inner


@pytest.fixture
def lambda_context_args():
# LambdaContext has several positional args before the ones that we
# care about for the timing tests, this gives reasonable defaults for
# those arguments. Taken from chalice tests
return ['lambda_name', 256]
36 changes: 31 additions & 5 deletions tests/test_sentry_chalice.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,26 @@
import pytest
from chalice.local import LambdaContext
from chalice.test import Client


class FakeTimeSource(object):
# taken from chalice tests
def __init__(self, times):
"""Create a fake source of second-precision time.
:type time: List
:param time: List of times that the time source should return in the
order it should return them. These should be in seconds.
"""
self._times = times

def time(self):
"""Get the next time.
This is for mimicing the Clock interface used in local.
"""
time = self._times.pop(0)
return time


def test_exception_boom(app) -> None:
with Client(app) as client:
response = client.http.get('/boom')
Expand All @@ -22,16 +41,23 @@ def test_has_request(app, capture_events):
assert response.status_code == 500

(event,) = events
assert event["transaction"] == "api_handler"
assert "data" not in event["request"]
assert event["request"]["headers"] == {}

assert event["level"] == "error"
(exception,) = event["exception"]["values"]
assert exception["type"] == "Exception"

def test_scheduled_event(app):

def test_scheduled_event(app, lambda_context_args):
@app.schedule('rate(1 minutes)')
def every_hour(event):
raise Exception('only chalice event!')

time_source = FakeTimeSource([0, 5])
context = LambdaContext(
*lambda_context_args, max_runtime_ms=10000, time_source=time_source
)
# time_remaining = context.get_remaining_time_in_millis()

lambda_event = {
"version": "0",
"account": "123456789012",
Expand All @@ -46,7 +72,7 @@ def every_hour(event):
],
}
with pytest.raises(Exception) as exc_info:
every_hour(lambda_event, context=None)
every_hour(lambda_event, context=context)
assert str(exc_info.value) == 'only chalice event!'


Expand Down

0 comments on commit 0cd3163

Please sign in to comment.