【发布时间】:2022-09-30 04:41:18
【问题描述】:
我有一个较旧的 Python 项目,它使用标准 IMAP 机制从邮箱中检索电子邮件等进行处理。不幸的是,随着 MS365 现在淘汰非 OAuth2 和非现代身份验证,我必须尝试编写一个不依赖用户凭据但具有对身份验证等的完全访问权限的应用程序,就像其他使用 OAuth2 的用户一样。
我已将 MSAL 库部分关闭,并且可以从远程获取访问令牌 - 此应用程序配置了使用客户端密码登录的工作流,并且可以访问所有用户的所有 EWS 和应用程序中的所有 IMAP.UseAsApp的权限。不过,通过应用程序集成,我可能会错误地请求信息。
该应用程序在 Azure AD 中分配给它的以下权限运行:
所述应用程序通过共享机密而不是证书进行身份验证。
我们正在拉 Outlook 范围,因为我们想使用 Office 365 Exchange Online 的 IMAP 范围并通过此令牌和 oauth 使用 IMAP 身份验证的东西,我不相信 MIcrosoft Graph API 有任何 IMAP 身份验证端点可用的机制,
这里基本上是一个例子,我试图将 MSAL OAuth2 与我的 Azure AD 中配置的应用程序链接起来,以获得有效的imap.authenticate 调用,至少弄清楚如何使用不记名令牌完成 OAuth2 部分:
import imaplib
import msal
import pprint
import base64
conf = {
\"authority\": \"https://login.microsoftonline.com/TENANT_ID\",
\"client_id\": \"APP_CLIENT_ID\",
\"scope\": [\"https://outlook.office.com/.default\"],
\"secret\": \"APP_SECRET_KEY\",
\"secret-id\": \"APP_SECRET_KEY (for documentation purposes)\",
\"tenant-id\": \"TENANT_ID\"
}
def generate_auth_string(user, token):
authstr = f\"user={user}\\x01auth=Bearer {token}\".encode(\'utf-8\')
return base64.b64encode(authstr)
if __name__ == \"__main__\":
app = msal.ConfidentialClientApplication(conf[\'client_id\'], authority=conf[\'authority\'],
client_credential=conf[\'secret\'])
result = app.acquire_token_silent(conf[\'scope\'], account=None)
if not result:
print(\"No suitable token in cache. Get new one.\")
result = app.acquire_token_for_client(scopes=conf[\'scopes\'])
if \"access_token\" in result:
print(result[\'token_type\'])
pprint.pprint(result)
else:
print(result.get(\"error\"))
print(result.get(\"error_description\"))
print(result.get(\"correlation_id\"))
# IMAP time!
imap = imaplib.IMAP4(\'outlook.office365.com\')
imap.starttls()
imap.authenticate(\"XOAUTH2\", lambda x: generate_auth_string(\'example@example.com\',
result[\'access_token\']))
# more IMAP stuff after this, but i haven\'t gotten further than this.
每次使用AUTHENTICATE 访问有效用户的帐户时,我都会收到AUTHENTICATE failed 消息。这必须作为应用程序而不是通过委托的用户身份验证来完成的原因是因为它是一个需要访问的无头 python 应用程序很多的通过 IMAP(提取 RFC822 格式的消息)收件箱,而不仅仅是一个特定的邮箱,我们不想为单个用户生成单独的 OAuth 令牌,我们宁愿只在应用程序级别使用它。
有人知道我做错了什么吗?或者,如果有人可以为我指出一个可行的示例的正确方向,那就太好了。
标签: python-3.x oauth-2.0 imap msal