gettext — Dienste für mehrsprachige Internationalisierung

Quellcode: Lib/gettext.py


Das Modul gettext bietet Dienste zur Internationalisierung (I18N) und Lokalisierung (L10N) für Ihre Python-Module und -Anwendungen. Es unterstützt sowohl die GNU gettext Message Catalog API als auch eine höherwertige, klassenbasierte API, die für Python-Dateien besser geeignet sein kann. Die unten beschriebene Schnittstelle ermöglicht es Ihnen, Ihre Modul- und Anwendungsnachrichten in einer natürlichen Sprache zu verfassen und einen Katalog übersetzter Nachrichten bereitzustellen, um sie unter verschiedenen natürlichen Sprachen auszuführen.

Einige Hinweise zur Lokalisierung Ihrer Python-Module und -Anwendungen werden ebenfalls gegeben.

GNU gettext API

Das Modul gettext definiert die folgende API, die der GNU gettext API sehr ähnlich ist. Wenn Sie diese API verwenden, wirken Sie sich global auf die Übersetzung Ihrer gesamten Anwendung aus. Oft ist dies das, was Sie möchten, wenn Ihre Anwendung einsprachig ist und die Sprachauswahl vom Gebietsschema Ihres Benutzers abhängt. Wenn Sie ein Python-Modul lokalisieren oder wenn Ihre Anwendung Sprachen im laufenden Betrieb wechseln muss, möchten Sie wahrscheinlich stattdessen die klassenbasierte API verwenden.

gettext.bindtextdomain(domain, localedir=None)

Bindet die domain an das Gebietsschema-Verzeichnis localedir. Genauer gesagt, gettext sucht nach binären .mo-Dateien für die angegebene Domäne unter Verwendung des Pfads (unter Unix): localedir/language/LC_MESSAGES/domain.mo, wobei language in den Umgebungsvariablen LANGUAGE, LC_ALL, LC_MESSAGES und LANG gesucht wird.

Wenn localedir weggelassen wird oder None ist, wird die aktuelle Bindung für domain zurückgegeben. [1]

gettext.textdomain(domain=None)

Ändert oder fragt die aktuelle globale Domäne ab. Wenn domain None ist, wird die aktuelle globale Domäne zurückgegeben, andernfalls wird die globale Domäne auf domain gesetzt, die dann zurückgegeben wird.

gettext.gettext(message)

Gibt die lokalisierte Übersetzung von message zurück, basierend auf der aktuellen globalen Domäne, Sprache und dem Gebietsschema-Verzeichnis. Diese Funktion wird normalerweise im lokalen Namensraum als _() abgekürzt (siehe Beispiele unten).

gettext.dgettext(domain, message)

Wie gettext(), sucht aber die Nachricht in der angegebenen domain.

gettext.ngettext(singular, plural, n)

Wie gettext(), berücksichtigt aber Pluralformen. Wenn eine Übersetzung gefunden wird, wird die Pluralformel auf n angewendet und die resultierende Nachricht zurückgegeben (einige Sprachen haben mehr als zwei Pluralformen). Wenn keine Übersetzung gefunden wird, wird singular zurückgegeben, wenn n gleich 1 ist; andernfalls wird plural zurückgegeben.

Die Pluralformel stammt aus dem Katalog-Header. Es handelt sich um einen C- oder Python-Ausdruck, der eine freie Variable n hat; der Ausdruck ergibt den Index des Plurals im Katalog. Siehe die GNU gettext Dokumentation für die genaue Syntax, die in .po-Dateien verwendet werden soll, und die Formeln für eine Vielzahl von Sprachen.

gettext.dngettext(domain, singular, plural, n)

Wie ngettext(), sucht aber die Nachricht in der angegebenen domain.

gettext.pgettext(context, message)
gettext.dpgettext(domain, context, message)
gettext.npgettext(context, singular, plural, n)
gettext.dnpgettext(domain, context, singular, plural, n)

