pythonでGmail 本文取得
まずラベルを指定して取得するには
ラベルIDが必要になる
vim base.py
で
from __future__ import print_function import os.path from googleapiclient.discovery import build from google_auth_oauthlib.flow import InstalledAppFlow from google.auth.transport.requests import Request from google.oauth2.credentials import Credentials # If modifying these scopes, delete the file token.json. SCOPES = ['https://www.googleapis.com/auth/gmail.readonly'] import base64, email #デコード用 import dateutil.parser #token.jsonを設定 tokenPath = "token.json" #credentials.jsonを設定 credentialsPath = "credentials.json" #メール本文のデコード def decode(encoded): decoded = base64.urlsafe_b64decode(encoded).decode() return decoded #メール本文の内容を配列で取得する関数 def gmail_get_messages_body(service, labelIdsValue): mailBody = [] # メッセージの一覧を取得 messages = service.users().messages() msg_list = messages.list(userId='me', labelIds=labelIdsValue).execute() # msg_list = messages.list(userId='me', labelIds=labelIdsValue ,maxResults=456).execute() #最大値指定 # 取得したメッセージの一覧を配列に格納 for msg in msg_list['messages']: #メールの受信日時を取得 date = gmail_get_messages_body_date(messages,msg) topid = msg['id'] msg = messages.get(userId='me', id=topid).execute() if(msg["payload"]["body"]["size"]!=0): mailBody.append(date+"<br>"+decode(msg["payload"]["body"]["data"])) else: #メールによっては"parts"属性の中に本文がある場合もある mailBody.append(date+"<br>"+decode(msg["payload"]["parts"][0]["body"]["data"])) return mailBody #gmail_get_messages_body関数内で受信日時を取得する関数 def gmail_get_messages_body_date(messages,msg): msg_id = msg['id'] m = messages.get(userId='me', id=msg_id, format='raw').execute() raw = base64.urlsafe_b64decode(m['raw']) # Emailを解析する eml = email.message_from_bytes(raw) date = dateutil.parser.parse(eml.get('Date')).strftime("%Y-%m-%d_%H-%M-%S") return date #ラベルのIDやnameを表示する関数 def gmail_display_label(service): results = service.users().labels().list(userId='me').execute() labels = results.get('labels', []) if not labels: print('No labels found.') else: print('Labels:') for label in labels: print(label) #初期化(from quickstart.py) def gmail_init(): creds = None # The file token.json stores the user's access and refresh tokens, and is # created automatically when the authorization flow completes for the first # time. if os.path.exists(tokenPath): creds = Credentials.from_authorized_user_file(tokenPath, SCOPES) # If there are no (valid) credentials available, let the user log in. if not creds or not creds.valid: if creds and creds.expired and creds.refresh_token: creds.refresh(Request()) else: flow = InstalledAppFlow.from_client_secrets_file( credentialsPath, SCOPES) creds = flow.run_local_server(port=0) # Save the credentials for the next run with open(tokenPath, 'w') as token: token.write(creds.to_json()) service = build('gmail', 'v1', credentials=creds) return service #ここからやりたい処理を書く service = gmail_init() #quickstart.pyと同じ処理にしてみた results = service.users().labels().list(userId='me').execute() labels = results.get('labels', []) if not labels: print('No labels found.') else: print('Labels:') for label in labels: print(label['name']) gmail_display_label(service)
として
python base.py
を実行すると
ラベルとID一覧が表示される
これでラベルIDがわかったので本文を取得するようにコード変更
from __future__ import print_function import os.path from googleapiclient.discovery import build from google_auth_oauthlib.flow import InstalledAppFlow from google.auth.transport.requests import Request from google.oauth2.credentials import Credentials import base64 import email import dateutil.parser # スコープの設定 SCOPES = ['https://www.googleapis.com/auth/gmail.readonly'] # トークンとクレデンシャルのパス tokenPath = "token.json" credentialsPath = "credentials.json" # メール本文のデコード関数 def decode(encoded): decoded = base64.urlsafe_b64decode(encoded).decode() return decoded # メール本文を取得する関数 def gmail_get_messages_body(service, labelIdsValue): mailBody = [] messages = service.users().messages() msg_list = messages.list(userId='me', labelIds=labelIdsValue).execute() for msg in msg_list['messages']: date = gmail_get_messages_body_date(messages, msg) topid = msg['id'] msg = messages.get(userId='me', id=topid).execute() # メールの本文を取得 if msg["payload"]["body"]["size"] != 0: mailBody.append(date + "<br>" + decode(msg["payload"]["body"]["data"])) elif 'parts' in msg["payload"]: # メール本文が parts 属性にある場合 for part in msg["payload"]["parts"]: if part["body"]["size"] != 0: mailBody.append(date + "<br>" + decode(part["body"]["data"])) break else: mailBody.append(date + "<br> No body content") return mailBody # メールの受信日時を取得する関数 def gmail_get_messages_body_date(messages, msg): msg_id = msg['id'] m = messages.get(userId='me', id=msg_id, format='raw').execute() raw = base64.urlsafe_b64decode(m['raw']) eml = email.message_from_bytes(raw) date = dateutil.parser.parse(eml.get('Date')).strftime("%Y-%m-%d_%H-%M-%S") return date # ラベルの表示関数(変更なし) def gmail_display_label(service): results = service.users().labels().list(userId='me').execute() labels = results.get('labels', []) # Gmail API 初期化関数(変更なし) def gmail_init(): creds = None if os.path.exists(tokenPath): creds = Credentials.from_authorized_user_file(tokenPath, SCOPES) if not creds or not creds.valid: if creds and creds.expired and creds.refresh_token: creds.refresh(Request()) else: flow = InstalledAppFlow.from_client_secrets_file( credentialsPath, SCOPES) creds = flow.run_local_server(port=0) with open(tokenPath, 'w') as token: token.write(creds.to_json()) service = build('gmail', 'v1', credentials=creds) return service # メイン処理 service = gmail_init() gmail_display_label(service) # ラベル ID を指定してメール本文を取得 mail_bodies = gmail_get_messages_body(service, "Label_4") for body in mail_bodies: print(body)
これで
python base.py
とすると
Lavel_4のIDのメールの本文を表示することができる