Files
breakpilot-compliance/backend-compliance/compliance/services/doc_checks/social_media_checks.py
T
Benjamin Admin fa4fd87102
Build + Deploy / build-admin-compliance (push) Successful in 9s
Build + Deploy / build-backend-compliance (push) Successful in 8s
Build + Deploy / build-ai-sdk (push) Successful in 42s
Build + Deploy / build-developer-portal (push) Successful in 8s
Build + Deploy / build-tts (push) Successful in 7s
Build + Deploy / build-document-crawler (push) Successful in 7s
Build + Deploy / build-dsms-gateway (push) Successful in 8s
Build + Deploy / build-dsms-node (push) Successful in 8s
CI / branch-name (push) Has been skipped
CI / guardrail-integrity (push) Has been skipped
CI / loc-budget (push) Failing after 18s
CI / secret-scan (push) Has been skipped
CI / go-lint (push) Has been skipped
CI / python-lint (push) Has been skipped
CI / nodejs-lint (push) Has been skipped
CI / nodejs-build (push) Successful in 2m57s
CI / dep-audit (push) Has been skipped
CI / sbom-scan (push) Has been skipped
CI / test-go (push) Failing after 49s
CI / test-python-backend (push) Successful in 42s
CI / test-python-document-crawler (push) Successful in 28s
CI / test-python-dsms-gateway (push) Successful in 23s
CI / validate-canonical-controls (push) Successful in 15s
Build + Deploy / trigger-orca (push) Successful in 2m24s
fix: 7 regex bugs from IHK Konstanz ground truth analysis
Fixes based on manual verification of all 30 failed checks:
1. Cookie table: recognize "folgende cookies" + column headers as text
2. Cookie names: add JSESSIONID, cookieinfo, et_id, BT_* patterns
3. Essential justified: match "sitzung zuordnen", "betrieb der website"
4. Social bookmarks: recognize as 2-click alternative
5. DSFA plural: "kanaelen" now matches alongside "kanal"
6. Section splitter: skip-headings no longer lose subsequent text
   (Risikoabwaegung section was cut from DSFA, losing risk scores)
7. Cookie legal basis: accept Art. 6(1)(f) in cookie context

Reduces false positives from 7 to ~1-2 for IHK Konstanz test case.
Ground truth table: zeroclaw/docs/ground-truth-ihk-konstanz.md

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-05-07 14:51:09 +02:00

277 lines
15 KiB
Python

