2013-07-26 7 views
39

wydaje się łatwo dostaćPython: Jak analizować organizmie z surowego email, biorąc pod uwagę, że surowe e-mail nie ma „ciało” tag lub cokolwiek

From 
To 
Subject 

etc poprzez

import email 
b = email.message_from_string(a) 
bbb = b['from'] 
ccc = b['to'] 

przy założeniu, że "a" jest ciągiem surowych wiadomości e-mail, który wygląda mniej więcej tak.

a = """From [email protected] Thu Jul 25 19:28:59 2013 
Received: from a1.local.tld (localhost [127.0.0.1]) 
    by a1.local.tld (8.14.4/8.14.4) with ESMTP id r6Q2SxeQ003866 
    for <[email protected]>; Thu, 25 Jul 2013 19:28:59 -0700 
Received: (from [email protected]) 
    by a1.local.tld (8.14.4/8.14.4/Submit) id r6Q2Sxbh003865; 
    Thu, 25 Jul 2013 19:28:59 -0700 
From: [email protected] 
Subject: oooooooooooooooo 
To: [email protected] 
Cc: 
X-Originating-IP: 192.168.15.127 
X-Mailer: Webmin 1.420 
Message-Id: <[email protected]> 
Date: Thu, 25 Jul 2013 19:28:59 -0700 (PDT) 
MIME-Version: 1.0 
Content-Type: multipart/mixed; boundary="bound1374805739" 

This is a multi-part message in MIME format. 

--bound1374805739 
Content-Type: text/plain 
Content-Transfer-Encoding: 7bit 

ooooooooooooooooooooooooooooooooooooooooooooooo 
ooooooooooooooooooooooooooooooooooooooooooooooo 
ooooooooooooooooooooooooooooooooooooooooooooooo 

--bound1374805739--""" 

KWESTIA

jak można uzyskać Body tego maila za pośrednictwem Python?

Do tej pory jest to jedyny znany mi kod, ale muszę go jeszcze przetestować.

if email.is_multipart(): 
    for part in email.get_payload(): 
     print part.get_payload() 
else: 
    print email.get_payload() 

Czy to jest właściwy sposób?

czy może coś jest prostsze, takie jak ...

import email 
b = email.message_from_string(a) 
bbb = b['body'] 

?

Odpowiedz

50

Zastosowanie Message.get_payload

b = email.message_from_string(a) 
if b.is_multipart(): 
    for payload in b.get_payload(): 
     # if payload.is_multipart(): ... 
     print payload.get_payload() 
else: 
    print b.get_payload() 
+0

@GagandeepSingh, Dziękuję za poprawne. – falsetru

+1

W każdym razie, aby to pokazać w zdekodowanym zwykłym tekście? –

+1

Nieważne! Zdałem sobie sprawę, że mogę po prostu użyć biblioteki base64 i zrobić base64.b64decode() –

4

Nie ma b['body'] w Pythonie. Musisz użyć get_payload.

if isinstance(mailEntity.get_payload(), list): 
    for eachPayload in mailEntity.get_payload(): 
     ...do things you want... 
     ...real mail body is in eachPayload.get_payload()... 
else: 
    ...means there is only text/plain part.... 
    ...use mailEntity.get_payload() to get the body... 

Powodzenia.

39

Aby być bardzo pozytywnym, należy pracować z rzeczywistą treścią e-maila (ale wciąż z możliwością, że nie parsujesz prawej części), musisz pominąć załączniki i skoncentrować się na części zwykłej lub html (w zależności od potrzeby) do dalszego przetwarzania.

Ponieważ przed wymienionego osprzętu może, a często są text/gładkie lub tekstu/część html, to nie kuloodporne próbki pomija te sprawdzając nagłówki treści Disposition:

b = email.message_from_string(a) 
body = "" 

if b.is_multipart(): 
    for part in b.walk(): 
     ctype = part.get_content_type() 
     cdispo = str(part.get('Content-Disposition')) 

     # skip any text/plain (txt) attachments 
     if ctype == 'text/plain' and 'attachment' not in cdispo: 
      body = part.get_payload(decode=True) # decode 
      break 
# not multipart - i.e. plain text, no attachments, keeping fingers crossed 
else: 
    body = b.get_payload(decode=True) 

okazji , walk() iteruje cudownie na częściach mime, a get_payload(decode=True) robi brudną pracę przy dekodowaniu base64 itd. Dla ciebie.

Niektóre tła - jak sugerowałem, wspaniały świat wiadomości MIME przedstawia wiele pułapek "niesłusznego" znajdowania treści wiadomości. W najprostszym przypadku jest to część "tekstowa/zwykła", a metoda get_payload() jest bardzo kusząca, ale nie żyjemy w prostym świecie - często jest ona otoczona treścią wieloczęściową/alternatywną, pokrewną, mieszaną itp.Wikipedia opisuje to ściśle - MIME, ale biorąc pod uwagę wszystkie poniższe przypadki są ważne - i powszechne - należy wziąć pod uwagę sieci bezpieczeństwa:

Bardzo często - prawie wszystko, co dostajesz w normalnym edytorze (Gmail, Outlook) tekst z przystawką:

multipart/mixed 
| 
+- multipart/related 
| | 
| +- multipart/alternative 
| | | 
| | +- text/plain 
| | +- text/html 
| |  
| +- image/png 
| 
+-- application/msexcel 

Stosunkowo prosta - po prostu alternatywa reprezentacji:

multipart/alternative 
| 
+- text/plain 
+- text/html 

Na dobre czy na złe, struktura ta jest również ważna:

multipart/alternative 
| 
+- text/plain 
+- multipart/related 
     | 
     +- text/html 
     +- image/jpeg 

Mam nadzieję, że to trochę pomaga.

P.S. Chodzi mi o to, że nie podchodzisz do e-maili lekko - gryzie, kiedy najmniej się tego spodziewasz :)

+3

Dziękuję za ten dokładny przykład i za sprecyzowanie ostrzeżenia - w przeciwieństwie do zaakceptowanej odpowiedzi. Myślę, że jest to o wiele lepsze/bezpieczniejsze podejście. –