XSLT - UTF-8 - Umlautproblem
gepostet vor 18 Jahre, 2 Monate von Moogly
Hallo,
habe ein Problem mit UTF-8 und Umlauten. Also, ich habe meine MySQL-Datenbank auf utf_8_general_ci und die Verbindung ebenso. Nun erstelle ich ein XML aus diesen Daten und jage es mit einer XSL durch den XSLT von PHP. Danach kommt es, wenn ein Umlaut wie ö,ä oder ü vorhanden ist, zu folgendem Fehler:
Warning: DOMDocument::loadXML() [function.loadXML]: Input is not proper UTF-8, indicate encoding ! Bytes: 0xF6 0x6F 0x67 0x6C in Entity
Die XML hat folgende Form:
öüää
Die XSL ist folgendermaßen aufgebaut:
sl="http://www.w3.org/1999/XSL/Transform">
utput method="html" indent="yes"/>
Die Umlaute oder andere kryptische Zeichen werden auch nicht korrekt angezeigt, wenn ich sie mittels echo ausgebe, in der Datenbank bzw. über PhpMyAdmin werden sie korrekt angezeigt. Lasse ich mir die Kodierung der Ausgabeseite mittels Seiteninfo anzeigen wird dort "UTF-8" angegeben.
Nutze ich ö kommt es zu dem Fehler, dass der XSLT ö als Enitie interpretiert.
Kann mir jemand helfen? Falls notwendig kann ich auch noch den Code meiner XML-Klasse und die Schnittstelle zur XSLT zeigen.
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von knalli
Na klar, du musst die Daten in der Datenbank auch in UTF-8 speichern; und keine HTML-Entities nutzen; nur HTML-Specialchars. Alles andere macht XSLT automatisch. Will heißen: Entweder du migrierst deine Daten manuell, oder nutzt bei jeder Ausgabe eine entsprechene Umformung:
function convertISOToUTF( $text)
{
return htmlspecialchars(utf8_encode(html_entity_decode($text)));
}1. Entities alle entfernen, 2. in utf konvertieren, 3. specials wieder enkodieren (xml: <, >, &)
gepostet vor 18 Jahre, 2 Monate von Moogly
Hi knalli,
wenn ich jetzt PhpMyAdmin nutze, werden die Daten doch automatisch in UTF-8 gespeichert, oder? Was ich nicht verstehe, wenn die Daten schon in UTF-8 gespeichert sind und in der Form an das Script ausgeliefert werden, warum muss man sie dann nochmals konvertieren?
Gruß
Moo
Edit: htmlspecialchars sollte doch auch ö in Ö oder Ö usw. umwandeln, oder? Hab hier das Problem, dass das nicht gemacht wird.
gepostet vor 18 Jahre, 2 Monate von knalli
Ich hab oben im Post ein bisschen iso, utf mit entities durcheinander gewürfelt..
Fakt ist: UTF benötigt eine Auflistung aller Entities und kann nur einige wenige Symbole. ¨ ist ein Symbol (nicht der Code) und ist im UTF nicht verankert - weil eben auch nicht notwendig.
html_entities (ändert <, >, &, ü, ö, usw.. in entities)
htmlspecialchars (ändert NUR <, >, &) weil dies DIE HTML/XML Specialchars sind.
In UTF kann man problemlos ein ü schreiben, problemlos ein é oder ein ² oder ein © oder was auch immer.. das ist ja der Sinn von UTF. Der XSLT Prozessor geht soweit ich das weiß aber hin, und wandelt jene Sonderzeichen in den entsprechenden Entitycode um (#&123.
Alles klar?
gepostet vor 18 Jahre, 2 Monate von Moogly
Jo, und ich glaub ich habe meinen Fehler gefunden. Die PHP Dateien waren mit ANSI codiert, habe sie jetzt in UTF-8 umcodiert. Nun funktionieren Umlaute etc. nur die Sondernzeichen die ich aus der DB ziehe, wollen nicht funktionieren. Woran könnte das denn noch liegen?
Gruß
Moo
Edit: Habe folgendes getestet: Lade ich ein String mit dem Inhalt "öö" aus einer Datei die UTF-8 formatiert ist, hat das XSLT von PHP kein Problem. Lade ich es aus der DB kommt es zu:
Warning: DOMDocument::loadXML() [function.loadXML]: Input is not proper UTF-8, indicate encoding ! Bytes: 0xF6 0xF6 0x3C 0x2F in Entity
gepostet vor 18 Jahre, 2 Monate von knalli
Und du hast die Daten aus der Datenbank gem. meines Funktionsvorschlag umgewandelt?
gepostet vor 18 Jahre, 2 Monate von exe
Genau das Problem hatte ich vor kurzem auch. Lösung war, die Daten in der Datenbank ebenfalls zu UTF-8 zu konvertieren. In meinem Fall habe ich die Daten, die bereits in Form von Dateien ausserhalb der Datenbank vorlagen, zu UTF-8 zu konvertiert und über die UTF-8 unterstützende Anwendung in die auf UTF-8 eingestellte Datenbank geladen.
gepostet vor 18 Jahre, 2 Monate von Moogly
Also ich habe sie mittels Dump eingetragen und habe unten das Charset entfernt. In PhpMyAdmin wird es ja korrekt angezeigt. Dann sollten doch die Daten richtig sein?
@knalli: Wieso soll ich das nochmal utf8_encoden? Die Daten sind ja schon UTF-8. Auch die ganzen PHP Scripte sind jetzt in UTF-8 codiert.
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von knalli
Ja und? Wenn dein UTF-String aber Entities beinhaltet (die zum Beispiel mit html_entites (oder wie die Funktion jetzt heißt) erstellt wurden), dann wird der XSLT zurecht immer noch protestieren; es ist (wie ich eben versuchte zu berichtigen) nicht das Problem UTF, sondern das Problem XML. Bei XML + Utf müssen grundsätzlich nur noch eine Handvoll Zeichen maskiert werden; alle anderen können "so" übernommen werden - nein, MÜSSEN übernommen werden. XHTML hat deshalb (behaupte ich jetzt mal, da ich keine Quelle weiß, macht nur sonst keinen Sinn) auch einen erweiterten Symbol-Entity-Schatz, damit man zB © schreiben kann. Denn die Basis von XML versteht nur & > und <. (und evtl noch was, was so selten gebraucht wird, das ich es vergessen habe).
Also zusammengefasst:
In einem normalen XML mit XSLT hat ein "Überraschung" nichts zu suchen.
Alle Operationen, die früher mit einem html_entity_encode o.ä. formatiert wurden, müssen im XML (nicht DB) nur noch mit einem htmlspecialchar "maskiert" werden. Beispiel: "Tipps & Tricks".
gepostet vor 18 Jahre, 2 Monate von Moogly
Ich habe aber keine Enitites in der Datenbank. Das mit den Entities war nur ein Test ob es evtl. damit funktioniert. Ich schreibe die ganzen Sachen ja aktuell unmaskiert in die Datenbank, aber irgendwo sind die Daten nicht UTF-8. Muss ich Apache bzw. PHP irgendwo noch auf UTF-8 umstellen? Mir gehen langsam echt die Ideen aus, wo noch ISO zwischenfunkt.
Ein weiteres Problem hat sich gerade eben ergeben, und zwar, wenn ich die PHP-SCript im UTF-8 Format abspeichere, dann kann ich kein header("Content-type: text/html; charset=UTF-8"); direkt an den Anfang schreiben, da es immer zu einem Fehler kommt. Dieser Fehler scheint auch bekannt zu sein, gibt es hier evtl. ein Workaround?
Aber erstmal wäre mein oberes Problem wichtiger.
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von knalli
Ja, das ist der sog. BOM-Byte. Abhilfe schafft hier nur die Verwendung eines geeigneten Editors. Aus eigener Erfahrung weiß ich, dass Eclipse damit keinerlei Probleme hat und Notepad++ damit sehr wohl. Bei dir heißt das also: Inhalt nehmen, neue Datei im Editor anlegen und einfügen/speichern.
--
Wie exe eben meinte; bist du sicher, dass deine Daten mittels deiner DB-Schnittstelle auch als UTF kommen? Wenn nicht, MUSST du sie vorher nochmals umwandeln. Nur weil PhpMyadmin das richtig anzeigt, heißt das noch lange nicht, das alles okay ist. Das ist im Endeffekt auch nur eine Ansammlung von PHP-Funktionalitäten, die mir persönlich wenigstens fremd sind.
Testvorschlag:
Alle Dateien in UTF: Datei schreiben, die ein UTF-Sonderzeichen in die Datenbank schreibt; danach es wieder ausliest und es anschließend ausgibt. Ausgabe und PhpMyAdmin gegenprüfen.
gepostet vor 18 Jahre, 2 Monate von Moogly
Habe mal deinen Testvorschlag umgesetzt, hier das Script:
include("config/basic_config.php");
include("classes/class.db.php");
$db = new db_class($db_verbindungen[game_id][0],$db_verbindungen[game_id][1],$db_verbindungen[game_id][2],$db_verbindungen[game_id][3]);
$insert="INSERT INTO ".prefix."test SET text=' '";
if(!$db->db_class_query($insert))
echo "query failed
".$db->db_class_get_last_error()."
";
$abfrage="SELECT text FROM ".prefix."test";
if(!$db->db_class_query($abfrage))
echo "query_failed
".$db->db_class_get_last_error()."
";
while($row = $db->db_class_get_result()) {
$text=$row->text;
echo $text;
}
?>
Die Ausgabe auf der Seite ist korrekt, nur in der DB steht jetzt:
â„‹ â„‹
Welche kostenlose Editoren gibt es denn, die keine Probleme mit diesem "BOM-Byte" haben? Nutze aktuell Rapid PHP 2006, der soll das angeblich können, scheint aber nicht so.
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von knalli
Wenn die Ausgabe korrekt ist, dann ist ja alles okay. Steht die Datenbank/Tabelle/Spalte auf UTF?
PhpMyAdmin muss das ja nicht korrekt anzeigen; alternativ logge dich mal in das Terminal ein, also nutze eine UTF fähige Shell, gehe mit der Konsole rein, stelle sicher, das die Connection UTF nutzt und führe das SELECT durch.
Ehrlich gesagt versteh ich das Problem nicht; ich habe derzeit in der Datenbank noch NonUTF-Werte, weswegen ich die o.g. Konvertierung derzeit immer anwende; wenn ich die Datenbank dann nach UTF "migriere", entfällt das alles bzw wird durch das Specialchars ersetzt (für Ausgaben im XML). Das funktioniert so einwandfrei.
gepostet vor 18 Jahre, 2 Monate von Moogly
Ich glaub ich weiß wo der Fehler bei der Anzeige in PhpMyAdmin liegt. Ich habe "de-utf-8" als Language gewählt, wahrscheinlich sind da nur die deutschen Zeichen enthalten. Naja, kann ich eben keine Textdaten mit PhpMyAdmin eintragen oder ich finde irgendwo einen Punkt wo man PhpMyAdmin auf alle Zeichen von UTF-8 stellen kann.
Danke für die Hilfe.
Wisst ihr noch kostenlose Editoren um diese "BOM-Byte" wegzukriegen?
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von exe
Eclipse
ist kostenlos:
www.eclipse.org
gepostet vor 18 Jahre, 2 Monate von Moogly
Hat irgendwer noch einen Rat woran das in PhpMyAdmin liegen könnte? ODer ist mein Verdacht richtig? Würde gerne PHPmyAdmin zum testen nutzen, darum ist es mir so wichtig.
Gruß
Moo
gepostet vor 18 Jahre, 2 Monate von planetenkiller
wenn wir schon mal beim Thema sind:
ich wollte in der xsl Datei
ü
für das ü verwenden.
In meiner XSL Datei habe ich folgendes ganz oben:
]>
ohne klammern, wegen forum hier.
er meldet zwar keine fehler, aber an der stelle, wo
ü
in der xsl steht, steht bei der ausgabe gar nichts?
ideen?
*edit*:
Für alle die auch probleme mit umlauten haben:
Da bei mir jedes Modul selber den xsl code transformiert und dann in der index.php alle teile im haupt-xsl-template zusammentransformiert werden, gab es bei mir probleme mit den umlauten(Format: &-#228; für ä (ohne bindestrich)) und auch das speichern der dateien in UTF-8 funktionierte nicht. Dann habe ich in der index.php, wo die Modul-funktion aufgefrufen wird ein utf8_decode() davor gehänt, und es geht jetzt.