Ähnlich wie die entsprechenden Funktionen ohne das p im Präfix (d.h. gettext(), dgettext(), ngettext(), dngettext()), aber die Übersetzung ist auf den angegebenen Nachrichtenkontext beschränkt.

Hinzugefügt in Version 3.8.

Beachten Sie, dass GNU gettext auch eine dcgettext() Methode definiert, diese wurde aber als nicht nützlich erachtet und ist daher derzeit nicht implementiert.

Hier ist ein Beispiel für die typische Verwendung dieser API

import gettext
gettext.bindtextdomain('myapplication', '/path/to/my/language/directory')
gettext.textdomain('myapplication')
_ = gettext.gettext
# ...
print(_('This is a translatable string.'))

Klassenbasierte API

Die klassenbasierte API des Moduls gettext bietet mehr Flexibilität und größeren Komfort als die GNU gettext API. Sie ist die empfohlene Methode zur Lokalisierung Ihrer Python-Anwendungen und -Module. gettext definiert eine GNUTranslations Klasse, die das Parsen von GNU .mo-Formatdateien implementiert und Methoden zur Rückgabe von Zeichenketten besitzt. Instanzen dieser Klasse können sich auch im Built-in-Namensraum als Funktion _() installieren.

gettext.find(domain, localedir=None, languages=None, all=False)

Diese Funktion implementiert den Standard-Algorithmus zur Suche nach .mo-Dateien. Sie nimmt eine domain entgegen, die identisch mit der ist, die textdomain() entgegennimmt. Die optionale localedir ist wie in bindtextdomain(). Die optionale languages ist eine Liste von Zeichenketten, wobei jede Zeichenkette ein Sprachcode ist.

Wenn localedir nicht angegeben ist, wird das Standard-Gebietsschema-Verzeichnis des Systems verwendet. [2] Wenn languages nicht angegeben ist, wird in den folgenden Umgebungsvariablen gesucht: LANGUAGE, LC_ALL, LC_MESSAGES und LANG. Die erste, die einen nicht-leeren Wert zurückgibt, wird für die Variable languages verwendet. Die Umgebungsvariablen sollten eine durch Doppelpunkte getrennte Liste von Sprachen enthalten, die anhand des Doppelpunkts geteilt wird, um die erwartete Liste von Sprachcode-Zeichenketten zu erzeugen.

find() erweitert und normalisiert dann die Sprachen und iteriert durch sie, wobei es nach einer existierenden Datei sucht, die aus diesen Komponenten aufgebaut ist

localedir/language/LC_MESSAGES/domain.mo

Der erste solche Dateiname, der existiert, wird von find() zurückgegeben. Wenn keine solche Datei gefunden wird, wird None zurückgegeben. Wenn all angegeben ist, gibt die Funktion eine Liste aller Dateinamen zurück, in der Reihenfolge, in der sie in der Sprachenliste oder den Umgebungsvariablen erscheinen.

gettext.translation(domain, localedir=None, languages=None, class_=None, fallback=False)

Gibt eine *Translations-Instanz basierend auf domain, localedir und languages zurück, die zuerst an find() übergeben werden, um eine Liste der zugehörigen .mo-Dateipfade zu erhalten. Instanzen mit identischen .mo-Dateinamen werden zwischengespeichert. Die tatsächlich instanziierte Klasse ist class_, falls angegeben, andernfalls GNUTranslations. Der Konstruktor der Klasse muss ein einzelnes Datei-Objekt-Argument entgegennehmen.

Wenn mehrere Dateien gefunden werden, werden spätere Dateien als Fallbacks für frühere verwendet. Um das Einstellen des Fallbacks zu ermöglichen, wird copy.copy() verwendet, um jedes Übersetzungsobjekt aus dem Cache zu klonen; die eigentlichen Instanzdaten werden weiterhin mit dem Cache geteilt.

Wenn keine .mo-Datei gefunden wird, löst diese Funktion OSError aus, wenn fallback falsch ist (was der Standard ist), und gibt eine NullTranslations-Instanz zurück, wenn fallback wahr ist.

