Du hast Claude Code gebeten, dem Login-Formular einen Ladezustand hinzuzufügen. Der Ladezustand funktioniert. Der Button sagt jetzt aber auch „Log in“ statt „Sign in“, die Fehlermeldung klingt freundlicher, und eine Überschrift ist plötzlich in Sentence Case. Niemand hat darum gebeten, alle Tests sind grün, und wenn niemand das komplette Diff Wort für Wort liest, geht es live.

Dieser Beitrag handelt genau von diesem Fehlerfall: bestehende, freigegebene Texte, die von einem KI-Coding-Agent stillschweigend umformuliert werden — und dem Workflow, der das verhindert. Strings, die Agents neu erstellen — hartcodiert und ohne Schlüssel —, sind ein anderes Problem, behandelt in warum KI-Coding-Tools ständig hartcodierte Strings hinzufügen. Wo Produkttexte grundsätzlich liegen sollten, ist eine Architekturfrage, behandelt in code-native Produkttexte. Dieser Beitrag bleibt beim konkreten Vorfall — dem Montagmorgen, an dem sich der Wortlaut geändert hat, ohne dass das jemand entschieden hätte. globalize.now ist ein code-natives System zur Verwaltung von UI-Texten mit integrierter Lokalisierung, und genau solche Vorfälle sind mit ein Grund, warum es das gibt.

Warum schreiben KI-Coding-Agents UI-Texte um?

KI-Coding-Agents schreiben UI-Texte um, weil sie Prosa in Komponenten sehen; sobald diese Texte hinter Schlüsseln in einer Quell-Locale-Datei liegen, wird eine Änderung zu einem expliziten, überprüfbaren Edit statt zum Nebeneffekt einer anderen Aufgabe.

Innerhalb einer Komponente hat „Sign in“ keinen Sonderstatus. Es ist ein String-Literal in einem JSX-Attribut, nicht zu unterscheiden von einem className oder einer Test-ID. Der Agent wurde mit Millionen von Diffs trainiert, in denen es als gutes Verhalten galt, umliegenden Code zu verbessern — und für ein Modell ist es derselbe Move, ein Label „klarer“ zu machen, wie eine Variable umzubenennen. Da wartet kein Type-Error, kein fehlschlagender Test, keine Owner-Annotation an den Wörtern. Die Umformulierung kostet den Agent nichts.

Die Änderung übersteht das Review aus demselben Grund. Reviewer lesen Logik. Eine Textänderung sitzt mitten in einem Diff, das eigentlich um einen Ladezustand geht, es kompiliert, es rendert, und wenn ein Snapshot-Test meckert, ist die Standardreaktion, den Snapshot zu aktualisieren — womit der neue Wortlaut so festgehalten wird, als wäre er abgesegnet.

Halten Rules-Dateien wie AGENTS.md das tatsächlich auf?

Agent-Rules-Dateien reduzieren die Häufigkeit; sie machen UI-Texte nicht unantastbar. Erst die Architektur macht die Änderung sichtbar.

Die Rules-Datei lohnt sich trotzdem — sie ist die günstigste Schicht und funktioniert oft genug, um dreißig Sekunden wert zu sein. Dieser Block funktioniert in AGENTS.md, CLAUDE.md und Cursor-Rules (.cursorrules oder .cursor/rules/):

## UI copy policy — do not modify user-facing text

- Never change user-visible strings (button labels, headings, empty states,
  error messages, tooltips, placeholder text) unless the task explicitly
  asks for a copy change.
- User-visible text lives in the source locale file (e.g. locales/en.json).
  Reference it by key. Never inline a new user-facing string in a component.
- If a task needs new user-facing text, add a key to the source locale file,
  reference it, and list the new key in your summary for copy review.
- Any diff to the source locale file is a copy change. Call it out
  separately — it needs its own approval, apart from code review.

Jetzt der ehrliche Teil. Eine Regel ist Kontext, und Kontext konkurriert. Bei einer langen Aufgabe ist die Anweisung eine Zeile unter Tausenden von Code-Tokens, und manchmal setzt sie sich nicht durch — gegen eine Kompaktierung, gegen einen Sub-Agent, der sie nie gesehen hat, gegen ein starkes Muster in der umgebenden Datei. Schlimmer noch: Der Agent, der die Regel bricht, meldet das nicht. Du bekommst keine Benachrichtigung, dass sich dein Wortlaut geändert hat — du bekommst ein Diff, in dem er sich zufällig geändert hat. Eine Konvention ist kein Check.

Die Rules-Datei ist also die erste Schicht — und die Schicht, der du allein nicht vertrauen solltest.

Wie machst du eine Textänderung sichtbar statt still?

Verschiebe jeden für Nutzer sichtbaren String aus den Komponenten heraus, hinter Schlüssel in einer Quell-Locale-Datei. Danach muss ein Agent, der deinen Wortlaut ändern will, eine Datei bearbeiten, deren einziger Zweck der Wortlaut ist.

Das ist der Schritt, den die Rules-Datei nicht leisten kann, und der Mechanismus dahinter ist simpel. Wenn Komponenten auf t('auth.signIn') verweisen, statt „Sign in“ erneut auszuformulieren, ändert sich beides gleichzeitig. Komponenten-Diffs enthalten keine Texte mehr, also gibt es für den Agent, der an deinem Ladezustand arbeitet, dort nichts umzuformulieren. Und jede Textänderung, ob von Agent oder Mensch, landet in einer einzigen Datei — wo eine geänderte Zeile das Ereignis ist, das dich interessiert, und nicht Rauschen drumherum. Ein Locale-Datei-Diff zu scannen dauert Sekunden. Eine schlechte Umformulierung rückgängig zu machen ist eine Zeile.