"""
Social Media DSE checks — Art. 26 DSGVO Joint Controller.
Level 1: Pflichtangabe erwaehnt?
Level 2: Pflichtangabe korrekt/vollstaendig?
"""
JOINT_CONTROLLER_CHECKLIST = [
# ── L1: Gemeinsam Verantwortliche ─────────────────────────────────
{
"id": "joint_parties",
"label": "Gemeinsam Verantwortliche benannt (Art. 26(1))",
"level": 1, "parent": None,
"patterns": [
r"gemeinsam.*verantwortlich", r"joint.*controller",
r"gemeinsame\s+verantwortlichkeit",
r"art\.\s*26", r"mitverantwortlich",
r"wir.*(?:und|gemeinsam).*(?:betreiber|facebook|meta|google)",
r"(?:betreiber|netzwerk).*verantwortlich",
],
"severity": "HIGH",
"hint": "Es fehlt der Hinweis auf die gemeinsame Verantwortlichkeit nach Art. 26 DSGVO. Benennen Sie ausdruecklich, dass Sie und die jeweilige Plattform gemeinsam Verantwortliche fuer die Datenverarbeitung sind.",
},
{
"id": "facebook_meta_named",
"label": "Facebook/Meta konkret als Verantwortlicher benannt",
"level": 2, "parent": "joint_parties",
"patterns": [
r"(?:facebook|meta)\s+(?:ireland|platforms|inc)",
r"meta\s+platforms.*(?:verantwortlich|controller|betreiber)",
],
"severity": "MEDIUM",
"hint": "Facebook/Meta ist nicht namentlich als gemeinsam Verantwortlicher aufgefuehrt. Nennen Sie die vollstaendige Firmenbezeichnung (z.B. Meta Platforms Ireland Limited) als Mitverantwortlichen.",
},
# ── L1: Vereinbarung Art. 26 ──────────────────────────────────────
{
"id": "arrangement",
"label": "Vereinbarung nach Art. 26 DSGVO",
"level": 1, "parent": None,
"patterns": [
r"vereinbarung.*art\.\s*26", r"art\.\s*26.*vereinbarung",
r"page\s*controller", r"fanpage", r"insights",
r"gemeinsame.*verantwortung.*(?:vertrag|vereinbarung)",
r"addendum|nachtrag|seiten.*insights",
],
"severity": "HIGH",
"hint": "Es fehlt ein Verweis auf die Vereinbarung nach Art. 26 DSGVO zwischen Ihnen und der Plattform. Erwaehnen Sie die bestehende Vereinbarung (z.B. Page Controller Addendum bei Facebook) und deren wesentlichen Inhalt.",
},
{
"id": "insights_referenced",
"label": "Seiteninsights / Page Insights erwaehnt",
"level": 2, "parent": "arrangement",
"patterns": [
r"(?:seiten[\-\s]?)?insights",
r"page\s+insights",
r"(?:statistik|nutzungsstatistik).*(?:facebook|meta|fanpage|seite)",
],
"severity": "MEDIUM",
"hint": "Die Verarbeitung von Seiten-Insights bzw. Page Insights wird nicht erwaehnt. Erlaeutern Sie, dass bei Nutzung Ihrer Social-Media-Seite Insights-Daten erhoben und verarbeitet werden.",
},
{
"id": "page_controller_addendum",
"label": "Page Controller Addendum / Seiten-Insights-Ergaenzung",
"level": 2, "parent": "arrangement",
"patterns": [
r"page\s+controller\s+addendum",
r"seiten[\-\s]?insights[\-\s]?erg(?:ae|ä)nzung",
r"(?:addendum|nachtrag|erg(?:ae|ä)nzung).*(?:controller|verantwortlich)",
],
"severity": "LOW",
"hint": "Das Page Controller Addendum (bzw. die Seiten-Insights-Ergaenzung) wird nicht namentlich erwaehnt. Verweisen Sie konkret auf das Addendum und verlinken Sie es, damit Betroffene die Vereinbarung nachvollziehen koennen.",
},
# ── L1: Anlaufstelle ──────────────────────────────────────────────
{
"id": "contact_point",
"label": "Anlaufstelle fuer Betroffene (Art. 26(1) S.3)",
"level": 1, "parent": None,
"patterns": [
r"anlaufstelle", r"kontaktstelle",
r"ansprechpartner.*betroffene",
r"rechte.*(?:gegen(?:ue|ü)ber)\s+(?:uns|beiden)",
r"rechte.*geltend\s+machen",
r"wenden\s+sie\s+sich",
],
"severity": "MEDIUM",
"hint": "Es fehlt eine Anlaufstelle fuer Betroffene gemaess Art. 26(1) S.3 DSGVO. Geben Sie an, an wen sich Betroffene zur Wahrnehmung ihrer Rechte wenden koennen.",
},
{
"id": "contact_both_parties",
"label": "Kontaktdaten beider Verantwortlicher",
"level": 2, "parent": "contact_point",
"patterns": [
r"(?:sowohl|beide).*(?:kontakt|wenden|geltend)",
r"(?:uns|bei\s+uns).*(?:als\s+auch|oder|und).*(?:facebook|meta|google|plattform)",
r"(?:facebook|meta|google|plattform).*(?:als\s+auch|oder|und).*(?:uns|bei\s+uns)",
],
"severity": "LOW",
"hint": "Die Kontaktdaten beider Verantwortlicher sind nicht vollstaendig angegeben. Stellen Sie klar, dass Betroffene ihre Rechte sowohl bei Ihnen als auch bei der Plattform geltend machen koennen, und nennen Sie die jeweiligen Kontaktwege.",
},
# ── L1: Verarbeitungsaufteilung ───────────────────────────────────
{
"id": "processing_split",
"label": "Verarbeitungsaufteilung (wer macht was)",
"level": 1, "parent": None,
"patterns": [
r"(?:wir|betreiber).*(?:verarbeiten|erheben|nutzen).*(?:daten|informationen)",
r"(?:facebook|meta|google|youtube|instagram|linkedin|twitter|x\.com).*(?:verarbeit|erhebt|nutzt|speichert)",
r"bei\s+besuch\s+(?:unserer|der)\s+(?:seite|fanpage|profil)",
r"(?:nutzungsstatistik|statistik|insight).*(?:betreiber|netzwerk)",
],
"severity": "HIGH",
"hint": "Es fehlt eine Beschreibung, welche Datenverarbeitungen Sie und welche die Plattform vornimmt. Erlaeutern Sie die Aufgabenverteilung (z.B. wer Insights-Daten erhebt und wer sie auswertet).",
},
# ── L1: Datenkategorien ───────────────────────────────────────────
{
"id": "social_data_types",
"label": "Kategorien verarbeiteter Daten",
"level": 1, "parent": None,
"patterns": [
r"(?:nutzungsstatistik|insight|reichweite|interaktion|klick|aufruf)",
r"(?:ip.?adresse|standort|browser|ger(?:ae|ä)t|alter|geschlecht)",
r"(?:personenbezogen|daten).*(?:social|netzwerk|plattform)",
r"(?:nutzername|beitr(?:ae|ä)g|profil|like|kommentar)",
],
"severity": "HIGH",
"hint": "Die Kategorien der verarbeiteten Daten sind nicht aufgefuehrt. Listen Sie auf, welche Daten verarbeitet werden (z.B. IP-Adresse, Standort, Geraetedaten, Interaktionen, demografische Daten).",
},
# ── L1: Plattformen ───────────────────────────────────────────────
{
"id": "platforms",
"label": "Auflistung der genutzten Plattformen",
"level": 1, "parent": None,
"patterns": [
r"(?:facebook|instagram|youtube|twitter|x\.com|linkedin|xing|tiktok)",
r"(?:kan(?:ae|ä)le|plattform|netzwerk|profil|account|auftritte).*(?:social|medien)",
r"social\s*media.*(?:angebot|pr(?:ae|ä)senz|auftritte)",
],
"severity": "MEDIUM",
"hint": "Die genutzten Social-Media-Plattformen werden nicht aufgelistet. Fuehren Sie alle Plattformen namentlich auf, auf denen Sie Praesenzen betreiben (z.B. Facebook, Instagram, LinkedIn, YouTube).",
},
{
"id": "platform_dse_links",
"label": "Links zu Datenschutzerklaerungen der Plattformen",
"level": 2, "parent": "platforms",
"patterns": [
r"(?:datenschutz|privacy).*(?:facebook|meta|google|youtube|instagram|linkedin|twitter)",
r"(?:facebook|meta|google|youtube|instagram|linkedin|twitter).*(?:datenschutz|privacy)",
r"(?:privacy\s+policy|datenschutzerkl(?:ae|ä)rung).*(?:finden\s+sie|abrufbar|unter)",
],
"severity": "LOW",
"hint": "Es fehlen Links zu den Datenschutzerklaerungen der einzelnen Plattformen. Verlinken Sie die jeweilige Privacy Policy (z.B. von Meta, Google, LinkedIn), damit Nutzer sich dort informieren koennen.",
},
# ── L1: Drittlandtransfer ─────────────────────────────────────────
{
"id": "third_country",
"label": "Drittlandtransfer (USA bei Social Media)",
"level": 1, "parent": None,
"patterns": [
r"(?:usa|vereinigte\s+staaten|drittland|drittstaaten)",
r"privacy\s+shield|data\s+privacy\s+framework|angemessenheitsbeschluss",
r"standardvertragsklausel|standard.*contractual",
r"(?:(?:ue|ü)bermittlung|(?:ueber|über)mittlung).*(?:usa|drittland|au(?:ss|ß)erhalb)",
],
"severity": "MEDIUM",
"hint": "Es fehlt ein Hinweis auf den Drittlandtransfer in die USA. Informieren Sie darueber, dass Daten in die USA uebermittelt werden, und nennen Sie die Rechtsgrundlage dafuer (z.B. Angemessenheitsbeschluss, Standardvertragsklauseln).",
},
{
"id": "usa_transfer_scc",
"label": "Standardvertragsklauseln (SCC) fuer US-Transfer",
"level": 2, "parent": "third_country",
"patterns": [
r"standard\s*vertragsklausel|scc",
r"standard\s+contractual\s+clause",
],
"severity": "MEDIUM",
"hint": "Standardvertragsklauseln (SCC) als Garantie fuer den US-Datentransfer werden nicht erwaehnt. Falls SCC als Rechtsgrundlage genutzt werden, fuehren Sie diese ausdruecklich auf.",
},
{
"id": "usa_transfer_dpf",
"label": "Data Privacy Framework (DPF) fuer US-Transfer",
"level": 2, "parent": "third_country",
"patterns": [
r"data\s+privacy\s+framework|dpf",
r"angemessenheitsbeschluss.*(?:usa|us|amerika)",
r"adequacy\s+decision",
],
"severity": "LOW",
"hint": "Das EU-US Data Privacy Framework (DPF) wird nicht als Transfergrundlage erwaehnt. Falls sich die Plattform auf den Angemessenheitsbeschluss stuetzt, erwaehnen Sie dies und verweisen Sie auf die DPF-Zertifizierung.",
},
# ── L1: Rechtsgrundlage ───────────────────────────────────────────
{
"id": "legal_basis",
"label": "Rechtsgrundlage (Art. 6 DSGVO)",
"level": 1, "parent": None,
"patterns": [
r"rechtsgrundlage", r"art\.\s*6",
r"berechtigtes\s+interesse",
r"einwilligung.*art\.\s*6", r"lit\.\s*[a-f]",
],
"severity": "MEDIUM",
"hint": "Die Rechtsgrundlage fuer die Datenverarbeitung nach Art. 6 DSGVO fehlt. Nennen Sie die einschlaegige Rechtsgrundlage (z.B. berechtigtes Interesse nach Art. 6(1) lit. f oder Einwilligung nach Art. 6(1) lit. a).",
},
{
"id": "legal_basis_specific_lit",
"label": "Konkretes Art. 6(1) lit. angegeben",
"level": 2, "parent": "legal_basis",
"patterns": [
r"art\.\s*6\s*(?:abs\.\s*)?1\s*(?:s\.\s*1\s*)?(?:lit\.\s*)?[a-f]",
],
"severity": "LOW",
"hint": "Der konkrete Buchstabe in Art. 6(1) DSGVO ist nicht angegeben. Nennen Sie den spezifischen Erlaubnistatbestand (z.B. lit. a fuer Einwilligung oder lit. f fuer berechtigtes Interesse).",
},
# ── L1: Betroffenenrechte ─────────────────────────────────────────
{
"id": "rights",
"label": "Betroffenenrechte (Art. 15-21)",
"level": 1, "parent": None,
"patterns": [
r"recht\s+auf\s+auskunft", r"recht\s+auf\s+l(?:oe|ö)schung",
r"art\.\s*1[5-9]", r"betroffenenrecht",
r"ihre\s+rechte", r"rechte.*betroffene",
r"widerspruchsrecht",
],
"severity": "MEDIUM",
"hint": "Die Betroffenenrechte nach Art. 15-21 DSGVO sind nicht aufgefuehrt. Listen Sie die Rechte auf (Auskunft, Berichtigung, Loeschung, Einschraenkung, Datenuebertragbarkeit, Widerspruch) und erklaeren Sie, wie Betroffene diese ausueben koennen.",
},
{
"id": "opt_out_social",
"label": "Opt-Out-Moeglichkeit fuer Social-Media-Tracking",
"level": 2, "parent": "rights",
"patterns": [
r"(?:opt[\-\s]?out|widerspruch|deaktivieren).*(?:social|facebook|tracking|insight)",
r"(?:social|facebook|tracking|insight).*(?:opt[\-\s]?out|widerspruch|deaktivieren)",
r"(?:abmelden|abschalten).*(?:tracking|statistik|insight)",
],
"severity": "LOW",
"hint": "Eine konkrete Opt-Out-Moeglichkeit fuer das Social-Media-Tracking fehlt. Beschreiben Sie, wie Nutzer dem Tracking widersprechen oder es deaktivieren koennen (z.B. ueber Plattform-Einstellungen oder Cookie-Opt-Out).",
},
# ── L1: Social Bookmarks vs Plugins ───────────────────────────────
{
"id": "social_bookmarks",
"label": "Hinweis auf Social Bookmarks vs. Plugins",
"level": 1, "parent": None,
"patterns": [
r"social\s*(?:bookmark|plugin|button|widget)",
r"(?:kein|keine).*(?:plugin|widget|button).*(?:gesetzt|eingebunden|geladen)",
r"(?:link|verweis|weiterleitung).*(?:dienst|anbieter|netzwerk)",
],
"severity": "MEDIUM",
"hint": "Es fehlt ein Hinweis, ob Social-Media-Plugins oder nur einfache Links (Bookmarks) eingebunden sind. Stellen Sie klar, ob beim Seitenaufruf bereits Daten an die Plattformen uebertragen werden oder erst nach Klick.",
},
{
"id": "two_click_solution",
"label": "2-Klick-Loesung oder vergleichbare Technik",
"level": 2, "parent": "social_bookmarks",
"patterns": [
r"(?:zwei|2)[\-\s]?klick",
r"(?:shariff|share[\-\s]?buttons?\s+ohne\s+tracking)",
r"(?:erst|nur)\s+(?:bei|nach|durch)\s+(?:klick|aktivierung).*(?:daten|verbindung)",
r"social\s*bookmark",
r"(?:kein|keine)\s+(?:social[\-\s]?media[\-\s]?)?plugin",
r"(?:link|verweis|grafik).*(?:weitergeleitet|weiterleitung)",
],
"severity": "LOW",
"hint": "Erlaeutern Sie die eingesetzte datenschutzfreundliche Technik: z.B. Social Bookmarks (reine Links ohne automatische Datenuebertragung), 2-Klick-Loesung oder Shariff-Buttons.",
},
]