Skip to content

Disable metrics if gevent is used #2688

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 12 additions & 7 deletions sentry_sdk/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
get_default_release,
handle_in_app,
logger,
is_gevent,
)
from sentry_sdk.serializer import serialize
from sentry_sdk.tracing import trace, has_tracing_enabled
Expand Down Expand Up @@ -250,14 +251,18 @@ def _capture_envelope(envelope):
self.metrics_aggregator = None # type: Optional[MetricsAggregator]
experiments = self.options.get("_experiments", {})
if experiments.get("enable_metrics", True):
from sentry_sdk.metrics import MetricsAggregator
if is_gevent():
logger.warning("Metrics currently not supported with gevent.")

self.metrics_aggregator = MetricsAggregator(
capture_func=_capture_envelope,
enable_code_locations=bool(
experiments.get("metric_code_locations", True)
),
)
else:
from sentry_sdk.metrics import MetricsAggregator

self.metrics_aggregator = MetricsAggregator(
capture_func=_capture_envelope,
enable_code_locations=bool(
experiments.get("metric_code_locations", True)
),
)

max_request_body_size = ("always", "never", "small", "medium")
if self.options["max_request_body_size"] not in max_request_body_size:
Expand Down
15 changes: 15 additions & 0 deletions sentry_sdk/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -1741,3 +1741,18 @@ def now():
def now():
# type: () -> float
return time.perf_counter()


try:
from gevent.monkey import is_module_patched
except ImportError:

def is_module_patched(*args, **kwargs):
# type: (*Any, **Any) -> bool
# unable to import from gevent means no modules have been patched
return False


def is_gevent():
# type: () -> bool
return is_module_patched("threading") or is_module_patched("_thread")
30 changes: 30 additions & 0 deletions tests/test_metrics.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,13 @@
except ImportError:
import mock # python < 3.3

try:
import gevent
except ImportError:
gevent = None

requires_gevent = pytest.mark.skipif(gevent is None, reason="gevent not enabled")


def parse_metrics(bytes):
rv = []
Expand Down Expand Up @@ -947,3 +954,26 @@ def bad_capture_envelope(*args, **kwargs):
m = parse_metrics(envelope.items[0].payload.get_bytes())
assert len(m) == 1
assert m[0][1] == "counter@none"


@pytest.mark.forked
@requires_gevent
def test_no_metrics_with_gevent(sentry_init, capture_envelopes):
from gevent import monkey

monkey.patch_all()

sentry_init(
release="fun-release",
environment="not-fun-env",
_experiments={"enable_metrics": True, "metric_code_locations": True},
)
ts = time.time()
envelopes = capture_envelopes()

metrics.incr("foobar", 1.0, tags={"foo": "bar", "blub": "blah"}, timestamp=ts)
metrics.incr("foobar", 2.0, tags={"foo": "bar", "blub": "blah"}, timestamp=ts)
Hub.current.flush()

assert Hub.current.client.metrics_aggregator is None
assert len(envelopes) == 0