Geändert in Version 3.3: IOError wurde früher ausgelöst, es ist jetzt ein Alias von OSError.

Geändert in Version 3.11: Der Parameter codeset wurde entfernt.

gettext.install(domain, localedir=None, *, names=None)

Dies installiert die Funktion _() im Built-in-Namensraum von Python, basierend auf domain und localedir, die an die Funktion translation() übergeben werden.

Für den Parameter names siehe die Beschreibung der Methode install() des Translationsobjekts.

Wie unten gezeigt, markieren Sie normalerweise die Zeichenketten in Ihrer Anwendung, die für die Übersetzung in Frage kommen, indem Sie sie in einen Aufruf der Funktion _() einbetten, wie folgt:

print(_('This string will be translated.'))

Aus Bequemlichkeit möchten Sie, dass die Funktion _() im Built-in-Namensraum von Python installiert wird, damit sie in allen Modulen Ihrer Anwendung leicht zugänglich ist.

Geändert in Version 3.11: names ist jetzt ein Keyword-only-Parameter.

Die Klasse NullTranslations

Übersetzungsklassen sind diejenigen, die tatsächlich die Übersetzung von ursprünglichen Quellcodedatei-Nachrichtenstrings in übersetzte Nachrichtenstrings implementieren. Die Basisklasse, die von allen Übersetzungsklassen verwendet wird, ist NullTranslations; diese stellt die grundlegende Schnittstelle bereit, mit der Sie Ihre eigenen spezialisierten Übersetzungsklassen schreiben können. Hier sind die Methoden von NullTranslations

class gettext.NullTranslations(fp=None)

Nimmt ein optionales Datei-Objekt fp entgegen, das von der Basisklasse ignoriert wird. Initialisiert die "geschützten" Instanzvariablen _info und _charset, die von abgeleiteten Klassen gesetzt werden, sowie _fallback, das über add_fallback() gesetzt wird. Anschließend wird self._parse(fp) aufgerufen, wenn fp nicht None ist.

_parse(fp)

In der Basisklasse eine No-op, diese Methode nimmt das Datei-Objekt fp entgegen und liest die Daten aus der Datei, wodurch ihr Nachrichten-Katalog initialisiert wird. Wenn Sie ein nicht unterstütztes Nachrichten-Katalog-Dateiformat haben, sollten Sie diese Methode überschreiben, um Ihr Format zu parsen.

add_fallback(fallback)

Fügt fallback als Fallback-Objekt für das aktuelle Übersetzungsobjekt hinzu. Ein Übersetzungsobjekt sollte sich auf den Fallback verlassen, wenn es keine Übersetzung für eine gegebene Nachricht bereitstellen kann.

gettext(message)

Wenn ein Fallback gesetzt wurde, wird gettext() an den Fallback weitergeleitet. Andernfalls wird message zurückgegeben. In abgeleiteten Klassen überschrieben.

ngettext(singular, plural, n)

Wenn ein Fallback gesetzt wurde, wird ngettext() an den Fallback weitergeleitet. Andernfalls wird singular zurückgegeben, wenn n 1 ist; andernfalls wird plural zurückgegeben. In abgeleiteten Klassen überschrieben.

pgettext(context, message)

Wenn ein Fallback gesetzt wurde, wird pgettext() an den Fallback weitergeleitet. Andernfalls wird die übersetzte Nachricht zurückgegeben. In abgeleiteten Klassen überschrieben.

Hinzugefügt in Version 3.8.

npgettext(context, singular, plural, n)

Wenn ein Fallback gesetzt wurde, wird npgettext() an den Fallback weitergeleitet. Andernfalls wird die übersetzte Nachricht zurückgegeben. In abgeleiteten Klassen überschrieben.

Hinzugefügt in Version 3.8.

info()

Gibt ein Wörterbuch zurück, das die Metadaten enthält, die in der Nachrichten-Katalogdatei gefunden wurden.

