Benutzer-Werkzeuge

Webseiten-Werkzeuge


informix:collate_umlaute

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:

  1. 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?
  1. 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?
  1. 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?
  1. 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?
  1. 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:

  1. DB-Locale mit Informationen zur Datenbank ermitteln.
  2. Client-Umgebung prüfen: Locale, Codeset, Terminal-/Applikationskette.
  3. Daten vor und nach Export/Import hexadezimal prüfen.
  4. Relevante String-Operationen gegen erwartete Bytewerte prüfen.
  5. Wenn die Datenbank ein Latin-1-Codeset verwendet, nachsehen, ob der Client tatsächlich Latin-1 liefert oder fälschlich UTF-8 behauptet.
  6. 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:

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

informix/collate_umlaute.txt · Zuletzt geändert: von 127.0.0.1