email.parser: Parsen von E-Mail-Nachrichten¶
Quellcode: Lib/email/parser.py
Nachrichtenobjektstrukturen können auf zwei Arten erstellt werden: sie können von Grund auf neu erstellt werden, indem ein EmailMessage-Objekt erstellt, Header über die Dictionary-Schnittstelle hinzugefügt und Nutzdaten mit set_content() und verwandten Methoden hinzugefügt werden, oder sie können durch Parsen einer serialisierten Darstellung der E-Mail-Nachricht erstellt werden.
Das Paket email stellt einen Standard-Parser bereit, der die meisten E-Mail-Dokumentstrukturen, einschließlich MIME-Dokumente, versteht. Sie können dem Parser ein Bytes-, String- oder Dateiobjekt übergeben, und der Parser gibt Ihnen die Wurzel EmailMessage-Instanz der Objektstruktur zurück. Bei einfachen, nicht-MIME-Nachrichten ist die Nutzlast dieses Wurzelobjekts wahrscheinlich ein String, der den Text der Nachricht enthält. Bei MIME-Nachrichten gibt das Wurzelobjekt True von seiner Methode is_multipart() zurück, und die Unterteile können über die Methoden zur Nutzlastmanipulation, wie get_body(), iter_parts() und walk() abgerufen werden.
Es gibt tatsächlich zwei Parser-Schnittstellen zur Verfügung: die Parser API und die inkrementelle FeedParser API. Die Parser API ist am nützlichsten, wenn Sie den gesamten Text der Nachricht im Speicher haben oder wenn die gesamte Nachricht in einer Datei auf dem Dateisystem liegt. FeedParser ist besser geeignet, wenn Sie die Nachricht aus einem Stream lesen, der möglicherweise auf weitere Eingaben wartet (z. B. beim Lesen einer E-Mail-Nachricht von einem Socket). Der FeedParser kann die Nachricht inkrementell verarbeiten und parsen und gibt das Wurzelobjekt erst zurück, wenn Sie den Parser schließen.
Beachten Sie, dass der Parser in begrenztem Umfang erweitert werden kann und Sie natürlich Ihren eigenen Parser von Grund auf neu implementieren können. Die gesamte Logik, die den gebündelten Parser des Pakets email und die Klasse EmailMessage verbindet, ist in der Klasse Policy verkörpert. Daher kann ein benutzerdefinierter Parser Nachrichtsobjektbäume nach Bedarf erstellen, indem er benutzerdefinierte Versionen der entsprechenden Policy-Methoden implementiert.
FeedParser API¶
Der BytesFeedParser, importiert aus dem Modul email.feedparser, bietet eine API, die für das inkrementelle Parsen von E-Mail-Nachrichten geeignet ist, wie es beim Lesen des Textes einer E-Mail-Nachricht aus einer blockierenden Quelle (z. B. einem Socket) erforderlich wäre. Der BytesFeedParser kann natürlich verwendet werden, um eine E-Mail-Nachricht zu parsen, die vollständig in einem bytes-ähnlichen Objekt, einem String oder einer Datei enthalten ist, aber die BytesParser API ist für solche Anwendungsfälle möglicherweise praktischer. Die Semantik und die Ergebnisse der beiden Parser-APIs sind identisch.
Die API des BytesFeedParser ist einfach: Sie erstellen eine Instanz, füttern sie mit einer Reihe von Bytes, bis keine mehr vorhanden sind, und schließen dann den Parser, um das Wurzelnachrichtenobjekt abzurufen. Der BytesFeedParser ist bei der Verarbeitung von standardkonformen Nachrichten äußerst präzise und leistet sehr gute Arbeit beim Parsen nicht-konformer Nachrichten und liefert Informationen darüber, wie eine Nachricht als fehlerhaft eingestuft wurde. Er füllt das Attribut defects eines Nachrichtenobjekts mit einer Liste aller gefundenen Probleme. Die Liste der Defekte, die er finden kann, finden Sie im Modul email.errors.
Hier ist die API für BytesFeedParser
- class email.parser.BytesFeedParser(_factory=None, *, policy=policy.compat32)¶
Erstellt eine Instanz von
BytesFeedParser. Das optionale _factory ist ein aufrufbares Objekt ohne Argumente; wenn es nicht angegeben wird, wird diemessage_factoryder policy verwendet. _factory wird aufgerufen, wenn ein neues Nachrichtenobjekt benötigt wird.Wenn policy angegeben ist, werden die von ihr festgelegten Regeln verwendet, um die Darstellung der Nachricht zu aktualisieren. Wenn policy nicht gesetzt ist, wird die
compat32-Policy verwendet, die die Abwärtskompatibilität mit der Python 3.2-Version des E-Mail-Pakets aufrechterhält undMessageals Standard-Factory bereitstellt. Alle anderen Policies stellenEmailMessageals Standard-_factory bereit. Weitere Informationen darüber, was policy sonst noch steuert, finden Sie in der Dokumentation zupolicy.Hinweis: **Das Policy-Schlüsselwort sollte immer angegeben werden**; der Standardwert wird in einer zukünftigen Python-Version zu
email.policy.defaultgeändert.Hinzugefügt in Version 3.2.
Geändert in Version 3.3: Das Schlüsselwort policy wurde hinzugefügt.
Geändert in Version 3.6: _factory hat standardmäßig die
message_factoryder Policy.- feed(data)¶
Füttert den Parser mit weiteren Daten. data sollte ein bytes-ähnliches Objekt sein, das eine oder mehrere Zeilen enthält. Die Zeilen können teilweise sein, und der Parser wird solche unvollständigen Zeilen ordnungsgemäß zusammenfügen. Die Zeilen können alle drei gängigen Zeilenenden aufweisen: Wagenrücklauf, Zeilenvorschub oder Wagenrücklauf und Zeilenvorschub (sie können sogar gemischt sein).
- class email.parser.FeedParser(_factory=None, *, policy=policy.compat32)¶
Funktioniert wie
BytesFeedParser, aber die Eingabe für die Methodefeed()muss ein String sein. Dies ist von begrenztem Nutzen, da eine solche Nachricht nur gültig sein kann, wenn sie nur ASCII-Text enthält oder, wennutf8Trueist, keine binären Anhänge enthält.Geändert in Version 3.3: Das Schlüsselwort policy wurde hinzugefügt.
Parser API¶
Die Klasse BytesParser, importiert aus dem Modul email.parser, bietet eine API, die zum Parsen einer Nachricht verwendet werden kann, wenn der vollständige Inhalt der Nachricht in einem bytes-ähnlichen Objekt oder einer Datei verfügbar ist. Das Modul email.parser bietet auch Parser zum Parsen von Strings und reine Header-Parser, BytesHeaderParser und HeaderParser, die verwendet werden können, wenn Sie nur an den Headern der Nachricht interessiert sind. BytesHeaderParser und HeaderParser können in diesen Situationen viel schneller sein, da sie nicht versuchen, den Nachrichtenkörper zu parsen, sondern die Nutzlast auf den rohen Körper setzen.
- class email.parser.BytesParser(_class=None, *, policy=policy.compat32)¶
Erstellt eine Instanz von
BytesParser. Die Argumente _class und policy haben die gleiche Bedeutung und Semantik wie die Argumente _factory und policy des Konstruktors vonBytesFeedParser.Hinweis: **Das Policy-Schlüsselwort sollte immer angegeben werden**; der Standardwert wird in einer zukünftigen Python-Version zu
email.policy.defaultgeändert.Geändert in Version 3.3: Das Argument strict, das in 2.4 als veraltet galt, wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
Geändert in Version 3.6: _class hat standardmäßig die
message_factoryder Policy.- parse(fp, headersonly=False)¶
Liest alle Daten aus dem binären dateiähnlichen Objekt fp, parst die resultierenden Bytes und gibt das Nachrichtenobjekt zurück. fp muss sowohl die Methode
readline()als auch die Methoderead()unterstützen.Die in fp enthaltenen Bytes müssen als Block von RFC 5322 (oder, wenn
utf8Trueist, RFC 6532) formatiert sein, einschließlich Zeilenumbrüchen für fortlaufende Header, optional vorangestellt von einem Envelope-Header. Der Header-Block wird entweder durch das Ende der Daten oder durch eine Leerzeile beendet. Nach dem Header-Block folgt der Body der Nachricht (der MIME-kodierte Unterteile enthalten kann, einschließlich Unterteilen mit einer Content-Transfer-Encoding von8bit).Das optionale headersonly ist ein Flag, das angibt, ob das Parsen nach dem Lesen der Header gestoppt werden soll oder nicht. Der Standardwert ist
False, was bedeutet, dass der gesamte Inhalt der Datei geparst wird.
- parsebytes(bytes, headersonly=False)¶
Ähnlich wie die Methode
parse(), nimmt sie jedoch ein bytes-ähnliches Objekt anstelle eines dateiähnlichen Objekts. Der Aufruf dieser Methode für ein bytes-ähnliches Objekt ist gleichbedeutend mit dem Umwickeln von bytes in eineBytesIO-Instanz und dem Aufrufen vonparse().Das optionale headersonly ist dasselbe wie bei der Methode
parse().
Hinzugefügt in Version 3.2.
- class email.parser.BytesHeaderParser(_class=None, *, policy=policy.compat32)¶
Exakt wie
BytesParser, aber headersonly hat standardmäßig den WertTrue.Hinzugefügt in Version 3.3.
- class email.parser.Parser(_class=None, *, policy=policy.compat32)¶
Diese Klasse ist parallel zu
BytesParser, behandelt aber String-Eingaben.Geändert in Version 3.3: Das Argument strict wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
Geändert in Version 3.6: _class hat standardmäßig die
message_factoryder Policy.- parse(fp, headersonly=False)¶
Liest alle Daten aus dem Text-Modus dateiähnlichen Objekt fp, parst den resultierenden Text und gibt das Wurzelnachrichtenobjekt zurück. fp muss sowohl die Methode
readline()als auch die Methoderead()für dateiähnliche Objekte unterstützen.Abgesehen von der Textmodus-Anforderung funktioniert diese Methode wie
BytesParser.parse().
- parsestr(text, headersonly=False)¶
Ähnlich wie die Methode
parse(), nimmt sie jedoch ein String-Objekt anstelle eines dateiähnlichen Objekts. Der Aufruf dieser Methode für einen String ist gleichbedeutend mit dem Umwickeln von text in eineStringIO-Instanz und dem Aufrufen vonparse().Das optionale headersonly ist dasselbe wie bei der Methode
parse().
- class email.parser.HeaderParser(_class=None, *, policy=policy.compat32)¶
Exakt wie
Parser, aber headersonly hat standardmäßig den WertTrue.
Da das Erstellen einer Nachrichtenobjektstruktur aus einem String oder einem Dateiobjekt eine sehr häufige Aufgabe ist, werden vier Funktionen als Bequemlichkeit bereitgestellt. Sie sind im Namensraum des Top-Level-Pakets email verfügbar.
- email.message_from_bytes(s, _class=None, *, policy=policy.compat32)¶
Gibt eine Nachrichtenobjektstruktur aus einem bytes-ähnlichen Objekt zurück. Dies ist äquivalent zu
BytesParser().parsebytes(s). Die optionalen Argumente _class und policy werden wie beim Konstruktor der KlasseBytesParserinterpretiert.Hinzugefügt in Version 3.2.
Geändert in Version 3.3: Das Argument strict wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
- email.message_from_binary_file(fp, _class=None, *, policy=policy.compat32)¶
Gibt eine Nachrichtenobjektstruktur aus einer geöffneten binären Datei zurück. Dies ist äquivalent zu
BytesParser().parse(fp). _class und policy werden wie beim Konstruktor der KlasseBytesParserinterpretiert.Hinzugefügt in Version 3.2.
Geändert in Version 3.3: Das Argument strict wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
- email.message_from_string(s, _class=None, *, policy=policy.compat32)¶
Gibt eine Nachrichtenobjektstruktur aus einem String zurück. Dies ist äquivalent zu
Parser().parsestr(s). _class und policy werden wie beim Konstruktor der KlasseParserinterpretiert.Geändert in Version 3.3: Das Argument strict wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
- email.message_from_file(fp, _class=None, *, policy=policy.compat32)¶
Gibt eine Nachrichtenobjektstruktur aus einer geöffneten Datei zurück. Dies ist äquivalent zu
Parser().parse(fp). _class und policy werden wie beim Konstruktor der KlasseParserinterpretiert.Geändert in Version 3.3: Das Argument strict wurde entfernt. Das Schlüsselwort policy wurde hinzugefügt.
Geändert in Version 3.6: _class hat standardmäßig die
message_factoryder Policy.
Hier ist ein Beispiel, wie Sie message_from_bytes() in einer interaktiven Python-Sitzung verwenden könnten
>>> import email
>>> msg = email.message_from_bytes(myBytes)
Zusätzliche Hinweise¶
Hier sind einige Hinweise zu den Parsing-Semantiken
Die meisten nicht-multipart-Nachrichten werden als einzelnes Nachrichtenobjekt mit einer String-Nutzlast geparst. Diese Objekte geben
Falsefüris_multipart()zurück, unditer_parts()gibt eine leere Liste zurück.Alle multipart-Nachrichten werden als Container-Nachrichtenobjekt mit einer Liste von Unter-Nachrichtenobjekten für ihre Nutzlast geparst. Die äußere Container-Nachricht gibt
Truefüris_multipart()zurück, unditer_parts()gibt eine Liste von Unterteilen zurück.Die meisten Nachrichten mit einem Content-Typ von message/* (wie message/delivery-status und message/rfc822) werden ebenfalls als Container-Objekte mit einer Listen-Nutzlast der Länge 1 geparst. Ihre Methode
is_multipart()gibtTruezurück. Das einzelne Element, das voniter_parts()geliefert wird, ist ein Unter-Nachrichtenobjekt.Einige nicht-standardkonforme Nachrichten sind möglicherweise nicht intern konsistent bezüglich ihrer multipart-Eigenschaft. Solche Nachrichten haben möglicherweise einen Content-Type-Header vom Typ multipart, aber ihre Methode
is_multipart()kannFalsezurückgeben. Wenn solche Nachrichten mit demFeedParsergeparst wurden, haben sie eine Instanz der KlasseMultipartInvariantViolationDefectin ihrer Attributliste defects. Weitere Details finden Sie inemail.errors.