charset()

Gibt die Kodierung der Nachrichten-Katalogdatei zurück.

install(names=None)

Diese Methode installiert gettext() im Built-in-Namensraum und bindet sie an _.

Wenn der Parameter names gegeben ist, muss es sich um eine Sequenz handeln, die die Namen von Funktionen enthält, die Sie zusätzlich zu _() im Builtins-Namensraum installieren möchten. Unterstützte Namen sind 'gettext', 'ngettext', 'pgettext' und 'npgettext'.

Beachten Sie, dass dies nur eine Möglichkeit ist, wenn auch die bequemste, um die Funktion _() für Ihre Anwendung verfügbar zu machen. Da sie sich global auf die gesamte Anwendung und insbesondere auf den Built-in-Namensraum auswirkt, sollten lokalisierte Module niemals _() installieren. Stattdessen sollten sie diesen Code verwenden, um _() für ihr Modul verfügbar zu machen

import gettext
t = gettext.translation('mymodule', ...)
_ = t.gettext

Dies platziert _() nur im globalen Namensraum des Moduls und wirkt sich daher nur auf Aufrufe innerhalb dieses Moduls aus.

Geändert in Version 3.8: 'pgettext' und 'npgettext' hinzugefügt.

Die Klasse GNUTranslations

Das Modul gettext stellt eine zusätzliche Klasse zur Verfügung, die von NullTranslations abgeleitet ist: GNUTranslations. Diese Klasse überschreibt _parse(), um das Lesen von GNU gettext-Format .mo-Dateien sowohl im Big-Endian- als auch im Little-Endian-Format zu ermöglichen.

GNUTranslations parst optionale Metadaten aus dem Übersetzungs-Katalog. Es ist eine Konvention bei GNU gettext, Metadaten als Übersetzung für die leere Zeichenkette einzufügen. Diese Metadaten sind im RFC 822-Stil als Schlüssel: Wert-Paare formatiert und sollten den Schlüssel Project-Id-Version enthalten. Wenn der Schlüssel Content-Type gefunden wird, wird die Eigenschaft charset verwendet, um die "geschützte" Instanzvariable _charset zu initialisieren, standardmäßig None, wenn sie nicht gefunden wird. Wenn die Charset-Kodierung angegeben ist, werden alle Nachrichten-IDs und Nachrichten-Zeichenketten, die aus dem Katalog gelesen werden, unter Verwendung dieser Kodierung in Unicode konvertiert, andernfalls wird ASCII angenommen.

Da auch Nachrichten-IDs als Unicode-Zeichenketten gelesen werden, gehen alle *gettext()-Methoden davon aus, dass Nachrichten-IDs Unicode-Zeichenketten sind, keine Byte-Zeichenketten.

Die gesamte Menge an Schlüssel/Wert-Paaren wird in ein Wörterbuch eingefügt und als "geschützte" Instanzvariable _info gesetzt.

Wenn die magische Zahl der .mo-Datei ungültig ist, die Hauptversionsnummer unerwartet ist oder andere Probleme beim Lesen der Datei auftreten, kann das Instanziieren einer GNUTranslations-Klasse OSError auslösen.

class gettext.GNUTranslations

Die folgenden Methoden werden von der Basisklassenimplementierung überschrieben

gettext(message)

Sucht die Nachrichten-ID message im Katalog und gibt die entsprechende Nachrichten-Zeichenkette als Unicode-Zeichenkette zurück. Wenn kein Eintrag im Katalog für die Nachrichten-ID message vorhanden ist und ein Fallback gesetzt wurde, wird die Suche an die gettext()-Methode des Fallbacks weitergeleitet. Andernfalls wird die Nachrichten-ID message zurückgegeben.

ngettext(singular, plural, n)

Führt eine Pluralformen-Suche einer Nachrichten-ID durch. singular wird als Nachrichten-ID für die Suche im Katalog verwendet, während n zur Bestimmung der zu verwendenden Pluralform verwendet wird. Die zurückgegebene Nachrichten-Zeichenkette ist eine Unicode-Zeichenkette.

