我一直在 Python 中使用 pywin32 从指定的 Outlook 通讯组列表中提取所有成员的姓名、电子邮件 ID、职位和其他详细信息。最初,代码执行得非常快;尽管我缺乏准确的估计,但它可以在 1-2 分钟内提取甚至 100-200 或更多成员的所有相关详细信息。然而,在我的组织内更换笔记本电脑后,我注意到速度显着下降。现在,类似的输出代码最多需要一个小时。尽管在网上搜索,我还没有发现任何相关提及此类问题。我们将不胜感激您的指导。
代码示例:
outApp = win32com.client.gencache.EnsureDispatch('Outlook.Application').GetNamespace("MAPI")
entries = outApp.AddressLists
dist_lists = entries['All Distribution Lists']
outlookdf=pd.DataFrame(columns=['User Name','Email','Job Level','Location','Department','DL Name'])
dl_names_list = ["<insert name of distribution list here>"]
print("Distribution Lists being extracted are: ")
for i in dl_names_list:
print(str(i))
print("----------------------------")
#########GET DL Names from list and put it in a dataframe
for i in dl_names_list:
print("Distribution List now being extracted: ")
print(str(i))
#initialize widgets
widgets = ['Remaining Time: ', pb.Percentage(), ' ',
pb.Bar(marker=pb.RotatingMarker()), ' ', pb.ETA()]
#initialize timer
timer = pb.ProgressBar(widgets=widgets, maxval=len(dist_lists.AddressEntries.Item(str(i)).GetExchangeDistributionList().Members)).start()
ind = 0
m_list_1 = []
m_list_2 = []
m_list_3 = []
m_list_4 = []
m_list_5 = []
for m in dist_lists.AddressEntries.Item(str(i)).GetExchangeDistributionList().Members:
user=m.GetExchangeUser()
try:
if len(user.Name) > 0 and (user.Name.find(', ') != -1):
value1 = user.Name
m_list_1.append(value1)
value2 = user.PrimarySmtpAddress
m_list_2.append(value2)
value3 = user.JobTitle
m_list_3.append(value3)
value4 = user.OfficeLocation
m_list_4.append(value4)
value5 = user.Department
m_list_5.append(value5)
timer.update(ind)
ind = ind + 1
except:
continue
timer.finish()
print("---------------------------------------------------")
df_m = pd.DataFrame(pd.DataFrame(
{'User Name': m_list_1,
'Email': m_list_2,
'Job Level': m_list_3,
'Location': m_list_4,
'Department': m_list_5
}))
df_m["DL Name"] = str(dist_lists.AddressEntries.Item(str(i)).GetExchangeDistributionList().Name)
outlookdf = pd.concat([outlookdf,df_m])
outlookdf = outlookdf.drop_duplicates()
outlookdf = outlookdf.reset_index(drop = True)
仅在 OOM 中您无能为力 - 使用
AddressEntries
集合,您被迫一次访问一个条目和一个属性。 AddressEntries
对象确实公开了RawTable
属性(返回IMAPITable
MAPI对象),但它不能在Python中使用,您需要C++或Delphi。如果可以选择使用 Redemption (我是其作者),则可以使用 Redemption.MAPITable 对象 - 它允许在一次调用中检索所有值。
在VBS中:
set addrEntries = Application.Session.AddressLists("Offline Global Address List").AddressEntries.Item("Everybody").Members
set Table = CreateObject("Redemption.MAPITable")
Table.Item = addrEntries
'0x39FE001F is PR_SMTP_ADDRESSS, need to specify it as a DASL name for ExecSQL
set Recordset = Table.ExecSQL("SELECT Name, ""http://schemas.microsoft.com/mapi/proptag/0x39FE001F"", JobTitle, OfficeLocation, Department from List")
while not Recordset.EOF
Debug.Print(Recordset.Fields(0).Value & " - " & Recordset.Fields(1).Value & " - " & Recordset.Fields(2).Value & " - " & Recordset.Fields(3).Value & " - " & Recordset.Fields(4).Value)
Recordset.MoveNext
wend