Inhaltsverzeichnis
Informix: Codeset, Collation und deutsche Umlaute
Ziel und Rahmen
Diese Notiz beschreibt die operative Ursache von Problemen mit deutschen Umlauten in Informix aus Sicht eines System- oder Datenbankadministrators. Der Schwerpunkt liegt nicht auf der Sprachtheorie, sondern auf den tatsächlichen Betriebsebenen:
- wie die Datenbank Zeichen kodiert,
- welche Rolle die Locale spielt,
- wo die eigentliche Ursache in Client/Server-Konvertierung liegt,
- wann eine Collation nur die Sortierung beeinflusst und wann sie in Wirklichkeit ein Encoding-Problem maskiert.
Wichtig: In Informix sind Codeset und Collation getrennte Konzepte. Eine falsche Annahme, sie seien identisch oder austauschbar, erzeugt die typischen Umlaut-Fehler.
1. Locale-Architektur in GLS
Informix verwendet GLS (Global Language Support). Eine Locale hat die Form:
Sprache_Territorium.Codeset[@Modifikator]
Typische Beispiele:
- ll_CC.819
- ll_CC.819@dict
- ll_CC.utf8
- ll_CC.57372
Die Bestandteile bedeuten:
- Sprache/Territorium: sprachliche und regionale Defaults, z. B. Datumsformate, Meldungen, kulturelle Regeln
- Codeset: definierte Byte-Tabelle für die gespeicherten Zeichen
- Modifikator: Vergleichs- und Sortierregeln, z. B. @dict
Das Entscheidende:
- Codeset bestimmt das Speicherformat in CHAR/VARCHAR/LVARCHAR.
- Collation bestimmt Vergleich, Sortierung und semantische Ordnung.
- Die Collation ist keine zweite Kodierung, sondern eine Vergleichslogik.
2. Codeset vs. Collation: die zentrale Trennung
2.1 Codeset
Der Codeset beschreibt, welche Bytes in der Datenbank für ein Zeichen verwendet werden. Beispiel für ISO-8859-1 / IBM CCSID 819:
- Ä = C4
- Ö = D6
- Ü = DC
- ä = E4
- ö = F6
- ü = FC
- ß = DF
In UTF-8 dagegen sind dieselben Zeichen mehrere Bytes, beispielsweise:
- ä = C3 A4
- ö = C3 B6
- ü = C3 BC
Das bedeutet: Die logische Rune „ü“ kann in verschiedenen Codesets als unterschiedliche Bytefolge erscheinen. Deshalb ist der tatsächliche Fehler oft ein Encoding-Mismatch, nicht ein Unicode-Problem der Datenbank selbst.
2.2 Collation
Die Collation beschreibt, wie Zeichen verglichen und sortiert werden. Sie betrifft SQL-Regeln wie:
- ORDER BY
- BETWEEN
- LIKE, je nach Typ und Locale
- Unique-Index-Validierung
- Range- und Partitionierungslogik
- Replikations- und Vergleichssemantik je nach Definition
Ein Modifikator wie @dict ändert nicht das gespeicherte Byte für ü, sondern nur die Reihenfolge, in der Zeichen als vergleichbar bzw. sortierbar behandelt werden.
Praktisch:
- 819 und 819@dict sind identisch in der Byte-Tabelle.
- 819@dict kann die Sortierung ändern.
- 819@dict ändert nicht FC zu einem anderen Byte.
- Ein Wechsel des Codesets (819 → UTF-8 oder umgekehrt) ändert dagegen das physische Bytebild der Daten.
3. DB_LOCALE und CLIENT_LOCALE
Der Ablauf ist immer:
Anwendung → CLIENT_LOCALE → GLS-Konvertierung → DB_LOCALE → Datenseite / Chunk
3.1 CLIENT_LOCALE
CLIENT_LOCALE beschreibt die Zeichenkodierung, mit der die Anwendung die Zeichen an den Server sendet. Ein Client kann Latin-1, UTF-8, UCS-2 oder ein anderer von GLS unterstützter Codeset verwenden.
3.2 DB_LOCALE
DB_LOCALE beschreibt den Codeset der Datenbank selbst. Sobald die Daten in die Datenbank gelangen, werden sie im DB-Codeset gespeichert. Die Datenbank selbst kennt nur diese interne Byte-Repräsentation.
3.3 Konvertierung
Wenn Client und Datenbank unterschiedliche Codesets verwenden, führt Informix eine Konvertierung durch. Das ist genau die Stelle, an der viele Fehler entstehen.
Beispiele:
- Client sendet UTF-8-C3-BC für ü, DB erwartet 819: die Konvertierung wird zu FC erwartet, sofern alle Locales korrekt gesetzt sind.
- Client sendet Latin-1 FC, DB erwartet UTF-8: der Server wandelt FC nach UTF-8, wenn die Konvertierung korrekt ist.
- Client behauptet UTF-8, liefert aber Latin-1-Bytes oder umgekehrt: Die Konvertierung interpretiert die Faustdaten fälschlich, und das Ergebnis ist Mojibake.
Das ist genau die Ursache, wenn im Feld plötzlich „ü“ oder andere verzerrte Zeichen auftauchen.
4. Warum @dict kein Encoding-Problem ist
Der häufigste Fehler im operativen Umgang ist die falsche Gleichsetzung von Collation und Encoding.
Korrekt:
- @dict ist Sortier-/Vergleichsregeln.
- 819 ist das Code-Schema.
Falsch:
- @dict geändert das Byte für „ü“.
- @dict macht aus einem latin-1-Byte ein UTF-8-Zeichen.
Diese Annahmen sind technisch falsch.
Beispiel:
- ll_CC.819 und ll_CC.819@dict speichern ü als FC, sofern der Codeset unverändert bleibt.
- Nur die Vergleichsregeln und die Reihenfolge bei ORDER BY, BETWEEN und ähnlichen Operationen ändern sich.
Wenn Umlaute in einer Datenbank falsch erscheinen, ist der Fehler in der Regel nicht @dict, sondern:
- falscher DB_LOCALE beim CREATE DATABASE,
- falscher CLIENT_LOCALE,
- falsche Umgebungsvariablen beim Import/Export,
- Fehlinterpretation der Bytes durch ein Werkzeug.
5. Was auf der Platte wirklich liegt
Informix speichert im Regelfall keine abstrakten „Buchstaben“, sondern Bytefolgen im DB-Codeset. Für 819 gilt:
- ä = E4
- ö = F6
- ü = FC
- Ä = C4
- Ö = D6
- Ü = DC
- ß = DF
Wer in einer 819-DB einen Ausdruck wie 'Müller' speichert, speichert in Wirklichkeit eine Bytefolge wie:
- M
- ü = FC
- l
- l
- e
- r
Das ist nicht UTF-8, keine kombinierende Darstellung und kein „U+00FC plus Trema“ in einem Zeichensatz-Container. Es ist einfach das DB-Byte.
Das ist der Kernpunkt für Betrieb und Diagnose:
- Wenn der Codeset 819 ist, ist ein Umlaut ein Latin-1-Byte.
- Wenn der Codeset UTF-8 ist, wird derselbe logische Buchstabe als zweibyte-Sequenz gespeichert.
6. Einfluss auf Länge, LIKE, Substring und Unique
Die Collation beeinflusst nicht die physische Bytefolge, aber sie wirkt auf die Semantik.
6.1 LENGTH und Substring
Bei 819 ist ein deutsches Zeichen ein einzelnes Byte. Ein Wert wie 'Müller' hat in einer 819-DB eine andere Byte-Länge als in einer UTF-8-DB.
Das ist operational wichtig:
- CHAR- und VARCHAR-Längen können im Vergleich zu UTF-8 deutlich anders aussehen,
- Substring-Operationen auf Bytes/Zeichen müssen vor dem Hintergrund des Codesets verstanden werden,
- bei Exporten/Imports oder dbload-Workflows muss die Byte-Kodierung konsistent sein.
6.2 LIKE und Vergleichslogik
Collation beeinflusst, wie SQL-Engines Zeichen als „gleich“ oder in einer Reihenfolge behandeln. Damit können Werte in WHERE, ORDER BY, BETWEEN und Unique-Prüfungen unterschiedlichen Vergleichsergebnissen unterliegen, obwohl die gespeicherten Bytes identisch sind.
Dieser Effekt ist besonders deutlich bei:
- Groß-/Kleinschreibung
- Umlaute und Sonderzeichen
- Sortierung in Dictionary-Order
- Vergleichsregeln über Sprache/Gebiet
Bei CHAR und VARCHAR richtet sich die normale Vergleichsreihenfolge grundsätzlich nach der Codeset-Reihenfolge; ein in der Locale definierter Modifikator wie @dict kann die Sortierregeln beeinflussen. NCHAR und NVARCHAR verwenden die lokalisierte Kollationsreihenfolge der Datenbank-Locale. Die genaue Wirkung hängt von DB_LOCALE und dessen Collation ab; deshalb sollten Sortierung und Vergleiche mit den tatsächlich verwendeten Datentypen getestet werden.
Je nach Locale und Kollationsregeln können ß und ss beziehungsweise Ä und Ae oder A beim Sortieren ähnlich oder gleich gewichtet werden. Eine ähnliche Sortierposition bedeutet jedoch nicht automatisch, dass die Werte bei = oder in einem Unique-Index als gleich gelten. Diese Fälle separat mit ORDER BY, Gleichheitsvergleichen und gegebenenfalls einem Test-Unique-Index prüfen.
6.3 Unique-Index und Replikation
Wenn die Collation zwei Werte als gleich behandelt, kann ein Unique-Index den zweiten Datensatz ablehnen, obwohl die Bytefolgen auf den ersten Blick unterschiedlich aussehen. Das ist ein Kollationsproblem, kein Codepage-Problem.
Dasselbe gilt bei Replikation und ER: Die Vergleichssemantik und die lokale DB-Locale der beteiligten Kataloge und Tabellen müssen für die beteiligten Datenbanken konsistent sein. Eine scheinbar reine Sortierfrage kann sich als Vergleichs-/Katalogproblem zeigen.
Ändert eine logische Migration die Locale oder die zugrunde liegenden Vergleichsregeln, müssen die Indizes in der Zieldatenbank unter diesen Regeln angelegt werden. Vorhandene Indexstrukturen nicht ungeprüft übernehmen: nach dem Import die betroffenen B-Tree-Indizes und Unique-Bedingungen kontrollieren und sie bei Bedarf mit dem für die Informix-Version vorgesehenen Verfahren neu aufbauen, notfalls durch Löschen und erneutes Anlegen. Eine physische Wiederherstellung derselben Datenbank-Locale ist davon zu unterscheiden.
7. Typische Betriebssymptome
7.1 Mojibake
Beispiel: Ein Client sendet UTF-8-C3-BC, der Server erwartet 819, und die Daten werden als zwei falsche Latin-1-Bytes interpretiert. Ergebnis: Zeichen wie ü, ä, ö oder ähnliches.
Typische Ursache:
- falscher CLIENT_LOCALE,
- falscher Client-Charset,
- ein Tool, das Bytes als UTF-8 ausgibt, obwohl der Server 819 erwartet,
- UNLOAD/dbload mit inkonsistenter Locale-Mischung.
7.2 Abgeschnittene Strings
Wenn UTF-8-Sequenzen in einen 819-Server oder umgekehrt in die falsche Definition geraten, können die Zeichen als ungültig oder unvollständig interpretiert werden. Das führt zu:
- abgeschnittenen Werten,
- falschen String-Längen,
- Umlautverlusten,
- Fehlern bei String-Funktionen.
7.3 Falscher Sortier-/Eindeutigkeitsfehler
Diese Fälle sind häufig ein Kollationsproblem:
- ORDER BY liefert rätselhafte Reihenfolge,
- Umlaute erscheinen an unerwarteter Stelle,
- Unique-Index verhält sich nach Collation, nicht nach Byte-Byte-Logik,
- BETWEEN schließt Werte ein/aus, die bei reiner Byte-Logik nicht zusammenpassen.
8. Relevante operative Regeln
8.1 Die Besonderheit: Collation wird beim CREATE DATABASE fixiert
Die entscheidende Eigenschaft von Informix-GLS ist: Die Locale der Datenbank, inklusive der Collation, wird beim CREATE DATABASE in die Datenbankstruktur eingepflanzt und bleibt für die Existenz der Datenbank relevant. Das gilt nicht nur für den Sprach-Default, sondern auch für die Vergleichs- und Sortiersemantik der DB.
Das bedeutet praktisch:
- Nach dem CREATE DATABASE ist die DB-Locale nicht nur eine Umgebungsvariable, sondern ein Bestandteil der Datenbank-Identität.
- Ein späteres SET mit anderen Variablen oder ein geändertes Shell-Environment ändert die gespeicherten Daten nicht.
- Die Datenbank selbst bleibt in der bereits festgelegten Locale-Definition verankert.
Dies ist der Grund, warum eine „Collation-Korrektur“ nachträglich nicht einfach über eine Environment-Variable oder einen einmaligen SET-Block erfolgen kann. Sobald die DB mit einem bestimmten Codeset und einer bestimmten Collation angelegt wurde, ist die physische und semantische Grundlage der Datenbank damit fixiert.
8.2 Warum Environment-Änderungen keine Korrektur sind
Die häufige falsche Annahme lautet: „Ich ändere DB_LOCALE oder CLIENT_LOCALE und die DB sortiert dann anders.“ Das ist nur für neue Verbindungen und neue Konvertierungen relevant, nicht für die bereits in der Datenbank gespeicherten Bytes und nicht für die bereits definierte DB-Locale.
Das ist ein wichtiger Punkt:
- DB_LOCALE bestimmt den internen Codedata-Storage der DB.
- CLIENT_LOCALE bestimmt die Interpretation der Client-Daten.
- Eine angepasste Umgebung kann nur den Zugriff und die Konvertierung auf dem Weg steuern.
- Sie kann eine bestehende DB nicht in eine andere Collation umwandeln, solange die DB nicht neu angelegt oder in einer kompatiblen Ziel-DB migriert wurde.
Kurz gesagt: Environment-Variablen sind nur die Konvertierungs- und Verbindungslogik; sie sind keine Definition der bereits gespeicherten DB-Semantik.
8.3 Die Abhängigkeit zwischen CLIENT_LOCALE, DB_LOCALE und Collation
Die operative Abhängigkeit ist:
- CLIENT_LOCALE muss zur tatsächlichen Kodierung der Anwendungsdaten passen.
- DB_LOCALE muss zum tatsächlichen DB-Codeset passen.
- Die Collation bestimmt Sortier-/Vergleichsregeln nur innerhalb dieses fixierten Codesets.
Wenn diese drei Seiten nicht zusammenpassen, ist der Effekt:
- fehlerhafte Konvertierung an der Client-/Server-Grenze,
- falsche Interpretation der Bytes,
- irreführende ORDER BY-/LIKE-/Unique-Ergebnisse,
- scheinbar „verschiedene Umlauten“ bei identischen Bytes,
- Fehler bei Imports/Exports und bei Replikations-/ER-Prozessen.
8.4 Warum eine Korrektur oft nur über neue DB oder Migration geht
Wenn eine DB mit dem falschen Codeset oder falscher Collation erstellt wurde, dann ist das Problem nachträglich nicht nur eine Frage der aktuellen Umgebung. Die logische Ursache liegt in der zu früh festgelegten DB-Locale und im fehlenden konsistenten Client-/Server-Codepfad.
In der Praxis ist die saubere Korrektur meist:
- neue Ziel-DB mit gültiger DB_LOCALE und entsprechender Collation,
- konsistente CLIENT_LOCALE beim Transfer,
- sauberer Import/Export oder Copy-Workflow,
- Prüfung der gespeicherten Bytes vor und nach dem Transfer,
- Verifikation der Sortierung und Vergleichssemantik in der neuen DB.
Bei dbexport/dbimport die erzeugte Schema-Datei im Exportverzeichnis vor dem Import prüfen. Sie kann das ursprüngliche CREATE DATABASE-Statement und damit die bisherige Locale enthalten; nicht ungeprüft annehmen, dass dbimport automatisch die gewünschte Ziel-Locale verwendet. Falls nötig, den Datenbankkopf in der Schema-Datei auf die Zieldefinition anpassen. DB_LOCALE muss zur Ziel-Datenbank passen; CLIENT_LOCALE muss beim Export und Import jeweils zur tatsächlichen Kodierung der Textdateien passen. Nach dem Import Daten, Collation-Verhalten und neu angelegte Indizes verifizieren.
8.5 Praktischer DBA-Check: Host, Client und DB
Ein valider Admin-Workflow für die Diagnose sieht typischerweise so aus:
- Host-Umgebung prüfen
- Welche Locale ist im Betriebssystem gesetzt?
- Welche Werte tragen DB_LOCALE, CLIENT_LOCALE, LANG, LC_ALL?
- Ist das erwartete Codeset wirklich aktiv, oder wird ein anderes Umwelt-Setting übernommen?
- Client-Umgebung prüfen
- Welche Zeichenkodierung nutzt die Anwendung wirklich?
- Gibt das Client-Tool bzw. die Sprache tatsächlich UTF-8 oder Latin-1 aus?
- Werden beim Schreiben von Daten die Bytes eindeutig in der erwarteten Kodierung erzeugt?
- DB-Locale prüfen
- Welche DB_LOCALE gilt für die Datenbank?
- Welcher Codeset ist für die Tabelle bzw. Datenbank festgelegt?
- Ist die DB bereits mit einem anderen Codeset oder einem anderen Modifikator angelegt worden?
- Reale Daten prüfen
- Hex- oder Byte-Ausgabe der betroffenen Spalten prüfen.
- Ist ein ü als FC im 819-Format sichtbar oder wird eine UTF-8-Sequenz erwartet?
- Wurden beim Import/Export Rohbytes falsch interpretiert?
- Semantik prüfen
- ORDER BY, BETWEEN, LIKE, Unique-Checks separat auf Kollation testen.
- Wenn die Sorte logisch auffällig ist, liegt die Ursache oft beim Modifikator / @dict.
- Wenn die gespeicherten Bytes verfälscht sind, liegt die Ursache eher am Codeset-Mismatch.
8.6 Diagnostische Unterscheidung: Codeset-Problem vs. Collation-Problem
Ein typischer Entscheidungsbaum:
- Fehler zeigt sich als „verzerrte Zeichen“ oder „Mojibake“
→ wahrscheinliches Codeset-/Konvertierungsproblem
- Fehler zeigt sich als „falsche Sortierung“ oder „verwirrte Eindeutigkeit“
→ wahrscheinliches Collation-Problem
- Die Bytes in der DB sind technisch korrekt, aber ORDER BY oder Unique-Checks wirken falsch
→ Collation oder Locale-Semantik ist die Ursache
- Die Bytes in der DB sind technisch falsch, obwohl die gleiche Bedeutung erwartet wurde
→ codeset-/CLIENT_LOCALE-/DB_LOCALE-Mismatch
8.7 Zielgerichtete Korrekturstrategie
Im Betrieb sollte die Korrektur immer dem Ursachepfad folgen:
- Wenn die DB in einem falschen Codeset angelegt wurde, muss man die Datenbasis in eine korrekt definierte Ziel-DB migrieren.
- Wenn nur die Konvertierung zwischen Client und DB falsch ist, reicht oft eine konsistente Locale-Konfiguration.
- Wenn nur die Sortierung falsch ist, liegt eine Collation- und Vergleichssemantikfrage vor, nicht ein Unicode-Transferproblem.
8.8 Betriebsregel in Kurzform
- Collation wird bei CREATE DATABASE festgelegt und ist nicht nachträglich einfach „umzuschalten“.
- DB_LOCALE legt das eigentliche Speicher-Codeset der Datenbank fest.
- CLIENT_LOCALE legt die Codierung der Client-Daten fest.
- Nur die Kombination aus korrekter DB_LOCALE, korrekter CLIENT_LOCALE und der passenden Collation liefert konsistente Umlaute und stabile Vergleiche.
Wenn zwei dieser Ebenen nicht zusammenpassen, entstehen die typischen Probleme mit ä, ö, ü, ß und anderen Sonderzeichen.
8.9 Runbook: Symptom → Ursache → Prüfung → Korrektur
Symptom A: Zeichen werden als ü, ä, ö dargestellt
Ursache:
- UTF-8-Bytes werden in eine 819-DB oder als Latin-1 interpretiert.
Prüfung:
locale env | grep -E 'LANG|LC_|CLIENT_LOCALE|DB_LOCALE'
SELECT name, LENGTH(name) FROM TABLE_NAME WHERE name LIKE '%M%';
Korrektur:
export CLIENT_LOCALE=en_US.819 export DB_LOCALE=en_US.819
Falls die Datenbank bereits im falschen Codeset steht, keine reine Laufzeitkorrektur, sondern neue DB oder sauberer Transfer planen.
Symptom B: ORDER BY oder Unique zeigt falsche Reihenfolge
Ursache:
- Collation / @dict entspricht nicht den erwarteten Vergleichsregeln.
Prüfung:
SELECT col FROM tab ORDER BY col; SELECT col, COUNT(*) FROM tab GROUP BY col HAVING COUNT(*) > 1;
Korrektur:
- DB-Locale mit passender Collation neu definieren oder passende Ziel-DB anlegen.
- Nicht allein durch CLIENT_LOCALE beheben.
Symptom C: Import/Export zeigt Umlaute erst nach Transfer falsch
Ursache:
- Prozess- oder Tool-Kodierung inkonsistent.
Prüfung:
file datafile hexdump -C datafile | head
Korrektur:
- Daten explizit mit passender CLIENT_LOCALE/DB_LOCALE transferieren.
- Lade-/Export-Tools mit gleicher Kodierung konfigurieren.
9. Interner Runbook-Block
Problem
Umlaute oder Sonderzeichen werden im Informix-System falsch dargestellt, sortieren falsch oder erzeugen Unique-/Vergleichsfehler.
Ursache
Die häufigste Ursache ist keine fehlende Informix-Funktionalität, sondern ein Mismatch zwischen:
- DB_LOCALE,
- CLIENT_LOCALE,
- realer Client-Kodierung,
- angelegter DB-Collation beim CREATE DATABASE.
Prüfung
locale env | grep -E 'LANG|LC_|CLIENT_LOCALE|DB_LOCALE'
SELECT name, VALUE FROM sysmaster:sysdbslocale WHERE name IN ('dbs_collate', 'dbs_cset');
SELECT col, LENGTH(col), col = 'Müller' AS eq_mueller, col = 'Muller' AS eq_muller FROM tab LIMIT 10;
SELECT col FROM tab ORDER BY col;
file exportfile hexdump -C exportfile | head
Diagnose
- Wenn Zeichen verzerrt sind: Codeset-/Konvertierungsproblem wahrscheinlich.
- Wenn Sortierung/Unique falsch ist: Collation-/@dict-Problem wahrscheinlich.
- Wenn die DB bereits existiert und die Locale beim CREATE DATABASE falsch war: keine reine Laufzeit-Umstellung, sondern neue DB oder Migration.
Lösung
export CLIENT_LOCALE=en_US.819 export DB_LOCALE=en_US.819
Oder mit UTF-8:
export CLIENT_LOCALE=en_US.utf8 export DB_LOCALE=en_US.utf8
Wenn die Datenbank bereits mit einem falschen Codeset oder falscher Collation angelegt wurde:
CREATE DATABASE db_new WITH LOG DB_LOCALE = 'en_US.819@dict' CLIENT_LOCALE = 'en_US.819';
Danach Daten mit konsistenter Locale transferieren und die Ergebnisse erneut prüfen.
Verifikation
SELECT col, LENGTH(col), col = 'Müller' AS eq_mueller, col = 'Muller' AS eq_muller FROM tab ORDER BY col;
locale
Erwartung:
- Umlaute werden konsistent dargestellt,
- Sortierung entspricht der definierten Collation,
- Vergleichssemantik stimmt mit der DB-Locale überein,
- keine neuen Verzerrungen beim Transfer.
10. Diagnostik im Betrieb
Für den Admin ist die wichtigste Frage nicht „Ist @dict aktiv?“, sondern:
- Welche DB_LOCALE gilt für die Datenbank?
- Welcher Codeset wird auf dem Client verwendet?
- Werden die Daten tatsächlich im gleichen Codeset geschrieben und gelesen?
- Werden beim Import/Export Bytes mit einer falschen Interpretation behandelt?
9.1 Richtige Prüfungen
Checkliste:
- DB-Locale mit Informationen zur Datenbank ermitteln.
- Client-Umgebung prüfen: Locale, Codeset, Terminal-/Applikationskette.
- Daten vor und nach Export/Import hexadezimal prüfen.
- Relevante String-Operationen gegen erwartete Bytewerte prüfen.
- Wenn die Datenbank ein Latin-1-Codeset verwendet, nachsehen, ob der Client tatsächlich Latin-1 liefert oder fälschlich UTF-8 behauptet.
- Sortier- und Vergleichsregeln separat prüfen, da @dict die Sortierung ändern kann, aber nicht das physische Zeichen selbst.
9.2 Beispielhafte Logik
Wenn ein ü in der Datenbank anstelle von UTF-8-C3-BC als FC auftaucht, ist der Speicher korrekt für 819. Wenn der Client aber UTF-8-Strings liefert und der Server 819 erwartet, entsteht ein Konvertierungsfehler. Das muss am Übergang korrigiert werden, nicht durch einen Collation-Wechsel.
10. 1-Seiten-Checkliste für den Betrieb
Kurzfassung
- Problem = falsch dargestellte Umlaute, falsche Sortierung oder Unique-/Vergleichsfehler.
- Ursache = Mismatch zwischen DB_LOCALE, CLIENT_LOCALE und realer Client-Kodierung; ggf. falsche DB-Locale beim CREATE DATABASE.
- Wichtig = Collation kann nur innerhalb eines bereits fest definierten Codesets wirksam werden; sie ändert keine gespeicherten Bytes.
Schnellprüfung
locale env | grep -E 'LANG|LC_|CLIENT_LOCALE|DB_LOCALE'
SELECT name, VALUE FROM sysmaster:sysdbslocale WHERE name IN ('dbs_collate', 'dbs_cset');
Entscheidungsregel
- Verzerrte Zeichen = Codeset-/Konvertierungsproblem
- Falsche Reihenfolge / Unique-Fehler = Collation-/@dict-Problem
- DB existiert bereits mit falscher Locale = neue DB oder Migration nötig
Korrektur
export CLIENT_LOCALE=en_US.819 export DB_LOCALE=en_US.819
Oder:
export CLIENT_LOCALE=en_US.utf8 export DB_LOCALE=en_US.utf8
Wenn die DB bereits falsch angelegt wurde:
CREATE DATABASE db_new WITH LOG DB_LOCALE = 'en_US.819@dict' CLIENT_LOCALE = 'en_US.819';
Verifikation
SELECT col, LENGTH(col), col = 'Müller' AS eq_mueller, col = 'Muller' AS eq_muller FROM tab ORDER BY col;
Erwartung:
- Zeichen korrekt dargestellt,
- Vergleichs- und Sortiersemantik passen zur DB-Locale,
- keine neuen Konvertierungsfehler beim Transfer.
11. IBM-Referenzen
Die folgenden IBM-Dokumentationsstellen sind die maßgeblichen offiziellen Referenzen für die Kernregeln von Informix GLS und Locales:
- IBM Informix Documentation: DB_LOCALE: Beschreibt die Datenbank-Locale und die Beziehung zwischen Locale, Codeset und gespeicherten Zeichen.
- IBM Informix Documentation: CLIENT_LOCALE: Beschreibt die Client-Seite und die GLS-Konvertierung an der Client-/Server-Grenze.
- IBM Informix Documentation: GLS und Locales: Beschreibt Codeset-, Collation- und localebezogene Regeln.
- IBM Informix Documentation: CREATE DATABASE und Locale: Beschreibt die Einbettung der Datenbank-Locale beim Anlegen der Datenbank.
- IBM Informix Documentation: Zeichensatzkonvertierung: Beschreibt, dass die Konvertierung nach Codeset und nicht nach Collation erfolgt.
Hinweis: IBM-Dokumentation kann je nach Version und Produktseite leicht verlinkt werden; die oben genannten Referenzen sind die offiziellen Einstiegspunkte für die hier beschriebenen Funktionen.
11. Schlussfolgerung
Das entscheidende technische Ergebnis lautet:
- Deutsche Umlaute sind in einer 819-DB nicht „nicht unterstützt“.
- Sie werden als einzelne Latin-1-Bytes im Codeset gespeichert.
- Der Fehler entsteht typischerweise durch falsche Locale- und Codeset-Kombinationen auf Client/Server-Grenze.
- @dict beeinflusst Sortierung und Vergleich, nicht das physische Byte.
- Für die operative Analyse muss man immer zwischen Datenspeicherung, Collation und Client-/Server-Umsetzung sauber trennen.
Nur wenn Codeset, Collation und Client-Locale zusammenpassen, funktionieren ä, ö, ü, ß korrekt in Informix.
12. Konkrete Konfigurationsbeispiele
12.1 Typische Umgebungsvariablen
Beispiel für eine Linux-/bash-Umgebung, in der der Client als UTF-8 arbeitet und die DB als 819 erwartet:
export LANG=en_US.UTF-8 export LC_ALL=en_US.UTF-8 export CLIENT_LOCALE=en_US.utf8 export DB_LOCALE=en_US.819
Beispiel für eine Latin-1-/819-Spezifikation im Client:
export LANG=en_US.ISO8859-1 export LC_ALL=en_US.ISO8859-1 export CLIENT_LOCALE=en_US.819 export DB_LOCALE=en_US.819
Wichtig: Diese Werte sind nur richtig, wenn die Anwendung wirklich exakt in diesem Codeset arbeitet. Ein falscher oder „nur vermuteter“ Wert erzeugt echte Byte-Verzerrungen.
12.2 Beispiel für CREATE DATABASE mit fixierter Locale
CREATE DATABASE dbname WITH LOG IN dbspace1 DB_LOCALE = 'en_US.819@dict' CLIENT_LOCALE = 'en_US.819' MODE ANSI;
Oder ebenfalls üblich:
CREATE DATABASE dbname WITH LOG DB_LOCALE = 'en_US.819' CLIENT_LOCALE = 'en_US.utf8';
Das ist der kritische Punkt: Nach dem CREATE DATABASE ist diese Locale für die DB fest. Ein späteres Setzen von CLIENT_LOCALE oder DB_LOCALE in der Shell ändert die bereits vorhandenen Daten nicht.
12.3 Beispiel für eine sichere SQL-Prüfung der DB-Locale
SELECT name, VALUE FROM sysmaster:sysdbslocale WHERE name IN ('dbs_collate', 'dbs_cset');
Wenn die DB definiert ist, zeigt die Datenbankkataloginformation, welcher Codeset und welche Collation für die DB gelten. Das ist der richtige Nachweis, nicht die aktuelle Shell-Umgebung.
12.4 Beispiel für einen Host-/Client-Check
echo "$LANG" echo "$LC_ALL" echo "$CLIENT_LOCALE" echo "$DB_LOCALE" locale
Prüfungen, die in der Praxis sinnvoll sind:
locale charmap iconv --list | grep -Ei 'UTF-8|ISO-8859-1|IBM-819'
Wenn der Client als UTF-8 deklariert ist, aber tatsächlich Latin-1-Bytes ausliefert, ist die Konvertierung falsch, obwohl die Shell-Umgebung „gut“ aussieht.
12.5 Testbeispiele für Codeset und Umlaut
Beispiel A: Datenbank ist 819, Client ist korrekt als 819 gesetzt.
CREATE TABLE test_umlaut ( id SERIAL, name VARCHAR(50) ); INSERT INTO test_umlaut(name) VALUES ('Müller'); SELECT name, LENGTH(name) FROM test_umlaut;
Erwartung:
- Der Wert wird als Latin-1-Byte im DB-Codeset abgelegt.
- LENGTH ist an der gespeicherten Byte-Länge orientiert; bei 819 ist „ü“ ein einzelnes Byte.
Beispiel B: Client liefert UTF-8, DB erwartet 819.
SET CLIENT_LOCALE 'en_US.utf8'; INSERT INTO test_umlaut(name) VALUES ('Müller');
Wenn die Client-Umgebung nicht exakt mit den tatsächlich gesendeten Bytes übereinstimmt, kann der String als falsche Bytefolge interpretiert werden. Der Gefahrensignal: sichtbare Verzerrung, Spracheingang fehlerhaft, Abweichungen bei LENGTH oder ORDER BY.
12.6 Test für Sortierung ohne Encoding-Wechsel
CREATE TABLE test_sort ( id SERIAL, name VARCHAR(20) ); INSERT INTO test_sort(name) VALUES ('Muller'), ('Müller'), ('Muller2'); SELECT name FROM test_sort ORDER BY name;
Erwartung:
- Die Reihenfolge hängt von Collation und codesetbezogener Vergleichslogik ab.
- Das ist ein Vergleichsproblem, nicht automatisch ein Zeichen-/Byteproblem.
12.7 Test für sichere Konvertierung bei Export/Import
Beispiel für einen Import-Workflow mit festem Client-Codeset:
export CLIENT_LOCALE=en_US.819 export DB_LOCALE=en_US.819 # Beispiel: Export mit konsistentem Format # Danach Import in die Ziel-DB mit derselben DB_LOCALE
Wenn Import/Export mit widersprüchlichen Locales läuft, wird das Zeichenmaterial falsch geordnet oder verfälscht.
12.8 Typischer Verifikations-Block nach einer Änderung
SELECT name, LENGTH(name), name = 'Müller' AS match_1, name = 'Muller' AS match_2 FROM test_umlaut; SELECT name FROM test_sort ORDER BY name;
Ziel dieser Prüfung:
- Sind die gezeigten Bytes und Zeichen konsistent?
- Stimmt die Sortierung zur erwarteten Collation?
- Ist die DB-Locale wirklich die gewünschte und nicht nur ein Shell-Setting?
12.9 Praktischer Entscheidungsbaum
1. Werden Zeichen verzerrt dargestellt? Ja -> Codeset-/Konvertierungsproblem prüfen Nein -> Sortier-/Collation-Problem prüfen 2. Sind Daten in DB bereits gespeichert? Ja -> DB_LOCALE und DB-Definition prüfen, kein bloßes SET erwartet Nein -> CREATE DATABASE / locale-Definition erneut prüfen 3. Ist CLIENT_LOCALE konsistent mit den tatsächlich gelieferten Bytes? Nein -> Client- oder Import-Fehler Ja -> DB_LOCALE prüfen 4. Ist ORDER BY / LIKE / Unique inkonsistent? Ja -> Collation und @dict prüfen Nein -> auf Export/Import oder Anwendungskodierung schauen
12.10 Betriebskorrektur in der Praxis
Minimaler, robuster Ablauf:
# 1. Umgebung prüfen locale env | grep -E 'LANG|LC_|CLIENT_LOCALE|DB_LOCALE' # 2. Ziel-DB mit korrekter Locale anlegen # CREATE DATABASE ... DB_LOCALE = 'en_US.819@dict' # 3. Client auf dieselbe Semantik stellen export CLIENT_LOCALE=en_US.819 # 4. Daten transferieren, danach Byte- und Vergleichsprüfungen durchführen
Wichtig: Wenn die vorhandene DB bereits im falschen Codeset bzw. mit falscher Collation erstellt wurde, ist eine reine Laufzeit-Umstellung meistens keine saubere Lösung. Dann ist eine neue, korrekt definierte DB oder eine glasklare Migration die belastbare Korrektur.
13. Schlagwörter
Informix, GLS, Locale, DB_LOCALE, CLIENT_LOCALE, Codeset, Collation, @dict, ISO-8859-1, CCSID-819, Latin-1, UTF-8, Unicode, deutsche Umlaute, äöüß, Byte-Repräsentation, Datenbankspeicher, ORDER BY, BETWEEN, LIKE, Unique-Index, String-Länge, Substring, Mojibake, dbload, UNLOAD, Import, Export, Replication, ER, Encoding, Character Conversion, Client-Server-Konvertierung, Datenbankadministrator, Troubleshooting, CREATE DATABASE, locale-check, hex-dump, shell-environment