Wenn die Nachrichten-ID nicht im Katalog gefunden wird und ein Fallback angegeben ist, wird die Anfrage an die ngettext()-Methode des Fallbacks weitergeleitet. Andernfalls wird, wenn n gleich 1 ist, singular zurückgegeben, und in allen anderen Fällen plural.

Hier ist ein Beispiel

n = len(os.listdir('.'))
cat = GNUTranslations(somefile)
message = cat.ngettext(
    'There is %(num)d file in this directory',
    'There are %(num)d files in this directory',
    n) % {'num': n}
pgettext(context, message)

Sucht den Kontext und die Nachrichten-ID im Katalog nach und gibt den entsprechenden Nachrichtentext als Unicode-Zeichenkette zurück. Wenn kein Eintrag im Katalog für die Nachrichten-ID und den Kontext vorhanden ist und ein Fallback festgelegt wurde, wird die Suche an die pgettext()-Methode des Fallbacks weitergeleitet. Andernfalls wird die Nachrichten-ID zurückgegeben.

Hinzugefügt in Version 3.8.

npgettext(context, singular, plural, n)

Führt eine Pluralform-Suche einer Nachrichten-ID durch. singular wird als Nachrichten-ID für die Suche im Katalog verwendet, während n verwendet wird, um zu bestimmen, welche Pluralform verwendet werden soll.

Wenn die Nachrichten-ID für Kontext nicht im Katalog gefunden wird und ein Fallback angegeben ist, wird die Anfrage an die npgettext()-Methode des Fallbacks weitergeleitet. Andernfalls, wenn n gleich 1 ist, wird singular zurückgegeben, und in allen anderen Fällen wird plural zurückgegeben.

Hinzugefügt in Version 3.8.

Unterstützung für Solaris-Nachrichtenkataloge

Das Solaris-Betriebssystem definiert sein eigenes binäres .mo-Dateiformat, aber da keine Dokumentation zu diesem Format gefunden werden kann, wird es derzeit nicht unterstützt.

Der Katalogkonstruktor

GNOME verwendet eine Version des gettext-Moduls von James Henstridge, aber diese Version hat eine leicht unterschiedliche API. Ihre dokumentierte Verwendung war

import gettext
cat = gettext.Catalog(domain, localedir)
_ = cat.gettext
print(_('hello world'))

Zur Kompatibilität mit diesem älteren Modul ist die Funktion Catalog() ein Alias für die oben beschriebene Funktion translation().

Ein Unterschied zwischen diesem Modul und dem von Henstridge: Seine Katalogobjekte unterstützten den Zugriff über eine Mapping-API, aber dies scheint ungenutzt zu sein und wird daher derzeit nicht unterstützt.

Internationalisierung Ihrer Programme und Module

Internationalisierung (I18N) bezeichnet den Vorgang, durch den ein Programm für mehrere Sprachen sensibilisiert wird. Lokalisierung (L10N) bezeichnet die Anpassung Ihres Programms, sobald es internationalisiert wurde, an die lokale Sprache und kulturelle Gewohnheiten. Um mehrsprachige Nachrichten für Ihre Python-Programme bereitzustellen, müssen Sie die folgenden Schritte unternehmen

  1. bereiten Sie Ihr Programm oder Modul vor, indem Sie übersetzbare Zeichenketten speziell markieren

  2. führen Sie eine Werkzeugsuite über Ihre markierten Dateien aus, um rohe Nachrichten-Kataloge zu generieren

  3. erstellen Sie sprachspezifische Übersetzungen der Nachrichten-Kataloge

  4. verwenden Sie das gettext-Modul, damit Nachrichten-Zeichenketten ordnungsgemäß übersetzt werden

