Skip to content

Commit 0c9148f

Browse files
authored
fix(crashtracker): fix payload from v1 into v2 (#6275)
Co-authored-by: anais.raison <anais.raison@datadoghq.com>
1 parent 355a45a commit 0c9148f

File tree

1 file changed

+50
-5
lines changed

1 file changed

+50
-5
lines changed

tests/parametric/test_crashtracking.py

Lines changed: 50 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,15 @@ def test_report_crash(self, test_agent: TestAgentAPI, test_library: APMLibrary):
1717

1818
while True:
1919
event = test_agent.wait_for_telemetry_event("logs", wait_loops=400)
20-
if event is None or "is_crash_ping:true" not in event["payload"][0]["tags"]:
20+
# Handling both v1 and v2 of the crashtracking payload so that we can
21+
# update to v2 without breaking the test.
22+
if isinstance(event.get("payload"), list):
23+
if "is_crash_ping:true" not in event["payload"][0]["tags"]:
24+
self.assert_crash_report_v1(test_library, event)
25+
break
26+
elif "is_crash_ping:true" not in event["payload"]["logs"][0]["tags"]:
27+
self.assert_crash_report_v2(test_library, event)
2128
break
22-
self.assert_crash_report(test_library, event)
2329

2430
@pytest.mark.parametrize("library_env", [{"DD_CRASHTRACKING_ENABLED": "false"}])
2531
def test_disable_crashtracking(self, test_agent: TestAgentAPI, test_library: APMLibrary):
@@ -31,8 +37,12 @@ def test_disable_crashtracking(self, test_agent: TestAgentAPI, test_library: APM
3137
event = json.loads(base64.b64decode(req["body"]))
3238

3339
if event["request_type"] == "logs":
34-
with pytest.raises(AssertionError):
35-
self.assert_crash_report(test_library, event)
40+
if isinstance(event.get("payload"), list):
41+
with pytest.raises(AssertionError):
42+
self.assert_crash_report_v1(test_library, event)
43+
else: # If payload is a dict
44+
with pytest.raises(AssertionError):
45+
self.assert_crash_report_v2(test_library, event)
3646

3747
@pytest.mark.parametrize("library_env", [{"DD_CRASHTRACKING_ENABLED": "true"}])
3848
def test_telemetry_timeout(self, test_agent: TestAgentAPI, test_library: APMLibrary):
@@ -46,7 +56,7 @@ def test_telemetry_timeout(self, test_agent: TestAgentAPI, test_library: APMLibr
4656
finally:
4757
test_agent.set_trace_delay(0)
4858

49-
def assert_crash_report(self, test_library: APMLibrary, event: dict):
59+
def assert_crash_report_v1(self, test_library: APMLibrary, event: dict):
5060
logger.debug(f"event: {json.dumps(event, indent=2)}")
5161

5262
assert isinstance(event.get("payload"), list), event.get("payload")
@@ -79,3 +89,38 @@ def assert_crash_report(self, test_library: APMLibrary, event: dict):
7989
assert tags_dict["si_signo"] == expected_signal_value
8090
else:
8191
raise AssertionError("signum/si_signo not found in tags_dict")
92+
93+
def assert_crash_report_v2(self, test_library: APMLibrary, event: dict):
94+
logger.debug(f"event: {json.dumps(event, indent=2)}")
95+
96+
assert isinstance(event.get("payload"), dict), event.get("payload")
97+
assert isinstance(event["payload"].get("logs"), list), event["payload"].get("logs")
98+
assert event["payload"]["logs"], event["payload"]["logs"]
99+
assert isinstance(event["payload"]["logs"][0], dict), event["payload"]["logs"][0]
100+
assert "tags" in event["payload"]["logs"][0]
101+
102+
tags = event["payload"]["logs"][0]["tags"]
103+
tags_dict = dict(item.split(":") for item in tags.split(","))
104+
logger.debug(f"tags_dict: {json.dumps(tags_dict, indent=2)}")
105+
106+
# Until the crash tracking RFC is out, there is no standard way to identify crash reports.
107+
# Most client libraries are using libdatadog so tesing signum tag would work,
108+
# but Java isn't so we end up with testing for severity tag.
109+
if test_library.lang == "java":
110+
assert "severity" in tags_dict, tags_dict
111+
assert tags_dict["severity"] == "crash", tags_dict
112+
else:
113+
# those values are defined in python's module signal. But it's more clear to have this defined here
114+
SIGABRT = 6 # noqa: N806
115+
SIGSEGV = 11 # noqa: N806
116+
117+
# According to the RFC, si_signo should be set to 11 for SIGSEGV
118+
# though, it's difficult for .NET to simulate a segfault, so SIGABRT is used instead
119+
expected_signal_value = f"{SIGABRT}" if test_library.lang == "dotnet" else f"{SIGSEGV}"
120+
121+
if "signum" in tags_dict:
122+
assert tags_dict["signum"] == expected_signal_value
123+
elif "si_signo" in tags_dict:
124+
assert tags_dict["si_signo"] == expected_signal_value
125+
else:
126+
raise AssertionError("signum/si_signo not found in tags_dict")

0 commit comments

Comments
 (0)