Um präzise zu sein, was das bringt: Der Agent kann die Locale-Datei weiterhin bearbeiten. Der Punkt ist nicht, dass die Wörter unantastbar werden — sondern dass es aufhört, ein Nebeneffekt zu sein, und stattdessen zu einem lesbaren, überprüfbaren Akt wird. Das ist der Unterschied, ob du es aus dem Diff erfährst oder von einer Kundin.

Die vollständige Begründung dafür, die Single Source of Truth im Codebase zu halten — statt in einem Design-Tool, das damit synchronisiert wird —, ist der Grundlagen-Beitrag code-native Produkttexte. Für diesen Beitrag reicht die eine Konsequenz: verschlüsselte Texte sind das, was aus deiner Rules-Datei mehr als eine Bitte macht — etwas Überprüfbares.

Wie sieht das Review-Gate aus?

Behandle jedes Diff an der Quell-Locale-Datei als Textänderung und leite es an die Person weiter, der die Wörter gehören.

Konkret: Trage das Locales-Verzeichnis in CODEOWNERS ein, damit bei jeder Änderung daran ein textverantwortlicher Mensch angefragt wird. Füge eine Zeile zur PR-Vorlage hinzu — „Ändert dieser PR nutzersichtbaren Wortlaut, und war das die Aufgabe?“. Und behalte in der Rules-Datei die Vorgabe, dass der Agent geänderte Schlüssel in seiner Zusammenfassung auflistet — hält er sich daran, ist das Review sofort erledigt, und tut er es nicht, greift trotzdem der CODEOWNERS-Hook.

In einem kleinen Team ist das leichter, als es klingt. Das Locale-Diff ist kurz, es liest sich in normaler Sprache, und „Soll der Button jetzt Log in sagen?“ ist eine Entscheidung, die jemand in fünf Sekunden treffen kann — vorausgesetzt, die Frage wird ihm tatsächlich vorgelegt, was die eigentliche Aufgabe des Gates ist.

Was, wenn der Agent deine Texte schon umgeschrieben hat?

Stelle zuerst den freigegebenen Wortlaut wieder her, verschlüssele dann die Strings, damit die nächste Umformulierung als Diff auftaucht.

Den Schaden zu finden ist eine Git-Übung: Vergleiche die betroffenen Komponenten mit dem letzten Commit, dem du vertraust, und lies nur die String-Literale. Stelle wieder her, was sich geändert hat. Wenn du nicht mit Sicherheit sagen kannst, welcher Wortlaut der freigegebene war — der Button sagt „Log in“, die Marketing-Seite sagt „Sign in“, und kein Artefakt hält fest, was richtig ist —, bist du auf den tieferliegenden Zustand gestoßen, den dieser Vorfall befeuert. Copy Drift bedeutet, dass für Nutzer sichtbarer Text über Oberflächen und Zeit hinweg von seiner freigegebenen Quelle abweicht, ohne eine einzige Source of Truth, von der er abweichen könnte. Dieser Begriff, seine Ursachen und Folgen sind ein eigener Beitrag: was ist Copy Drift.

Verschlüssele dann, was du wiederhergestellt hast — beginnend mit den Strings, die der Agent angefasst hat. Sie sind nachweislich die, die im Schussfeld standen.

Wo kommt Lokalisierung ins Spiel?

Eine stille Umformulierung ist in einer Sprache ein Ärgernis und in zehn ein Risiko: Jede Übersetzung, die vom alten Wortlaut abstammt, ist jetzt veraltet, und nichts sagt dir, dass neu übersetzt werden muss.

Hier verstärkt sich der Agent-Vorfall. Lieferst du den umformulierten englischen Text aus, sagen dein Deutsch, Japanisch und Spanisch immer noch das Alte — die Oberflächen widersprechen sich jetzt nicht nur zwischen Screens, sondern zwischen Sprachen. Kataloge, die auseinanderlaufen, sind ein eigener Fehlermodus mit eigenen Lösungen, behandelt in Übersetzungsdateien außer Sync.

Verschlüsselte Texte schließen auch diese Lücke, denn ein geänderter Quell-String ist ein sichtbares Ereignis, an dem seine Übersetzungen hängen, statt ein Literal, das sich still bewegt hat. Das ist das Designprinzip hinter globalize.now: Texte leben im Codebase, single-sourced hinter Schlüsseln, und Lokalisierung ist derselbe Vorgang statt ein Anbau — verbinde ein Repository, und jede Sprache leitet sich aus dieser einen Quelle ab. Teams, die mit KI-Coding-Tools ausliefern, stoßen am frühesten darauf, weshalb wir für Entwickler schreiben und für Menschen, die mit KI-Tools bauen.

Wenn das nächste Mal ein Agent in deinen Komponenten unterwegs ist, entscheidet sich, ob ein geändertes Label als Entscheidung auftaucht oder als Überraschung. globalize.now hält deine für Nutzer sichtbaren Strings single-sourced im Repository, das du verbindest, und leitet jede Sprache aus diesem einen Text ab.

globalize.now konvertiert hartcodierte App-Texte in übersetzungsreife Locale-Dateien und hält sie aktuell, während Sie veröffentlichen.

Probiere globalize.now kostenlos