Um Ihren Code für I18N vorzubereiten, müssen Sie sich alle Zeichenketten in Ihren Dateien ansehen. Jede Zeichenkette, die übersetzt werden muss, sollte durch Einpacken in _('...') markiert werden – d.h. ein Aufruf der Funktion _. Zum Beispiel

filename = 'mylog.txt'
message = _('writing a log message')
with open(filename, 'w') as fp:
    fp.write(message)

In diesem Beispiel ist die Zeichenkette 'writing a log message' als übersetzungsfähig markiert, während die Zeichenketten 'mylog.txt' und 'w' dies nicht sind.

Es gibt einige Werkzeuge, um die für die Übersetzung bestimmten Zeichenketten zu extrahieren. Das ursprüngliche GNU gettext unterstützte nur C- oder C++-Quellcode, aber seine erweiterte Version xgettext scannt Code, der in einer Reihe von Sprachen geschrieben ist, einschließlich Python, um als übersetzbar markierte Zeichenketten zu finden. Babel ist eine Python-Internationalisierungsbibliothek, die ein pybabel-Skript zum Extrahieren und Kompilieren von Nachrichten-Katalogen enthält. François Pinards Programm namens xpot erledigt eine ähnliche Aufgabe und ist Teil seines po-utils-Pakets.

(Python enthält auch reine Python-Versionen dieser Programme, genannt pygettext.py und msgfmt.py; einige Python-Distributionen installieren sie für Sie. pygettext.py ist ähnlich wie xgettext, versteht aber nur Python-Quellcode und kann andere Programmiersprachen wie C oder C++ nicht verarbeiten. pygettext.py unterstützt eine Kommandozeilenschnittstelle ähnlich wie xgettext; Details zur Verwendung finden Sie, indem Sie pygettext.py --help ausführen. msgfmt.py ist binärkompatibel mit GNU msgfmt. Mit diesen beiden Programmen benötigen Sie möglicherweise nicht das GNU gettext-Paket, um Ihre Python-Anwendungen zu internationalisieren.)

xgettext, pygettext und ähnliche Werkzeuge generieren .po-Dateien, die Nachrichten-Kataloge sind. Es handelt sich um strukturierte, für Menschen lesbare Dateien, die jede markierte Zeichenkette im Quellcode zusammen mit einem Platzhalter für die übersetzten Versionen dieser Zeichenketten enthalten.

Kopien dieser .po-Dateien werden dann an einzelne menschliche Übersetzer übergeben, die Übersetzungen für jede unterstützte natürliche Sprache schreiben. Sie senden die abgeschlossenen sprachspezifischen Versionen als <language-name>.po-Datei zurück, die mit dem Programm msgfmt in eine maschinenlesbare binäre .mo-Katalogdatei kompiliert wird. Die .mo-Dateien werden vom gettext-Modul für die eigentliche Übersetzungsverarbeitung zur Laufzeit verwendet.

Wie Sie das gettext-Modul in Ihrem Code verwenden, hängt davon ab, ob Sie ein einzelnes Modul oder Ihre gesamte Anwendung internationalisieren. Die nächsten beiden Abschnitte behandeln jeden Fall.

Lokalisierung Ihres Moduls

Wenn Sie Ihr Modul lokalisieren, müssen Sie darauf achten, keine globalen Änderungen vorzunehmen, z. B. am integrierten Namensraum. Sie sollten nicht die GNU gettext-API verwenden, sondern stattdessen die klassenbasierte API.

Nehmen wir an, Ihr Modul heißt „spam“ und die verschiedenen natürlichsprachlichen Übersetzungs-.mo-Dateien des Moduls befinden sich in /usr/share/locale im GNU gettext-Format. Hier ist, was Sie am Anfang Ihres Moduls einfügen würden

import gettext
t = gettext.translation('spam', '/usr/share/locale')
_ = t.gettext

Lokalisierung Ihrer Anwendung

