Eddie: MySQL 4 => 5 (UTF-8-Sonderzeichen-Problem)

Liebe SelfHTMLer,

ich stehe kurz vor dem Relaunch meiner Seite, nach 2 Jahren reichlich Arbeit. Nur mit einem Problem habe ich noch zu kämpfen und würde mich da sehr über Input freuen.

Konkret geht es darum, eine uralte Seite (11 Jahre!) mit uralter MySQL-DB auf einen halbwegs tragfähgigen Stand zu bringen, nämlich

  • MySQL 5.5.28 mit
  • <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
  • und UTF8-Output.
    Aber wie nicht anders zu erwarten, habe ich gerade mit Sonderzeichen zu kämpfen.

Das Setting sieht ungefähr so aus:

Alte Datenbank:

MySQL 4.1.22, Tabellen-Kollation: latin1_swedish_ci

Neue Datenbank:

MySQL 5.5.28, Tabellen-Kollation: (noch) latin1_swedish_ci, was wahrscheinlich das Hauptproblem ist

.htaccess

AddDefaultCharset utf-8

HTML-Head:

<meta http-equiv="content-type" content="text/html; charset=utf-8" />

Ich hoffe, ich habe nichts vergessen. Das Problem bei mir ist, dass ich mir schon garnicht sicher bin, welche dieser Parameter sinnvoll oder (un)nötig sind. Das heißt, ich weiß nicht, wie ich sinnvoll und mit reduzierten Einflussfaktoren an die Sache rangehe.

Mein Ziel ist logischerweise,
a) dass das "ö" aus der alten DB in der neuen Datenbank nicht als "öh" erscheint, sondern als "ö"
b) dass der User die Daten als UTF8 bekommt und auch ein "ö" sieht.

Für jeden Hinweis bin ich sehr dankbar. Auch wenn ihr bspw. brauchbare Tutorials kennt, die einen nicht nur blöd gucken lassen (Thema Collation, da geht mir das so). Oder vielleicht ist es ja total simpel und die Lösung liegt auf der Hand, wär ich natürlich auch froh drüber ;-)

Eddie

  1. Tach!

    Alte Datenbank:

    MySQL 4.1.22, Tabellen-Kollation: latin1_swedish_ci

    MMySQL-Versionen vor 4.5 hatten nur eine generelle Einstellung zur Zeichenkodierung. Für Tabellen oder Spalten konnte da noch nichts weiter individuell eingestellt werden.

    Neue Datenbank:

    MySQL 5.5.28, Tabellen-Kollation: (noch) latin1_swedish_ci, was wahrscheinlich das Hauptproblem ist

    Das Hauptproblem ist, dass das Zeichenkodierungskonzept stark aufgebort worden ist. Man kann an vielen Stellen eine Kodierungsangabe setzen, manche sind nur Default-Werte für andere Stellen, beispielsweise die Tabellen-Kodierung. Bitte lies erstmal den umfangreichen Teil zur Zeichenkodierung in unserem Wiki, besonders den Bereich zu MySQL.

    Ich hoffe, ich habe nichts vergessen. Das Problem bei mir ist, dass ich mir schon garnicht sicher bin, welche dieser Parameter sinnvoll oder (un)nötig sind. Das heißt, ich weiß nicht, wie ich sinnvoll und mit reduzierten Einflussfaktoren an die Sache rangehe.

    Das wird hoffentlich durch die Lektüre klarer. Dazu brauchst du auch noch die Abschnitte zu Webdokumenten und zum Webserver.

    Mein Ziel ist logischerweise,
    a) dass das "ö" aus der alten DB in der neuen Datenbank nicht als "öh" erscheint, sondern als "ö"

    Der Dump der alten Datenbank ist Latin1-kodiert, was einem Windows-1252 entspricht. Wenn du diese Daten in die neue Datenbank importierst, musst du diese Zeichenkodierung angeben, damit der Einleser sie richtig interpretieren kann.

    b) dass der User die Daten als UTF8 bekommt und auch ein "ö" sieht.

    Und dann musst du beim Auslesen auch noch angeben, welche Kodierung du gern hättest. Das wird aber (hoffentlich) alles klarer nach der empfohlenen Lektüre.

    Für jeden Hinweis bin ich sehr dankbar. Auch wenn ihr bspw. brauchbare Tutorials kennt, die einen nicht nur blöd gucken lassen (Thema Collation, da geht mir das so).

    Bitte konkret nachfragen, wenn was unklar geblieben ist.

    dedlfix.

    1. Der Dump der alten Datenbank ist Latin1-kodiert, was einem Windows-1252 entspricht. Wenn du diese Daten in die neue Datenbank importierst, musst du diese Zeichenkodierung angeben, damit der Einleser sie richtig interpretieren kann.

      ... oder er macht den Dump (sowohl export als auch import) mit dem MySqlDumper Vers. >= 1.24, soweit ich weiß, berücksichtigt der das (nahezu) automatisch. Jedenfalls ist im dortigen Support ein ganzes Thema sehr ausführlich genau der Problematik des TO gewidmet.

      Mik

    2. Prima, danke, dedlfix! Das war genau der richtige Einstiegspunkt!

      Das folgende Zitat (das sich nur auf MySQL bezieht!) kann ich jedenfalls bestätigen, denn so schlimm wie gedacht, war's zum Schluss garnicht:

      "Insgesamt gibt es 10 verschiedene Stellen, an denen eine Zeichenkodierung konfiguriert oder angegeben werden kann. Das hört sich schlimmer an, als es am Ende ist."

      Sehr geholfen bei der praktischen Umsetzung hat mir dann noch dies hier, in genau der Reihenfolge:

      http://ronaldbradford.com/blog/migrating-mysql-latin1-to-utf8-preparation-2010-02-11/
      http://ronaldbradford.com/blog/migrating-mysql-latin1-to-utf8-preparation-2-2010-02-22/
      http://ronaldbradford.com/blog/migrating-mysql-latin1-to-utf8-the-process-2010-03-06/

      So, jetzt muss ich noch projektweit die htmlentities() rausschmeißen, dann ist gut :-)

      Bei Interesse: aus sehr, sehr alt mach neu (User: Reisender, Pwd: Schluesselloch).

      Nächtlicher Gruss,
      Eddie

      1. Om nah hoo pez nyeetz, Eddie!

        So, jetzt muss ich noch projektweit die htmlentities() rausschmeißen, dann ist gut :-)

        Aber nicht komplett, sondern durch htmlspecialchars() ersetzen, denn einige Zeichen müssen zwingend ersetzt werden, damit am Ende kein Müll entsteht.

        Matthias

        --
        Der Unterschied zwischen Java und JavaScript ist größer als der zwischen schwer und Schwerin.