Martin Hein: Zeichensätze

Hallo Forum,

ich habe eine PHP/MySQL-Anwendung programmiert. Das Frontend ist XHTML
mit UTF8 Charset. Die Daten für die DB habe ich vom Kunden als xls bekommen und als CSV in die DB importiert. Dabei gab es ein Problem:

Als ich unter phpMyAdmin die DB mit allen Tabellen angelegt habe,
habe ich überall, wo ich UTF8 auswählen konnte UTF8 ausgewählt,
um einheitlich nur mit UTF8 zu arbeiten. Danach gingen beim Import
der CSV dummerweise alle Sonderzeichen drauf ;( Daher habe ich in
meiner DB überall latin1 angegeben und im PHP-Quellcode alles, was
ich aus der DB geholt habe für die Darstellung geparsed:

$string = utf8_encode($string);
$string = htmlentities($string, ENT_QUOTES, "UTF-8");

Das ging so. Jetzt gibt es ein Problem:

In der DB sollen zusätzlich russische Schriftzeichen stehen. Wenn ich
die jetzt unter phpMyAdmin mit Copy&Paste einfüge werden mir dort '?'
angezeigt, was mir logisch erscheint, weil der Schriftsatz nicht stimmt.

Kann mir jemand die Lösung verraten, wie die russischen Schriftzeichen
von ...

xls -> csv -> phpmyadmin -> mysql -> php -> xhtml

heil bleiben ?

tausend Dank und

beste gruesse,
martin

  1. echo $begrüßung;

    [Zeichen-Probleme beim Umgang mit MySQL]

    Das MySQL-Handbuch gibt im Kapitel Character Set Support detailliert Auskunft, welche Angaben wo gemacht werden können und was sie bewirken. Besonders wichtig ist zum einen die Einstellung der einzelnen Felder, die angibt, welche Zeichen das Feld aufnehmen kann, und zum anderen die Kodierung der aktuellen Verbindung zum Client (PHP in deinem Fall), die festlegt, gemäß welcher Kodierung ankommende Daten interpretiert werden und wie ausgehende Daten kodiert werden (Stichwort: SET NAMES, bzw. passende Funktionen der MySQL-API (z.B. mysql_set_charset()). Im Grunde genommen muss dich als Client nur deine eigene Verbindungskodierungsaushandlung interessieren, denn MySQL kodiert intern zwischen unterschiedlich konfigurierten Kodierungen selbständig um, so dies technisch möglich ist.

    In der DB sollen zusätzlich russische Schriftzeichen stehen. Wenn ich
    die jetzt unter phpMyAdmin mit Copy&Paste einfüge werden mir dort '?'
    angezeigt, was mir logisch erscheint, weil der Schriftsatz nicht stimmt.

    MySQL hat vermutlich keine Möglichkeit, die fraglichen Zeichen mit der angegebenen Kodierung des Feldes zu speichern. Wenn dort Latin1 eingestellt ist, dann sind die speicherbaren Daten auf Latin1 beschränkt. Andere Zeichen gehen verloren, bzw. landen als Fragezeichen im Feld. Stell die Feld-Kodierung auf eine passende um (z.B. UTF-8, das passt immer). phpMyAdmin kann ansonsten mit der Kodierproblematik umgehen. Auf der Startseite sollte unter "Zeichensatz / Kollation der MySQL-Verbindung" eine UTF-8-Kodierung angegeben werden. Diese  dort angegebenen Kodierung verwendet es (und handelt es vorher mit dem MySQL-Server aus), um Daten an den MySQL-Server zu schicken. Lesend verwendet es generell UTF-8.

    Kann mir jemand die Lösung verraten, wie die russischen Schriftzeichen von ...
    xls -> csv -> phpmyadmin -> mysql -> php -> xhtml
    heil bleiben ?

    Beim Importieren von Dateien über den phpMyAdmin muss die Kodierung der Daten in der Datei im Import-Dialog angegeben werden. Ansonsten musst du dir an jeder Schnittstelle zwischen zwei Systemen klar sein, in welcher Kodierung die Daten ankommen, bzw. welche Kodierung zum Senden verwendet werden soll, und wie der Empfänger über diese Kodierung informiert wird.

    echo $verabschiedung $name";

    1. echo $begrüßung;

      Da aufgrund von Forumsproblemen deine Anwort verlorengegangen ist, und meine Antwort darauf dann nicht mehr angenommen wurde, versuch ich mal aus meinen Gedächtnis deine Antwort zu rekonstruieren. Die Zitate sind also nicht echt, nur sinngemäß.

      phpMyAdmin zeigt nach Umstellung der Felder auf UTF-8 alles richtig an

      Wenn der PMA alle Zeichen richtig anzeigt, kann man davon ausgehen, dass sie in dem betreffenden Feld richtig drinstehen.

      beim Auslesen nun mysql_query('SET NAMES utf8'); eingefügt

      Das ist für den westlichen Raum und den Kodierungen ISO-8859-X und UTF-8 ausreichend. Es gibt für mindestens eine der asiatischen Kodierungen ein Problem bei mysql_real_escape_string(), wenn SET NAMES statt mysql_set_charset() verwendet wurde, aber wenn UTF-8 verwendet wird, ist dieses Problem uninteressant.

      in Richtung HTML htmlentities($string, ENT_COMPAT, 'UTF-8'); eingefügt

      Warum das? Wenn du UTF-8 als Kodierung verwendest und das an den üblichen Stellen (HTTP-Header Content-Typ und als Ersatz im gleichnamigen META-Element) so deklarierst, kannst du dir diese Umwandlung sparen.

      irgendwas funktioniert trotzdem nicht

      Bitte spezifizier das mal genauer. Der Teil zwischen MySQL und PHP sieht ja in Ordnung aus. Aus der Schilderung konnte ich nicht entnehmen, was da jetzt noch nicht funktioniert.

      echo "$verabschiedung $name";