【问题标题】:Extracting HTML table data from email to csv file, 1st column values to row headers, using Python使用 Python 将 HTML 表格数据从电子邮件提取到 csv 文件,将第一列值提取到行标题
【发布时间】:2021-04-26 15:37:22
【问题描述】:

我正在尝试通读 Outlook 文件夹并获取 ReceivedTime、CC、Subject、HTMLBody,但将表格提取到列中。我可以将 1) ReceivedTime,CC,Subject,HTMLBody 拉到一个数据框中,我可以这样做 2) 将 HTMLBody 表提取到一个数据框中,但我无法同时执行 1) 和 2)。

当前代码:

import win32com.client
import pandas as pd
from bs4 import BeautifulSoup


outlook = win32com.client.Dispatch("Outlook.Application")
mapi = outlook.GetNamespace("MAPI")

inbox = mapi.Folders[User@email.com'].Folders['Inbox'].Folders['Subfolder Name']
Mail_Messages = inbox.Items

for mail in Mail_Messages:
     receivedtime = mail.ReceivedTime.strftime('%Y-%m-%d %H:%M:%S')
     cc = mail.CC
     body = mail.HTMLBody
     html_body = BeautifulSoup(body,"lxml")
     html_tables = html_body.find_all('table')[0]

df = pd.read_html(str(html_tables),header=None)[0]
display(df)

当前数据框显示如下。但我也想要相关的 ReceivedTime、CC 和主题。

0 1
0 Report Name Report.pdf
1 Team Name Team A
2 Project Name Project A
3 Unique ID Number 123456789
4 Due Date 1/1/2021

但希望列 [0] 改为行标题。因此,当每封电子邮件被读取时,它会为收件箱子文件夹中的所有电子邮件生成一个如下所示的数据框:

0 Report Name Team Name Project Name Unique ID Number Due Date ReceivedTime CC Subject
1 Report.pdf Team A Project A 123456789 1/5/2021 1/1/2021 4:38:44 AM User1@email.com, User2@email.com Action Required:Report A Coming due
2
3
4

但是我被卡住了,仍然是一个初学者,但是我看到的所有其他帖子并没有完全让我明白我正在尝试做的事情。我很感激这方面的任何帮助。

【问题讨论】:

  • 所以您只想转置一个数据帧(带有 html_body 内容),然后加入另一个数据帧(带有 CC,接收时间)到它?那么这可能对你有帮助:stackoverflow.com/questions/42381639/… 和这个:stackoverflow.com/questions/33088010/…
  • anilewe,谢谢你,我试过了,但仍然不是我想要的。我想从电子邮件中提取接收时间、抄送、主题和正文。在电子邮件正文中有一个标准表格,我想将表格数据分成 5 个附加列(看起来像上面的第二个表格)。所以也许我会以错误的方式去做。我在循环遍历所有电子邮件的 HTMLBody 并将 html 表拆分为仍与接收时间、抄送和主题相关的其他列时遇到问题。
  • 我看错了你的问题,对不起。看看我的回答,是不是这个意思?这可能不是最有效的方法,但至少是一种有效的方法。

标签: python pandas beautifulsoup win32com


【解决方案1】:

试试这个:

import win32com.client
import pandas as pd
from bs4 import BeautifulSoup
from pprint import pprint

outlook = win32com.client.Dispatch("Outlook.Application")
mapi = outlook.GetNamespace("MAPI")

inbox = mapi.Folders['User@email.com'].Folders['Inbox'].Folders['Subfolder Name']
Mail_Messages = inbox.Items

# a list where contents of each e-mail - CC, receiv.time and subject will have been put
contents = []
column_names = ['Report Name', 'Team Name', 'Project Name', 'Unique ID Number', 'Due Date', 'ReceivedTime', 'CC', 'Subject']

for mail in Mail_Messages:

    body = mail.HTMLBody
    html_body = BeautifulSoup(body, "lxml")
    html_tables = html_body.find_all('table')

    # uncomment following lines if you want to have column names defined programatically rather than hardcoded
    # column_names = pd.read_html(str(html_tables), header=None)[0][0]
    # column_names = column_names.tolist()
    # column_names.append("CC")
    # column_names.append("Received Time")
    # column_names.append("Subject")

    # a list containing a single e-mail data - html table, CC, receivedTime and subject
    row = pd.read_html(str(html_tables), header=None)[0][1]
    row = row.tolist()
    row.append(mail.CC)
    row.append(mail.ReceivedTime.strftime('%Y-%m-%d %H:%M:%S'))
    row.append(mail.Subject)

    # appending each full row to a list
    contents.append(row)


# and finally converting a list into dataframe
df = pd.DataFrame(contents, columns=column_names)

pprint(df)

【讨论】:

  • anilewe 非常感谢!这正是我想要做的,你的代码工作得很好!你救了我可能又一个星期的挫折,谢谢你!
猜你喜欢
  • 1970-01-01
  • 2015-12-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-01-24
  • 2023-04-05
  • 2022-06-21
  • 1970-01-01
相关资源
最近更新 更多