44 lines
1.6 KiB
Python
44 lines
1.6 KiB
Python
"""Хук before_send для GlitchTip/Sentry SDK (tradein-local, #396).
|
||
|
||
Redact-ит consumer-PII (client_name / client_phone / client_email и пр.)
|
||
из error events до отправки в GlitchTip — estimator/trade-in flow таскает
|
||
эти поля, а send_default_pii=False их не покрывает (это user-data в
|
||
request.data / extra / contexts, не PII-заголовки).
|
||
"""
|
||
|
||
from __future__ import annotations
|
||
|
||
from typing import Any
|
||
|
||
from sentry_sdk.types import Event
|
||
|
||
_REDACTED = "[REDACTED]"
|
||
# Ключи consumer-PII (нижний регистр; сверка case-insensitive).
|
||
_PII_KEYS = frozenset(
|
||
{"client_name", "client_phone", "client_email", "phone", "email", "name"}
|
||
)
|
||
|
||
|
||
def _scrub(obj: Any) -> None:
|
||
"""Рекурсивно заменить значения PII-ключей в dict на [REDACTED] (in-place)."""
|
||
if isinstance(obj, dict):
|
||
for key, value in obj.items():
|
||
if isinstance(key, str) and key.lower() in _PII_KEYS:
|
||
obj[key] = _REDACTED
|
||
else:
|
||
_scrub(value)
|
||
elif isinstance(obj, list):
|
||
for item in obj:
|
||
_scrub(item)
|
||
|
||
|
||
def scrub_pii_event(event: Event, _hint: dict[str, Any]) -> Event | None:
|
||
"""Redact consumer-PII из error event перед отправкой. Возвращает event (не None)."""
|
||
if not isinstance(event, dict):
|
||
return event
|
||
request = event.get("request")
|
||
if isinstance(request, dict):
|
||
_scrub(request.get("data"))
|
||
_scrub(event.get("extra"))
|
||
_scrub(event.get("contexts"))
|
||
return event
|