Yanix im Detail: Mehrsprachigkeit und Dateiformate

28. Dezember 2007 – 15:44

Die Welt ist groß und spricht nicht nur eine Sprache. iBot konnte bisher zwei: Einen wirren Mischmasch aus Deutsch und Englisch. Das wird in Yanix nicht mehr sein.

Ein mächtiges aber effektives System zur Mehrsprachigkeit soll dem Abhilfe schaffen. Über die Realisierung habe ich mir einige Zeit den Kopf zerbrochen. Die meisten PHP-System inkludieren einfach eine PHP-Datei, welche die Definition für viele viele Sprach-Strings enthält. Diese Methode hat jedoch einige Nachteile:

  • Langsam: Erst muss der PHP-Parser über die Datei, dann muss diese noch ausgeführt werden.
  • Groß: Es entsteht durch die PHP-Definitionen sehr viel Code der nicht sein muss. Übersetzer, die vielleicht nicht viel Ahnung von PHP haben, könnten außerdem Code zerstören.
  • Umständlich: Definitionen kopieren, Maskierungen beachten, keine Syntax-Fehler machen usw. Sehr viel Aufwand der eigentlich nicht sein müsste.

Anfangs wollte ich in Yanix viel auf XML-Dateien setzen, jedoch ist das Parsen von diesen in PHP sehr unbequem. Dann fand ich diesen Befehl, mit welchem sich wirklich sehr einfach .ini-Dateien parsen lassen. Dieses Dateiformat ist uralt, aber sehr praktisch: Es unterstützt Sektionen und hat eine sehr einfache Syntax.

Anfangs setzte ich gerne auf diese Funktion und habe viel (Profile, Plugin-Informationen) damit gemacht, doch stoßte auf ein Problem: Die PHP-Funktion ignoriert Zeilen die es für “ungültig” hält und Sektionen muss man extra wählen.

Ich fand in meiner Klassensammlung schnell einen Parser für .ini-Dateien, optimierte ihn und stellte Teile von Yanix darauf um.

Genug von Formaten, zurück zu der Mehrsprachigkeit! Ich habe für die Yanix-Sprachdateien das .ini-Format gewählt, Sprachdateien schauen nun etwa so aus:

1
2
3
4
5
6
[options]
prefix=[PluginController]
 
[strings]
; General
load_failed_file_not_exists=Could not load %plugin%: file not exists

Im Options-Block werden Einstellungen für dne Sprachparser definiert, im Beispiel soll jedem Eintrag bei Abruf der Prefix [PluginController] voran gestellt werden. Variablen können mit %name% definiert werden und werden vom Parser ersetzt.

Ein praktisches Beispiel (in einem Plugin):

Log::Debug($this->Lang('load_failed_file_not_exists', array('plugin' => 'demo')));

In Plugins wird die Methode Lang() der Klasse PluginBase verwendet, von der jedes Plugin erbt. PluginBase hat ein paar Methoden, dazu aber vielleicht ein anderes Mal mehr dazu.

Die Ausgabe der Konsole:

[D 28.12 14:21:51][PluginController] Could not load demo: file not exists

Plugins und Yanix selbst nutzen getrennte Orte zum Speichern der Sprachdateien. Bei Yanix liegen diese im Ordner lang/, bei den Plugins in deren Ordnern.

Eine weitere Möglichkeit, wenn Plugins z.B. sehr viele Sprachstrings brauchen und oft die selben Variablen darin benötigen, ist diese:

1
2
3
4
5
6
7
8
// Namespace definieren ($this->name ist immer der Pluginname)
Lang::UseNamespace($this->name);
// Allgemeine Variablen definieren
Lang::UseVariables(array('plugin' => $this->name, 'foo' => 'bar'));
 
// Sprachstring ausgeben
$string = __('foo');
Log::Debug($string);

Im Moment bin ich noch dabei, das ganze System zu verfeinern und zu optimieren, bis zum Release ist Yanix dann vollständig übersetzbar! :)

Kommentar schreiben