[{"data":1,"prerenderedAt":807},["ShallowReactive",2],{"blog-llm-output-guardrails-moderation-de":3},{"slug":4,"published":5,"minutes":6,"category":7,"tags":8,"keywords":14,"about":27,"sources":35,"cover":66,"og":67,"expertise":68,"locales":69,"lang":71,"title":73,"description":74,"coverAlt":75,"metaTitle":76,"takeaways":77,"faq":83,"toc":99,"blocks":133,"others":525},"llm-output-guardrails-moderation","2026-10-17",13,"security",[9,10,11,12,13],"LLM security","Guardrails","Content moderation","OWASP","Output validation",[15,16,17,18,19,20,21,22,23,24,25,26],"llm output guardrails","improper output handling llm","owasp llm05","openai moderation api","omni-moderation-latest","llama guard 4","nemo guardrails streaming","markdown image exfiltration","sanitize llm output html","groundedness detection","llm content moderation production","output rails",[28,30,33],{"name":11,"url":29},"https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FContent_moderation",{"name":31,"url":32},"Cross-site scripting","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FCross-site_scripting",{"name":12,"url":34},"https:\u002F\u002Fowasp.org\u002F",[36,39,42,45,48,51,54,57,60,63],{"title":37,"url":38},"OWASP GenAI Security Project: LLM05:2025 Improper Output Handling","https:\u002F\u002Fgenai.owasp.org\u002Fllmrisk\u002Fllm052025-improper-output-handling\u002F",{"title":40,"url":41},"OpenAI API Docs: Moderation","https:\u002F\u002Fplatform.openai.com\u002Fdocs\u002Fguides\u002Fmoderation",{"title":43,"url":44},"Meta: Llama Guard 4 model card and prompt formats","https:\u002F\u002Fwww.llama.com\u002Fdocs\u002Fmodel-cards-and-prompt-formats\u002Fllama-guard-4\u002F",{"title":46,"url":47},"NVIDIA NeMo Guardrails: Output rail streaming configuration","https:\u002F\u002Fdocs.nvidia.com\u002Fnemo\u002Fguardrails\u002Fconfigure-guardrails\u002Fyaml-schema\u002Fstreaming\u002Foutput-rail-streaming.md",{"title":49,"url":50},"Microsoft Learn: Prompt Shields in Azure AI Content Safety","https:\u002F\u002Flearn.microsoft.com\u002Fen-us\u002Fazure\u002Fai-services\u002Fcontent-safety\u002Fconcepts\u002Fjailbreak-detection",{"title":52,"url":53},"Microsoft Learn: Groundedness detection in Azure AI Content Safety","https:\u002F\u002Flearn.microsoft.com\u002Fen-us\u002Fazure\u002Fai-services\u002Fcontent-safety\u002Fconcepts\u002Fgroundedness",{"title":55,"url":56},"Microsoft Learn: Protected material detection in Azure AI Content Safety","https:\u002F\u002Flearn.microsoft.com\u002Fen-us\u002Fazure\u002Fai-services\u002Fcontent-safety\u002Fconcepts\u002Fprotected-material",{"title":58,"url":59},"Guardrails AI documentation","https:\u002F\u002Fwww.guardrailsai.com\u002Fdocs",{"title":61,"url":62},"Vue.js docs: Security best practices","https:\u002F\u002Fvuejs.org\u002Fguide\u002Fbest-practices\u002Fsecurity.html",{"title":64,"url":65},"Simon Willison: Remote prompt injection in GitLab Duo leads to source code theft","https:\u002F\u002Fsimonwillison.net\u002F2025\u002FMay\u002F23\u002Fremote-prompt-injection-in-gitlab-duo\u002F","\u002Fimages\u002Fblog\u002Fllm-output-guardrails-moderation\u002Fcover.webp","\u002Fimages\u002Fblog\u002Fllm-output-guardrails-moderation\u002Fog.jpg","ai-engineer",[70,71,72],"en","de","hu","Output-Guardrails für LLMs: Moderation, sicheres Rendern und Validierung, bevor etwas passiert","Was nach der Modellantwort zu prüfen ist: sicheres Markdown-Rendering, Schema-Prüfung vor Aktionen, Moderations-Klassifikatoren, Streaming und Groundedness.","Drei enger werdende Rahmen als Trichter gestapelt, Punkte fallen zu einer Schale neben einem Schloss.","Output-Guardrails und Moderation für LLMs · Balázs Csorba",[78,79,80,81,82],"OWASP LLM05:2025 behandelt Modellausgaben als nicht vertrauenswürdige Eingabe für das nächste System: Browser, Datenbank, Shell oder Mail-Vorlage.","Die meisten echten Output-Vorfälle sind Rendering- und Aktionsfehler, nicht anstößiger Text. Zuerst Markdown bereinigen und Bilder und Links einschränken.","Strukturierte Ausgaben gegen Schema und Allowlist prüfen, bevor sie eine Aktion auslösen; nie an eval, eine Shell oder zusammengesetztes SQL übergeben.","Moderations-Klassifikatoren wie omni-moderation-latest oder Llama Guard 4 liefern Signale, keine Urteile; Schwellen und Aktionen legen Sie pro Kategorie fest.","Streaming verschiebt den Kompromiss: Entweder sieht der Nutzer einen Chunk vor der Sperre, oder jeder Chunk kostet die Latenz der Prüfung.",[84,87,90,93,96],{"q":85,"a":86},"Was ist Improper Output Handling?","Das ist der Eintrag LLM05:2025 der OWASP LLM Top 10: unzureichende Validierung, Bereinigung und Behandlung von Modellausgaben, bevor sie an andere Komponenten gehen. Typische Folgen sind XSS im Browser, SQL-Injection, Path Traversal oder Remote Code Execution im Backend.",{"q":88,"a":89},"Reicht der OpenAI-Moderation-Endpunkt als Output-Guardrail?","Er deckt Kategorien der Inhaltssicherheit ab, etwa Hass, Belästigung, Selbstverletzung, sexuelle Inhalte, Gewalt und Anleitungen zu illegalen Handlungen, und ist kostenlos. Er prüft nicht, ob HTML sicher gerendert werden kann, ob eine Antwort belegt ist oder ob ein Tool-Aufruf erlaubt ist. Er ist eine Schicht von mehreren.",{"q":91,"a":92},"Kann ich eine gestreamte Antwort moderieren?","Ja, aber Sie müssen sich entscheiden. OpenAI liefert Inline-Moderationswerte erst, wenn die vollständige Ausgabe vorliegt. NeMo Guardrails prüft standardmäßig Chunks von 200 Tokens und streamt jeden Chunk entweder vor der Prüfung oder hält ihn zurück, bis sie bestanden ist.",{"q":94,"a":95},"Soll ich markierte Ausgaben blockieren oder umschreiben?","Das hängt von der Kategorie ab. Bei klaren Sicherheitsverstößen blockieren und durch eine feste Nachricht ersetzen, bei geleakten personenbezogenen Daten oder Secrets schwärzen, Grenzfälle und geschäftskritische Fälle an einen Menschen geben. Jede Entscheidung mit den Werten protokollieren, um Schwellen nachzujustieren.",{"q":97,"a":98},"Wie verhindere ich Exfiltration über Markdown-Bilder?","Keine Bilder oder Links auf beliebige Domains aus Modellausgaben rendern. Eine Allowlist von Hosts verwenden, alles andere serverseitig entfernen oder umschreiben, rohes HTML im Markdown-Renderer abschalten und eine strikte Content Security Policy setzen.",[100,103,106,109,112,115,118,121,124,127,130],{"id":101,"title":102},"output-is-untrusted-input","Modellausgabe ist nicht vertrauenswürdige Eingabe für das nächste System",{"id":104,"title":105},"four-jobs","Vier verschiedene Aufgaben, die alle Guardrails heißen",{"id":107,"title":108},"render-safely","Markdown so rendern, als hätte ein Angreifer es geschrieben",{"id":110,"title":111},"validate-before-acting","Strukturierte Ausgaben validieren, bevor sie etwas auslösen",{"id":113,"title":114},"moderation-classifiers","Moderations-Klassifikatoren: was die gängigen Optionen prüfen",{"id":116,"title":117},"streaming","Streaming: zuerst anzeigen oder zuerst prüfen",{"id":119,"title":120},"groundedness-and-leakage","Prüfung auf Belegbarkeit und Datenabfluss",{"id":122,"title":123},"actions-and-thresholds","Blockieren, schwärzen, umschreiben oder eskalieren",{"id":125,"title":126},"layered-pipeline","Alles zusammen in einer Server-Route",{"id":128,"title":129},"testing-guardrails","Guardrails testen wie jede andere Funktion",{"id":131,"title":132},"sources","Quellen",[134,144,147,150,162,165,166,169,207,210,211,214,229,231,237,238,246,267,274,275,278,308,318,328,335,336,351,368,373,374,381,389,390,393,437,444,445,448,455,457,468,469,472,487,490,491],{"type":135,"content":136},"paragraph",[137,138,143],"Die meisten Diskussionen über Guardrails beginnen bei der Eingabe: Prompt Injection, Jailbreaks, Nutzer, die Dinge verlangen, die sie nicht bekommen sollen. Diese Hälfte ist wichtig, darüber habe ich in ",{"tag":139,"to":140,"children":141},"link","\u002Fblog\u002Fprompt-injection-lethal-trifecta-patterns",[142],"Abwehr von Prompt Injection"," geschrieben. Hier geht es um die andere Hälfte. Sobald das Modell geantwortet hat, landet sein Text irgendwo: in einer Chat-Blase, die als Markdown gerendert wird, in einem JSON-Parser, der eine Gutschrift auslöst, in einer Mail-Vorlage, in einer SQL-Abfrage. Jedes dieser Ziele hat eigene Regeln dafür, was sicher ist, und das Modell kennt keine davon.",{"type":135,"content":145},[146],"Die OWASP Top 10 für LLM-Anwendungen nennen dieses Risiko LLM05:2025 Improper Output Handling. Im Folgenden beschreibe ich, wie ich Output-Prüfungen in produktiven Funktionen aufbaue: was wie gerendert wird, was vor einer Aktion validiert wird, wo Moderations-Klassifikatoren hingehören, was Streaming daran ändert und wie man zwischen Blockieren, Umschreiben und Eskalieren entscheidet.",{"type":148,"level":149,"id":101,"text":102},"heading",2,{"type":135,"content":151},[152,153,157,158,161],"OWASP definiert Improper Output Handling als unzureichende Validierung, Bereinigung und Behandlung von Modellausgaben, bevor sie weitergereicht werden. Die Beispiele im Eintrag sind gewöhnliche Web-Schwachstellen mit einer neuen Quelle: Ausgaben, die an ",{"tag":154,"children":155},"code",[156],"exec"," oder ",{"tag":154,"children":159},[160],"eval"," gehen, JavaScript oder Markdown, das der Browser als XSS ausführt, generiertes SQL ohne Parametrisierung, Dateipfade aus Ausgaben und Inhalte, die ohne Escaping in Mail-Vorlagen landen.",{"type":135,"content":163},[164],"Diese Kategorie verdient ihren eigenen Platz, weil der Angreifer keinen Zugriff auf Ihre Ausgabe braucht. Mit indirekter Prompt Injection kann ein Dokument, eine Produktbewertung oder eine Webseite, die das Modell liest, steuern, was es schreibt. OWASP nennt genau das als Faktor, der die Auswirkung erhöht, neben Modellrechten, die über die des Endnutzers hinausgehen, und fehlender kontextabhängiger Kodierung. Die erste Gegenmaßnahme ist deutlich: das Modell wie jeden anderen Nutzer behandeln und auf seine Ausgaben Zero Trust anwenden.",{"type":148,"level":149,"id":104,"text":105},{"type":135,"content":167},[168],"Ein Teil der Verwirrung um Output-Guardrails kommt daher, dass das Wort vier Aufgaben mit unterschiedlichen Werkzeugen und Zuständigkeiten abdeckt. Ich halte sie in Design-Reviews auseinander, weil ein Team, das eine Moderations-API eingekauft hat, oft glaubt, alle vier abgedeckt zu haben.",{"type":170,"head":171,"rows":178},"table",[172,174,176],[173],"Aufgabe",[175],"Beantwortete Frage",[177],"Typisches Werkzeug",[179,186,193,200],[180,182,184],[181],"Sicheres Rendern",[183],"Kann dieser Text beim Anzeigen Code ausführen oder Daten abfließen lassen?",[185],"Markdown-Renderer-Konfiguration, Sanitizer, CSP",[187,189,191],[188],"Aktionsvalidierung",[190],"Ist dieser Tool-Aufruf oder dieses JSON erlaubt und wohlgeformt?",[192],"JSON Schema, Allowlists, Berechtigungsprüfung",[194,196,198],[195],"Inhaltssicherheit",[197],"Ist das schädlich, hasserfüllt oder gegen die Richtlinie?",[199],"omni-moderation-latest, Llama Guard 4, Azure AI Content Safety",[201,203,205],[202],"Korrektheit und Datenabfluss",[204],"Ist es belegt, und gibt es Daten preis, die es nicht soll?",[206],"Groundedness-Prüfung, PII- und Secret-Scanner",{"type":135,"content":208},[209],"Die Reihenfolge der Tabelle ist auch die Reihenfolge, in der ich die Arbeit priorisieren würde. Rendering- und Aktionsfehler machen aus einer einzelnen schlechten Antwort einen Vorfall; anstößiger Text in einem B2B-Support-Widget ist peinlich, löscht aber selten Daten.",{"type":148,"level":149,"id":107,"text":108},{"type":135,"content":212},[213],"Chat-Oberflächen rendern Markdown, weil es gut aussieht. Markdown ist aber auch ein Weg, den Browser URLs abrufen zu lassen. Das klassische Exfiltrationsmuster: Eine eingeschleuste Anweisung bringt das Modell dazu, private Daten in den Query-String einer Bild-URL zu schreiben, und der Browser schickt sie dem Angreifer, sobald das Bild gerendert wird, ganz ohne Klick. Simon Willison hat das bei vielen Produkten dokumentiert; im Fall von GitLab Duo, gemeldet im Mai 2025, brachte eine versteckte Anweisung in einem öffentlichen Projekt den Assistenten dazu, einen privaten Merge Request zu lesen und eine Base64-Zusammenfassung über ein Bild-Tag auszuleiten. GitLab behob das, indem Links und Bilder nur noch auf vertrauenswürdige Domains zeigen dürfen.",{"type":135,"content":215},[216,217,220,221,224,225,228],"In einem Vue- oder Nuxt-Frontend gelten die Regeln, die der Vue-Sicherheitsleitfaden schon für Nutzerinhalte nennt: nie nicht vertrauenswürdige Inhalte als Template verwenden, ",{"tag":154,"children":218},[219],"v-html"," nicht mit unbereinigtem HTML nutzen und URLs auf dem Server bereinigen. Für Modellausgaben mache ich vier Dinge: rohes HTML im Markdown-Renderer abschalten, Bilder und Links mit Hosts außerhalb einer Allowlist umschreiben oder verwerfen, verbleibenden externen Links ",{"tag":154,"children":222},[223],"rel=\"noopener nofollow\""," geben und eine Content Security Policy senden, deren ",{"tag":154,"children":226},[227],"img-src"," nur eigene Hosts erlaubt. Die CSP ist das Netz, das auch dann noch hält, wenn der Renderer einen Fehler hat.",{"type":154,"code":230},"\u002F\u002F server\u002Futils\u002Frender-answer.ts — Markdown from the model, rendered on the server\nimport MarkdownIt from 'markdown-it'\n\nconst ALLOWED_HOSTS = new Set(['balazscsorba.com', 'cdn.example-shop.at'])\nconst md = new MarkdownIt({ html: false, linkify: false })\n\nfunction allowed(url: string) {\n  try {\n    const u = new URL(url, 'https:\u002F\u002Fbalazscsorba.com')\n    return (u.protocol === 'https:' && ALLOWED_HOSTS.has(u.hostname))\n  } catch { return false }\n}\n\n\u002F\u002F images to unknown hosts become plain alt text, so nothing is fetched\nmd.renderer.rules.image = (tokens, i) => {\n  const src = tokens[i].attrGet('src') ?? ''\n  return allowed(src) ? `\u003Cimg src=\"${md.utils.escapeHtml(src)}\" alt=\"${md.utils.escapeHtml(tokens[i].content)}\">`\n                      : md.utils.escapeHtml(tokens[i].content)\n}\nconst defaultLink = md.renderer.rules.link_open ?? ((t, i, o, e, s) => s.renderToken(t, i, o))\nmd.renderer.rules.link_open = (tokens, i, opts, env, self) => {\n  if (!allowed(tokens[i].attrGet('href') ?? '')) tokens[i].attrSet('href', '#blocked-link')\n  tokens[i].attrSet('rel', 'noopener nofollow')\n  return defaultLink(tokens, i, opts, env, self)\n}\n\nexport const renderAnswer = (text: string) => md.render(text)\n",{"type":135,"content":232},[233,234,236],"Auf dem Server rendern und HTML erst an den Client schicken, nachdem diese Regeln gelaufen sind. Wer im Browser rendert, wendet dort dieselben Regeln an und behält trotzdem die CSP, denn eine einzige Komponente, die bei roher Ausgabe auf ",{"tag":154,"children":235},[219]," zurückfällt, macht den Rest zunichte.",{"type":148,"level":149,"id":110,"text":111},{"type":135,"content":239},[240,241,245],"Wenn eine Ausgabe eine Aktion steuert, also einen Tool-Aufruf, eine Gutschrift oder eine Datenbankabfrage, sind die Prüfungen deterministisch und billig, es gibt also keinen Grund, sie wegzulassen. Der strikte JSON-Schema-Modus garantiert die Form, nicht die Bedeutung, wie ich in ",{"tag":139,"to":242,"children":243},"\u002Fblog\u002Fstructured-outputs-json-schema-llm",[244],"Structured Outputs mit JSON Schema"," erklärt habe. Nach dem Parsen die Werte gegen Geschäftsregeln prüfen: Darf der aktuelle Nutzer diese Bestellnummer sehen, liegt die Gutschrift unter dem Limit, das der Assistent selbst gewähren darf, gibt es diese SKU im Katalog.",{"type":247,"items":248},"list",[249,254,256,258,260],[250,251,253],"Ausgaben nie an ",{"tag":154,"children":252},[160],", eine Shell oder eine Template-Engine übergeben, die Ausdrücke ausführt.",[255],"Für jeden Wert aus dem Modell parametrisierte Abfragen verwenden; OWASP nennt das ausdrücklich.",[257],"Dateinamen und IDs über eine Nachschlagetabelle auflösen, statt Pfade aus Text zu bauen.",[259],"Ausgaben für den Zielkontext escapen: HTML, Mail, CSV, Shell-Argument.",[261,262,266],"Vor irreversiblen Aktionen einen Menschen einbinden, wie bei ",{"tag":139,"to":263,"children":264},"\u002Fblog\u002Fhuman-in-the-loop-ai-agents",[265],"Freigabestufen mit Human in the Loop",".",{"type":135,"content":268},[269,270,266],"Speziell bei generiertem SQL zählen die Read-only-Rolle und der Abfrage-Validator mehr als jeder Klassifikator; Details dazu in ",{"tag":139,"to":271,"children":272},"\u002Fblog\u002Ftext-to-sql-llm-guardrails",[273],"Guardrails für Text-to-SQL",{"type":148,"level":149,"id":113,"text":114},{"type":135,"content":276},[277],"Für Inhaltssicherheit schreibt man selten ein eigenes Modell. Drei Familien decken die meisten Projekte ab, die ich sehe: den OpenAI-Moderation-Endpunkt, Meta Llama Guard 4 als Open-Weights-Modell zum Selbsthosten oder Mieten und Azure AI Content Safety mit mehreren spezialisierten Detektoren.",{"type":170,"head":279,"rows":286},[280,282,284],[281],"Option",[283],"Was es klassifiziert",[285],"Hinweise aus der Doku",[287,294,301],[288,290,292],[289],"OpenAI omni-moderation-latest",[291],"Text und Bilder; Kategorien wie Belästigung, Hass, Illegales, Selbstverletzung, Sexuelles, Gewalt",[293],"Kostenlos. Viele Kategorien nur für Text. Kann inline in einer Generierungsanfrage laufen.",[295,297,299],[296],"Meta Llama Guard 4 (12B)",[298],"Prompts und Antworten gegen Gefahrenkategorien S1 bis S14",[300],"Open Weights, Text und Bilder. Gibt safe oder unsafe plus verletzte Kategorien aus. Kategorien im Prompt anpassbar.",[302,304,306],[303],"Azure AI Content Safety",[305],"Schadenskategorien, Prompt Shields, Groundedness, geschütztes Material",[307],"Erkennung geschützten Materials nur auf Englisch; der Code-Index reicht nur bis April 2023.",{"type":135,"content":309},[310,311,157,314,317],"Llama Guard 4 nutzt die Gefahrentaxonomie von MLCommons mit einer Ergänzung: S1 Gewaltverbrechen, S2 gewaltlose Verbrechen, S3 Sexualverbrechen, S4 Ausbeutung von Kindern, S5 Verleumdung, S6 Fachberatung, S7 Privatsphäre, S8 geistiges Eigentum, S9 Massenvernichtungswaffen, S10 Hass, S11 Selbstverletzung, S12 sexuelle Inhalte, S13 Wahlen und S14 Missbrauch von Code-Interpretern. Um eine Antwort zu prüfen, muss der Prompt laut Meta sowohl die Nutzernachricht als auch die Antwort des Agenten enthalten, weil die Frage der Kontext für die Bewertung ist. Die erste Ausgabezeile ist ",{"tag":154,"children":312},[313],"safe",{"tag":154,"children":315},[316],"unsafe",", die zweite nennt die verletzten Kategorien.",{"type":135,"content":319},[320,321,324,325,327],"OpenAI hat Inline-Moderation ergänzt: Mit einem ",{"tag":154,"children":322},[323],"moderation","-Objekt auf oberster Ebene und ",{"tag":154,"children":326},[19]," in einer Responses- oder Chat-Completions-Anfrage erhält man Werte für Eingabe und Ausgabe, ohne zweiten Aufruf. Die Doku ist in zwei Punkten deutlich, die ich jedem Team mitgeben würde. Eine sicherheitsbewusste Ablehnung kann trotzdem markiert werden, weil sie schädliche Inhalte bespricht, also sind die Werte Signale für die eigene Richtlinie und keine automatische Sperre. Und bei Tool-Aufrufen deckt die Moderation Argumente und Ausgaben im Gespräch ab, nicht Tool-Namen, Beschreibungen oder Schemas.",{"type":329,"variant":330,"title":331,"body":332},"callout","warn","Eine Moderations-API ist keine Sicherheitsgrenze",[333],[334],"Keiner dieser Klassifikatoren prüft, ob eine Bild-URL Daten abfließen lässt, ob eine Gutschrift im JSON innerhalb der Limits liegt oder ob die Antwort stimmt. Ein sauberes Moderationsergebnis bei einer Exfiltrations-Payload ist das erwartbare Ergebnis, kein Versagen des Klassifikators.",{"type":148,"level":149,"id":116,"text":117},{"type":135,"content":337},[338,339,342,343,346,347,350],"Nutzer erwarten, dass Tokens während der Generierung erscheinen, und jede Output-Prüfung will den ganzen Text. Beides zugleich geht nicht, und die Werkzeuge sagen das auch. OpenAI schreibt, dass Inline-Moderationswerte erst nach Vorliegen der vollständigen Ausgabe kommen, nicht mit den Deltas. NVIDIA NeMo Guardrails führt Output Rails bei aktiviertem Streaming auf Chunks aus: ",{"tag":154,"children":340},[341],"chunk_size"," ist standardmäßig 200 Tokens, ",{"tag":154,"children":344},[345],"context_size"," übernimmt 50 Tokens in den nächsten Chunk, damit ein Satz über eine Grenze hinweg als Ganzes bewertet wird, und ",{"tag":154,"children":348},[349],"stream_first"," bestimmt die Reihenfolge.",{"type":352,"attrs":353,"inner":357,"caption":358},"diagram",{"viewBox":354,"role":355,"aria-labelledby":356},"0 0 720 170","img","ogr-stream-t ogr-stream-d","\u003Ctitle id=\"ogr-stream-t\">Zwei Arten, mit Output-Prüfung zu streamen\u003C\u002Ftitle>\u003Cdesc id=\"ogr-stream-d\">Tokens werden zu Chunks gepuffert; der Chunk wird entweder gesendet und dann geprüft oder geprüft und dann gesendet.\u003C\u002Fdesc>\u003Cdefs>\u003Cmarker id=\"ogr-stream-ah\" viewBox=\"0 0 10 10\" refX=\"9\" refY=\"5\" markerWidth=\"7\" markerHeight=\"7\" orient=\"auto-start-reverse\">\u003Cpath d=\"M0 0L10 5L0 10z\" class=\"d-head\" \u002F>\u003C\u002Fmarker>\u003C\u002Fdefs>\u003Crect x=\"20\" y=\"47\" width=\"154\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"97\" y=\"81\" text-anchor=\"middle\" class=\"d-text\">Modell\u003C\u002Ftext>\u003Ctext x=\"97\" y=\"103\" text-anchor=\"middle\" class=\"d-small\">Token-Stream\u003C\u002Ftext>\u003Cpath d=\"M174 85H194\" class=\"d-line\" marker-end=\"url(#ogr-stream-ah)\" \u002F>\u003Crect x=\"196\" y=\"47\" width=\"154\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"272\" y=\"81\" text-anchor=\"middle\" class=\"d-text\">Puffer\u003C\u002Ftext>\u003Ctext x=\"272\" y=\"103\" text-anchor=\"middle\" class=\"d-small\">Chunk mit 200 Tokens\u003C\u002Ftext>\u003Cpath d=\"M349 85H369\" class=\"d-line\" marker-end=\"url(#ogr-stream-ah)\" \u002F>\u003Crect x=\"371\" y=\"47\" width=\"154\" height=\"76\" rx=\"10\" class=\"d-fill-accent\" \u002F>\u003Ctext x=\"448\" y=\"81\" text-anchor=\"middle\" class=\"d-text\">Rail-Prüfung\u003C\u002Ftext>\u003Ctext x=\"448\" y=\"103\" text-anchor=\"middle\" class=\"d-small\">+50 Tokens Kontext\u003C\u002Ftext>\u003Cpath d=\"M524 85H544\" class=\"d-line\" marker-end=\"url(#ogr-stream-ah)\" \u002F>\u003Crect x=\"546\" y=\"47\" width=\"154\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"623\" y=\"81\" text-anchor=\"middle\" class=\"d-text\">Client\u003C\u002Ftext>\u003Ctext x=\"623\" y=\"103\" text-anchor=\"middle\" class=\"d-small\">anzeigen oder stoppen\u003C\u002Ftext>",[359,360,363,364,367],"Mit ",{"tag":154,"children":361},[362],"stream_first: True"," erhält der Client jeden Chunk vor der Prüfung; mit ",{"tag":154,"children":365},[366],"False"," läuft die Prüfung zuerst und addiert ihre Latenz zu jedem Chunk.",{"type":135,"content":369},[359,370,372],{"tag":154,"children":371},[349]," auf true, dem Standard, kann der Nutzer einen Chunk bereits gelesen haben, der dann gesperrt wird, und der Stream endet mit einem JSON-Fehler, den das Frontend behandeln muss, am besten indem es die Blase ersetzt, statt einen halben Satz stehen zu lassen. Mit false wird nie etwas Gesperrtes angezeigt, aber jeder Chunk wartet auf die Prüfung. Meine Regel: zuerst streamen bei Assistenten mit geringem Risiko, bei denen der schlimmste Fall ein unglücklicher Satz ist; zuerst prüfen, wenn Ausgaben personenbezogene Daten, Preise oder Zusagen enthalten können, an die das Unternehmen gebunden wäre.",{"type":148,"level":149,"id":119,"text":120},{"type":135,"content":375},[376,377,266],"In einem RAG-Assistenten ist der teuerste Output-Fehler eine selbstsichere Antwort, die die Quellen nicht stützen. Azure AI Content Safety bietet dafür Groundedness Detection: Man schickt den generierten Text und die Quellen, wählt eine Domain wie Medical oder Generic, und der Dienst markiert unbelegte Inhalte. Ein optionaler Korrekturmodus liefert an die Quellen angepassten Text zurück. Ich nutze solche Prüfungen eher für Stichproben und Alarme als als harte Sperre, weil ein Grounding-Richter selbst ein fehlerbehaftetes Modell ist und die eigentliche Lösung weiter vorne bei Retrieval und Zitaten liegt, beschrieben in ",{"tag":139,"to":378,"children":379},"\u002Fblog\u002Fllm-hallucination-grounding-citations",[380],"Grounding und Zitate",{"type":135,"content":382},[383,384,388],"Datenabfluss lässt sich leichter deterministisch prüfen. Ausgaben nach bekannten Mustern durchsuchen: IBANs, Mail-Adressen und Telefonnummern anderer Personen als des aktuellen Nutzers, API-Keys, interne Hostnamen und Fragmente des eigenen System-Prompts. Dieselben Detektoren, die man auf der Eingabeseite für ",{"tag":139,"to":385,"children":386},"\u002Fblog\u002Fpii-redaction-llm-pipelines",[387],"PII-Schwärzung"," nutzt, funktionieren auch auf der Ausgabeseite; der Unterschied ist, dass man bei Ausgaben meist schwärzt und protokolliert, statt die ganze Antwort zu verwerfen.",{"type":148,"level":149,"id":122,"text":123},{"type":135,"content":391},[392],"Eine Guardrail ist eine Entscheidung, kein Wert. Für jede Kategorie festhalten, was passiert, wenn sie anschlägt, und wer es sieht. Mit dieser Tabelle beginne ich und justiere sie dann mit echtem Traffic.",{"type":170,"head":394,"rows":401},[395,397,399],[396],"Befund",[398],"Aktion",[400],"Nutzer sieht",[402,409,416,423,430],[403,405,407],[404],"Unsicherer Link- oder Bild-Host",[406],"In Text umschreiben, protokollieren",[408],"Antwort ohne Link",[410,412,414],[411],"Klarer Verstoß gegen Inhaltssicherheit",[413],"Blockieren, durch festen Text ersetzen, Werte protokollieren",[415],"Neutrale Ablehnung und Kontaktmöglichkeit",[417,419,421],[418],"PII oder Secret einer anderen Person",[420],"Schwärzen, Security alarmieren",[422],"Antwort mit maskiertem Wert",[424,426,428],[425],"Ungültige Tool-Argumente",[427],"Ablehnen, Fehler einmal an das Modell zurückgeben",[429],"Nichts, außer der Retry scheitert",[431,433,435],[432],"Unbelegte Aussage in einer RAG-Antwort",[434],"Zur Prüfung markieren, Stichprobe",[436],"Antwort mit Quellen wie gewohnt",{"type":135,"content":438},[439,440,443],"Zwei Gewohnheiten halten das ehrlich. Für jede Entscheidung Klassifikator-Version, Werte und Aktion protokollieren, weil Schwellen driften, wenn der Anbieter ein Modell hinter einem ",{"tag":154,"children":441},[442],"-latest","-Alias aktualisiert. Und Nutzern beim Blockieren etwas Brauchbares zeigen: Eine feste Nachricht mit einem Weg zu einem Menschen ist besser als eine stumme leere Blase, die Leute für einen Fehler halten und erneut versuchen.",{"type":148,"level":149,"id":125,"text":126},{"type":135,"content":446},[447],"Billige deterministische Prüfungen laufen zuerst, Klassifikatoren danach und das Rendering zuletzt, damit die teuren und fehlbaren Schritte so wenig wie möglich sehen. In Nuxt oder jedem Node-Backend ist die Variante ohne Streaming eine kurze Funktion.",{"type":352,"attrs":449,"inner":452,"caption":453},{"viewBox":450,"role":355,"aria-labelledby":451},"0 0 720 180","ogr-pipe-t ogr-pipe-d","\u003Ctitle id=\"ogr-pipe-t\">Pipeline der Output-Guardrails\u003C\u002Ftitle>\u003Cdesc id=\"ogr-pipe-d\">Die Modellausgabe durchläuft Leak-Scan, Schema-Prüfung, Moderation und sicheres Rendering, bevor sie den Nutzer erreicht.\u003C\u002Fdesc>\u003Cdefs>\u003Cmarker id=\"ogr-pipe-ah\" viewBox=\"0 0 10 10\" refX=\"9\" refY=\"5\" markerWidth=\"7\" markerHeight=\"7\" orient=\"auto-start-reverse\">\u003Cpath d=\"M0 0L10 5L0 10z\" class=\"d-head\" \u002F>\u003C\u002Fmarker>\u003C\u002Fdefs>\u003Crect x=\"20\" y=\"52\" width=\"118\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"79\" y=\"86\" text-anchor=\"middle\" class=\"d-text\">Ausgabe\u003C\u002Ftext>\u003Ctext x=\"79\" y=\"108\" text-anchor=\"middle\" class=\"d-small\">Text oder JSON\u003C\u002Ftext>\u003Cpath d=\"M138 90H158\" class=\"d-line\" marker-end=\"url(#ogr-pipe-ah)\" \u002F>\u003Crect x=\"160\" y=\"52\" width=\"118\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"220\" y=\"86\" text-anchor=\"middle\" class=\"d-text\">Leak-Scan\u003C\u002Ftext>\u003Ctext x=\"220\" y=\"108\" text-anchor=\"middle\" class=\"d-small\">PII, Secrets\u003C\u002Ftext>\u003Cpath d=\"M279 90H299\" class=\"d-line\" marker-end=\"url(#ogr-pipe-ah)\" \u002F>\u003Crect x=\"301\" y=\"52\" width=\"118\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"360\" y=\"86\" text-anchor=\"middle\" class=\"d-text\">Schema\u003C\u002Ftext>\u003Ctext x=\"360\" y=\"108\" text-anchor=\"middle\" class=\"d-small\">Regeln, Allowlist\u003C\u002Ftext>\u003Cpath d=\"M419 90H439\" class=\"d-line\" marker-end=\"url(#ogr-pipe-ah)\" \u002F>\u003Crect x=\"441\" y=\"52\" width=\"118\" height=\"76\" rx=\"10\" class=\"d-fill-accent\" \u002F>\u003Ctext x=\"500\" y=\"86\" text-anchor=\"middle\" class=\"d-text\">Moderation\u003C\u002Ftext>\u003Ctext x=\"500\" y=\"108\" text-anchor=\"middle\" class=\"d-small\">Werte, Richtlinie\u003C\u002Ftext>\u003Cpath d=\"M560 90H580\" class=\"d-line\" marker-end=\"url(#ogr-pipe-ah)\" \u002F>\u003Crect x=\"582\" y=\"52\" width=\"118\" height=\"76\" rx=\"10\" class=\"d-box\" \u002F>\u003Ctext x=\"641\" y=\"86\" text-anchor=\"middle\" class=\"d-text\">Rendern\u003C\u002Ftext>\u003Ctext x=\"641\" y=\"108\" text-anchor=\"middle\" class=\"d-small\">Hosts, CSP\u003C\u002Ftext>",[454],"Nach Kosten sortiert: zuerst deterministische Prüfungen, dann der Klassifikator, zuletzt die Rendering-Regeln.",{"type":154,"code":456},"\u002F\u002F server\u002Futils\u002Fguard-output.ts\nimport { renderAnswer } from '.\u002Frender-answer'\nimport { redactLeaks } from '.\u002Fredact'          \u002F\u002F your PII \u002F secret patterns\n\nconst BLOCKED = 'I cannot help with that here. Please contact our support team.'\n\nexport async function guardOutput(text: string) {\n  const { text: clean, findings } = redactLeaks(text)\n\n  const res = await fetch('https:\u002F\u002Fapi.openai.com\u002Fv1\u002Fmoderations', {\n    method: 'POST',\n    headers: { Authorization: `Bearer ${process.env.OPENAI_API_KEY}`, 'Content-Type': 'application\u002Fjson' },\n    body: JSON.stringify({ model: 'omni-moderation-latest', input: clean }),\n  })\n  if (!res.ok) throw new Error(`moderation failed: ${res.status}`)   \u002F\u002F fail closed\n  const result = (await res.json()).results[0]\n\n  const decision = result.flagged ? 'block' : findings.length ? 'redact' : 'allow'\n  console.info(JSON.stringify({ event: 'output_guard', decision, findings, scores: result.category_scores }))\n\n  return { html: renderAnswer(decision === 'block' ? BLOCKED : clean), decision }\n}\n",{"type":135,"content":458},[459,460,463,464,266],"Zwei Entscheidungen in dieser Skizze sind bewusst getroffen. Sie schlägt geschlossen fehl, wenn der Moderationsaufruf scheitert, was für einen öffentlichen Assistenten richtig ist und für ein internes Werkzeug, bei dem Verfügbarkeit wichtiger ist, falsch; entscheiden Sie das ausdrücklich. Und sie nutzt ",{"tag":154,"children":461},[462],"flagged"," als erste Entscheidung, wie OpenAI vorschlägt, protokolliert aber jeden Wert, damit man später auf Schwellen pro Kategorie umstellen kann. Wer ein Framework bevorzugt: Guardrails AI verpackt dieselbe Idee in Validatoren, die man an einen Modellaufruf hängt, siehe meinen ",{"tag":139,"to":465,"children":466},"\u002Ftools\u002Fguardrails-ai",[467],"Test von Guardrails AI",{"type":148,"level":149,"id":128,"text":129},{"type":135,"content":470},[471],"Guardrails versagen in zwei Richtungen, und beide kosten Geld. Übersehene Verstöße sind die offensichtliche. Fehlalarme sind die leise: Ein Support-Assistent, der Fragen zum „Beenden eines Prozesses“ oder zum „Versand von Gefahrgut“ ablehnt, verliert Nutzer, ohne dass es jemand merkt. Ein kleines gelabeltes Set mit beiden Arten aufbauen, einschließlich Fachvokabular, das Klassifikatoren stolpern lässt, und es in der CI laufen lassen, sobald sich eine Schwelle, ein Prompt oder eine Klassifikator-Version ändert.",{"type":247,"items":473},[474,476,478,480],[475],"Exfiltrations-Payloads aufnehmen: Bild-URLs mit Query-Strings, Links auf ähnlich aussehende Domains, HTML-Tags in Markdown.",[477],"Tool-Aufrufe mit Werten außerhalb des Bereichs und IDs anderer Kunden aufnehmen.",[479],"Sperrquote und Fehlalarmquote pro Kategorie auf Produktionsstichproben verfolgen, nicht nur im Testset.",[481,482,486],"Die ganze Kette mit einem Werkzeug wie ",{"tag":139,"to":483,"children":484},"\u002Ftools\u002Fpromptfoo",[485],"Promptfoo"," red-teamen, denn eine Payload, die eine Schicht passiert, ist erst interessant, wenn sie alle passiert.",{"type":135,"content":488},[489],"Output-Guardrails sind unspektakuläre Ingenieursarbeit: Renderer-Konfiguration, Schemas, ein Klassifikator-Aufruf und eine Entscheidungstabelle. Genau deshalb funktionieren sie. Das Modell wird Sie weiter überraschen; die Systeme danach sollten es nicht.",{"type":148,"level":149,"id":131,"text":132},{"type":247,"ordered":492,"items":493},true,[494,498,501,504,507,510,513,516,519,522],[495],{"tag":496,"href":38,"children":497},"a",[37],[499],{"tag":496,"href":41,"children":500},[40],[502],{"tag":496,"href":44,"children":503},[43],[505],{"tag":496,"href":47,"children":506},[46],[508],{"tag":496,"href":50,"children":509},[49],[511],{"tag":496,"href":53,"children":512},[52],[514],{"tag":496,"href":56,"children":515},[55],[517],{"tag":496,"href":59,"children":518},[58],[520],{"tag":496,"href":62,"children":521},[61],[523],{"tag":496,"href":65,"children":524},[64],[526,582,626,728],{"slug":527,"published":528,"minutes":529,"category":7,"tags":530,"keywords":536,"about":547,"sources":557,"cover":576,"og":577,"expertise":68,"locales":578,"lang":71,"title":579,"description":580,"coverAlt":581},"slopsquatting-ai-package-hallucinations","2026-10-16",6,[531,532,533,534,535],"Supply chain security","Coding agents","npm","PyPI","Package hallucination",[537,538,539,540,541,542,543,544,545,546],"slopsquatting","package hallucination","ai hallucinated packages","llm package confusion attack","coding agent supply chain security","npm min-release-age","pnpm minimumReleaseAge","uv exclude-newer","npm ignore-scripts","huggingface-cli hallucinated package",[548,551,554],{"name":549,"url":550},"Typosquatting","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FTyposquatting",{"name":552,"url":553},"Supply chain attack","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FSupply_chain_attack",{"name":555,"url":556},"Hallucination (artificial intelligence)","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FHallucination_(artificial_intelligence)",[558,561,564,567,570,573],{"title":559,"url":560},"Spracklen et al.: We Have a Package for You! A Comprehensive Analysis of Package Hallucinations by Code Generating LLMs (2024)","https:\u002F\u002Farxiv.org\u002Fabs\u002F2406.10279",{"title":562,"url":563},"Lasso Security, Bar Lanyado: Diving Deeper into AI Package Hallucinations (Mar 2024)","https:\u002F\u002Fwww.lasso.security\u002Fblog\u002Fai-package-hallucinations",{"title":565,"url":566},"npm Docs: config (min-release-age, before, ignore-scripts, allow-scripts)","https:\u002F\u002Fdocs.npmjs.com\u002Fcli\u002Fv11\u002Fusing-npm\u002Fconfig",{"title":568,"url":569},"pnpm: Dependency resolution settings (minimumReleaseAge)","https:\u002F\u002Fpnpm.io\u002Fsettings\u002Fdependency-resolution",{"title":571,"url":572},"uv: Settings reference (exclude-newer, require-hashes)","https:\u002F\u002Fdocs.astral.sh\u002Fuv\u002Freference\u002Fsettings\u002F",{"title":574,"url":575},"pip documentation: Secure installs and hash-checking mode","https:\u002F\u002Fpip.pypa.io\u002Fen\u002Fstable\u002Ftopics\u002Fsecure-installs\u002F","\u002Fimages\u002Fblog\u002Fslopsquatting-ai-package-hallucinations\u002Fcover.webp","\u002Fimages\u002Fblog\u002Fslopsquatting-ai-package-hallucinations\u002Fog.jpg",[70,71,72],"Slopsquatting: wenn Coding-Agenten Pakete installieren, die es nicht gibt","Wie LLMs Paketnamen halluzinieren, wie Angreifer sie registrieren und welche Registry-, Lockfile- und Agenten-Kontrollen die Installation stoppen.","Drei Kästen auf einer Schiene, der mittlere hohl und versetzt, darunter passende Quadrate auf einer Ablage.",{"slug":583,"published":528,"minutes":529,"category":7,"tags":584,"keywords":589,"about":600,"sources":607,"cover":620,"og":621,"expertise":68,"locales":622,"lang":71,"title":623,"description":624,"coverAlt":625},"rag-poisoning-knowledge-base-attacks",[585,586,587,12,588],"RAG security","Data poisoning","Prompt injection","Vector database",[590,591,592,593,594,595,596,597,598,599],"rag poisoning","knowledge base poisoning","poisonedrag","rag security","indirect prompt injection rag","owasp llm08 vector and embedding weaknesses","vector database security","rag data poisoning defense","hidden text prompt injection","secure rag ingestion",[601,604,606],{"name":602,"url":603},"Retrieval-augmented generation","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FRetrieval-augmented_generation",{"name":587,"url":605},"https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FPrompt_injection",{"name":12,"url":34},[608,611,614,617],{"title":609,"url":610},"Zou et al.: PoisonedRAG: Knowledge Corruption Attacks to Retrieval-Augmented Generation of Large Language Models (2024)","https:\u002F\u002Farxiv.org\u002Fabs\u002F2402.07867",{"title":612,"url":613},"Greshake et al.: Not what you've signed up for: Compromising Real-World LLM-Integrated Applications with Indirect Prompt Injection (2023)","https:\u002F\u002Farxiv.org\u002Fabs\u002F2302.12173",{"title":615,"url":616},"OWASP Gen AI Security Project: LLM08:2025 Vector and Embedding Weaknesses","https:\u002F\u002Fgenai.owasp.org\u002Fllmrisk\u002Fllm082025-vector-and-embedding-weaknesses\u002F",{"title":618,"url":619},"OWASP Gen AI Security Project: LLM04:2025 Data and Model Poisoning","https:\u002F\u002Fgenai.owasp.org\u002Fllmrisk\u002Fllm042025-data-and-model-poisoning\u002F","\u002Fimages\u002Fblog\u002Frag-poisoning-knowledge-base-attacks\u002Fcover.webp","\u002Fimages\u002Fblog\u002Frag-poisoning-knowledge-base-attacks\u002Fog.jpg",[70,71,72],"RAG-Poisoning: wie wenige Dokumente einen Assistenten steuern und wie man die Wissensbasis verteidigt","Wie Angreifer Dokumente platzieren, die RAG-Systeme finden, was PoisonedRAG und OWASP zeigen und welche Kontrollen bei Ingestion, Retrieval und Antwort helfen.","Blätter laufen auf einem Band in einen Behälter, eines trägt einen kleinen Block, ein Tor am Ausgang.",{"slug":627,"published":628,"minutes":629,"category":7,"tags":630,"keywords":636,"about":645,"sources":655,"cover":722,"og":723,"expertise":68,"locales":724,"lang":71,"title":725,"description":726,"coverAlt":727},"coding-agent-secrets-hygiene","2026-10-08",11,[631,632,633,634,635],"AI agents","Secrets management","Claude Code","Pre-commit scanning","CI security",[637,638,639,640,641,642,643,644],"coding agent secrets","keep secrets away from AI agents","Claude Code deny read .env","gitleaks pre-commit hook","GitHub push protection secrets","OIDC GitHub Actions short-lived credentials","rotate a leaked API key","MCP server token scope",[646,649,652],{"name":647,"url":648},"Principle of least privilege","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FPrinciple_of_least_privilege",{"name":650,"url":651},"Model Context Protocol","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FModel_Context_Protocol",{"name":653,"url":654},"Git","https:\u002F\u002Fen.wikipedia.org\u002Fwiki\u002FGit",[656,659,662,665,668,671,674,677,680,683,686,689,692,695,698,701,704,707,710,713,716,719],{"title":657,"url":658},"Claude Code: permissions","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fpermissions",{"title":660,"url":661},"Claude Code: sandboxed Bash","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fsandboxing",{"title":663,"url":664},"Claude Code: hooks","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fhooks",{"title":666,"url":667},"Claude Code: data usage","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fdata-usage",{"title":669,"url":670},"Claude Code: settings","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fsettings",{"title":672,"url":673},"Claude Code: MCP servers","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fmcp",{"title":675,"url":676},"Codex: configuration reference","https:\u002F\u002Fdevelopers.openai.com\u002Fcodex\u002Fconfig-reference",{"title":678,"url":679},"Codex: agent approvals and security","https:\u002F\u002Flearn.chatgpt.com\u002Fdocs\u002Fagent-approvals-security",{"title":681,"url":682},"Codex: advanced configuration","https:\u002F\u002Flearn.chatgpt.com\u002Fdocs\u002Fconfig-file\u002Fconfig-advanced",{"title":684,"url":685},"GitHub: about push protection","https:\u002F\u002Fdocs.github.com\u002Fen\u002Fcode-security\u002Fsecret-scanning\u002Fintroduction\u002Fabout-push-protection",{"title":687,"url":688},"GitHub: security hardening with OIDC","https:\u002F\u002Fdocs.github.com\u002Fen\u002Factions\u002Fsecurity-for-github-actions\u002Fsecurity-hardening-your-deployments\u002Fabout-security-hardening-with-openid-connect",{"title":690,"url":691},"GitHub: OpenID Connect reference","https:\u002F\u002Fdocs.github.com\u002Fen\u002Factions\u002Freference\u002Fsecurity\u002Foidc",{"title":693,"url":694},"GitHub: using secrets in Actions","https:\u002F\u002Fdocs.github.com\u002Fen\u002Factions\u002Fsecurity-guides\u002Fusing-secrets-in-github-actions",{"title":696,"url":697},"GitHub: secure use reference","https:\u002F\u002Fdocs.github.com\u002Fen\u002Factions\u002Fsecurity-for-github-actions\u002Fsecurity-guides\u002Fsecurity-hardening-for-github-actions",{"title":699,"url":700},"GitHub: removing sensitive data","https:\u002F\u002Fdocs.github.com\u002Fen\u002Fauthentication\u002Fkeeping-your-account-and-data-secure\u002Fremoving-sensitive-data-from-a-repository",{"title":702,"url":703},"gitleaks: README and latest release","https:\u002F\u002Fgithub.com\u002Fgitleaks\u002Fgitleaks",{"title":705,"url":706},"TruffleHog: README","https:\u002F\u002Fgithub.com\u002Ftrufflesecurity\u002Ftrufflehog",{"title":708,"url":709},"detect-secrets: README and latest release","https:\u002F\u002Fgithub.com\u002FYelp\u002Fdetect-secrets",{"title":711,"url":712},"Model Context Protocol: security best practices","https:\u002F\u002Fmodelcontextprotocol.io\u002Fspecification\u002F2025-06-18\u002Fbasic\u002Fsecurity_best_practices",{"title":714,"url":715},"OWASP: Secrets Management Cheat Sheet","https:\u002F\u002Fcheatsheetseries.owasp.org\u002Fcheatsheets\u002FSecrets_Management_Cheat_Sheet.html",{"title":717,"url":718},"OWASP: LLM02 sensitive information disclosure","https:\u002F\u002Fgenai.owasp.org\u002Fllmrisk\u002Fllm022025-sensitive-information-disclosure\u002F",{"title":720,"url":721},"Git: git-add documentation","https:\u002F\u002Fgit-scm.com\u002Fdocs\u002Fgit-add","\u002Fimages\u002Fblog\u002Fcoding-agent-secrets-hygiene\u002Fcover.webp","\u002Fimages\u002Fblog\u002Fcoding-agent-secrets-hygiene\u002Fog.jpg",[70,71,72],"Coding-Agenten und Secrets: Schlüssel aus Kontext, Logs und Commits","Wie Secrets über Coding-Agenten abfließen und welche Kontrollen sie stoppen: Deny-Regeln, Sandbox, Pre-Commit-Scans, Push-Schutz, OIDC und Rotation.","Kleine Quadrate auf einer Schiene stoppen an einer Wand mit Schloss, dahinter eine offene Kiste.",{"slug":729,"published":730,"minutes":629,"category":7,"tags":731,"keywords":737,"about":746,"sources":759,"cover":801,"og":802,"expertise":68,"locales":803,"lang":71,"title":804,"description":805,"coverAlt":806},"works-council-ai-tools-austria-germany","2026-10-02",[732,733,734,735,736],"Works council","AI coding tools","Employee monitoring","GDPR","Co-determination",[738,739,740,741,742,743,744,745],"works council AI tools","AI coding tools works council","Betriebsrat KI Mitbestimmung","§ 87 BetrVG Überwachung","§ 96 ArbVG Kontrollmaßnahmen","AI usage logs employee monitoring","works agreement for AI tools","GDPR Article 88 employee data",[747,750,753,756],{"name":748,"url":749},"General Data Protection Regulation","https:\u002F\u002Feur-lex.europa.eu\u002Feli\u002Freg\u002F2016\u002F679\u002Foj\u002Feng",{"name":751,"url":752},"EU Artificial Intelligence Act (Regulation (EU) 2024\u002F1689)","https:\u002F\u002Feur-lex.europa.eu\u002Feli\u002Freg\u002F2024\u002F1689\u002Foj\u002Feng",{"name":754,"url":755},"Arbeitsverfassungsgesetz (Austrian Labour Constitution Act)","https:\u002F\u002Fwww.ris.bka.gv.at\u002FGeltendeFassung.wxe?Abfrage=Bundesnormen&Gesetzesnummer=10008329",{"name":757,"url":758},"Betriebsverfassungsgesetz (German Works Constitution Act), § 87","https:\u002F\u002Fwww.gesetze-im-internet.de\u002Fbetrvg\u002F__87.html",[760,762,764,767,770,772,775,777,780,783,786,789,792,795,798],{"title":761,"url":755},"Arbeitsverfassungsgesetz (ArbVG), §§ 96 and 96a, consolidated text of 10 October 2026, RIS",{"title":763,"url":758},"Betriebsverfassungsgesetz (BetrVG), § 87, gesetze-im-internet.de",{"title":765,"url":766},"Betriebsverfassungsgesetz (BetrVG), § 90, gesetze-im-internet.de","https:\u002F\u002Fwww.gesetze-im-internet.de\u002Fbetrvg\u002F__90.html",{"title":768,"url":769},"Bundesdatenschutzgesetz (BDSG), § 26, gesetze-im-internet.de","https:\u002F\u002Fwww.gesetze-im-internet.de\u002Fbdsg_2018\u002F__26.html",{"title":771,"url":749},"Regulation (EU) 2016\u002F679 (GDPR), EUR-Lex",{"title":773,"url":774},"GDPR Article 5(1)(e), storage limitation, gdpr-info.eu","https:\u002F\u002Fgdpr-info.eu\u002Fart-5-gdpr\u002F",{"title":776,"url":752},"Regulation (EU) 2024\u002F1689 (AI Act), EUR-Lex",{"title":778,"url":779},"Regulation (EU) 2026\u002F1744, EUR-Lex","https:\u002F\u002Feur-lex.europa.eu\u002Feli\u002Freg\u002F2026\u002F1744\u002Foj",{"title":781,"url":782},"AI Act Article 26, AI Act Explorer","https:\u002F\u002Fartificialintelligenceact.eu\u002Farticle\u002F26\u002F",{"title":784,"url":785},"AI Act Annex III, AI Act Explorer","https:\u002F\u002Fartificialintelligenceact.eu\u002Fannex\u002F3\u002F",{"title":787,"url":788},"BAG, 1 ABR 16\u002F23 (July 2024), headset system, gesetze.co","https:\u002F\u002Fgesetze.co\u002Furteile\u002F1_ABR_16-23",{"title":790,"url":791},"ArbG Hamburg, 24 BVGa 1\u002F24: law-firm summary by CMS","https:\u002F\u002Fcms.law\u002Fde\u002Fdeu\u002Flegal-updates\u002Fkein-mitbestimmungsrecht-des-betriebsrats-bei-chatgpt-co",{"title":793,"url":794},"ArbG Hamburg, 24 BVGa 1\u002F24: law-firm summary by Gleiss Lutz","https:\u002F\u002Fwww.gleisslutz.com\u002Fde\u002Fknow-how\u002Farbeitsgericht-hamburg-zu-chatgpt-kein-mitbestimmungsrecht-des-betriebsrats",{"title":796,"url":797},"Claude Code documentation: monitoring usage","https:\u002F\u002Fcode.claude.com\u002Fdocs\u002Fen\u002Fmonitoring-usage",{"title":799,"url":800},"GitHub Docs: Copilot metrics data reference","https:\u002F\u002Fdocs.github.com\u002Fen\u002Fcopilot\u002Freference\u002Fmetrics-data","\u002Fimages\u002Fblog\u002Fworks-council-ai-tools-austria-germany\u002Fcover.webp","\u002Fimages\u002Fblog\u002Fworks-council-ai-tools-austria-germany\u002Fog.jpg",[70,71,72],"KI-Coding-Tools und Betriebsrat: wann Nutzungsprotokolle als Überwachung gelten","Nutzungsprotokolle können ein KI-Tool zum Überwachungssystem machen. Was § 96 ArbVG und § 87 BetrVG verlangen und was du vor dem Rollout klären solltest.","Zwei hohe Rechtecke nebeneinander unter einem breiten Blatt, fünf kleine Quadrate fallen in eine Kiste.",1792222777468]