Wenn Sie Ihre Anwendung lokalisieren, können Sie die Funktion _() global in den integrierten Namensraum installieren, normalerweise in der Haupttreiberdatei Ihrer Anwendung. Dies ermöglicht es allen Ihren anwendungsspezifischen Dateien, einfach _('...') zu verwenden, ohne sie explizit in jeder Datei installieren zu müssen.

Im einfachen Fall müssen Sie also nur das folgende Code-Snippet in die Haupttreiberdatei Ihrer Anwendung einfügen

import gettext
gettext.install('myapplication')

Wenn Sie das Locale-Verzeichnis festlegen müssen, können Sie es an die Funktion install() übergeben

import gettext
gettext.install('myapplication', '/usr/share/locale')

Sprachen im laufenden Betrieb ändern

Wenn Ihr Programm viele Sprachen gleichzeitig unterstützen muss, möchten Sie möglicherweise mehrere Übersetzungsinstanzen erstellen und dann explizit zwischen ihnen wechseln, wie folgt

import gettext

lang1 = gettext.translation('myapplication', languages=['en'])
lang2 = gettext.translation('myapplication', languages=['fr'])
lang3 = gettext.translation('myapplication', languages=['de'])

# start by using language1
lang1.install()

# ... time goes by, user selects language 2
lang2.install()

# ... more time goes by, user selects language 3
lang3.install()

Verschobene Übersetzungen

In den meisten Programmierfällen werden Zeichenketten dort übersetzt, wo sie kodiert werden. Gelegentlich müssen Sie jedoch Zeichenketten zur Übersetzung markieren, die eigentliche Übersetzung aber auf später verschieben. Ein klassisches Beispiel ist

animals = ['mollusk',
           'albatross',
           'rat',
           'penguin',
           'python', ]
# ...
for a in animals:
    print(a)

Hier möchten Sie die Zeichenketten in der animals-Liste als übersetzbar markieren, aber sie nicht tatsächlich übersetzen, bis sie gedruckt werden.

Hier ist eine Möglichkeit, diese Situation zu handhaben

def _(message): return message

animals = [_('mollusk'),
           _('albatross'),
           _('rat'),
           _('penguin'),
           _('python'), ]

del _

# ...
for a in animals:
    print(_(a))

Dies funktioniert, weil die Dummy-Definition von _() einfach die Zeichenkette unverändert zurückgibt. Und diese Dummy-Definition überschreibt vorübergehend jede Definition von _() im integrierten Namensraum (bis zum Befehl del). Seien Sie jedoch vorsichtig, wenn Sie eine vorherige Definition von _() im lokalen Namensraum haben.

Beachten Sie, dass die zweite Verwendung von _() „a“ nicht als übersetzbar für das gettext-Programm identifiziert, da der Parameter keine Zeichenketten-Literal ist.

Ein anderer Weg, dies zu handhaben, ist das folgende Beispiel

def N_(message): return message

animals = [N_('mollusk'),
           N_('albatross'),
           N_('rat'),
           N_('penguin'),
           N_('python'), ]

# ...
for a in animals:
    print(_(a))

In diesem Fall markieren Sie übersetzbare Zeichenketten mit der Funktion N_(), die nicht mit einer Definition von _() kollidiert. Sie müssen jedoch Ihr Nachrichtenextraktionsprogramm anweisen, nach übersetzbaren Zeichenketten zu suchen, die mit N_() markiert sind. xgettext, pygettext, pybabel extract und xpot unterstützen dies alle durch die Verwendung des Kommandozeilen-Schalters -k. Die Wahl von N_() ist hier völlig willkürlich; es hätte genauso gut MarkThisStringForTranslation() sein können.

Danksagungen

Die folgenden Personen trugen Code, Feedback, Designvorschläge, frühere Implementierungen und wertvolle Erfahrungen zur Erstellung dieses Moduls bei

  • Peter Funk

  • James Henstridge

  • Juan David Ibáñez Palomar

  • Marc-André Lemburg

  • Martin von Löwis

  • François Pinard

  • Barry Warsaw

  • Gustavo Niemeyer

Fußnoten