基于Azure认证的PHP自动抓取邮件问题(适配Cron定时任务)
解决Azure AD认证无交互自动抓取邮件问题
问题根源
原代码采用隐式授权流(response_type=token),这是面向用户交互的认证方式,必须手动完成登录流程,完全不适用Cron定时任务这类无人工参与的场景。要实现无交互自动认证,需改用客户端凭证流(Client Credentials Flow)——这是服务对服务的认证模式,无需用户介入。
前置Azure AD配置
- 在Azure AD应用注册的「API权限」页面,添加应用权限(注意不是委托权限),选择Microsoft Graph的
Mail.Read权限,点击「授予管理员同意」(必须完成此步骤,否则会出现权限不足错误)。 - 确认应用已生成有效的客户端密码(Secret ID),并确保Tenant ID、App ID、Secret信息准确无误。
修改后的PHP代码
<?php // 配置信息 $appId = "xxxxx"; $tenantId = "xxxxx"; $secret = "xxxxxx"; $targetMailbox = "user@yourdomain.com"; // 需抓取的目标邮箱地址 // 1. 通过客户端凭证流获取Access Token $tokenUrl = "https://login.microsoftonline.com/{$tenantId}/oauth2/v2.0/token"; $tokenParams = [ 'grant_type' => 'client_credentials', 'client_id' => $appId, 'client_secret' => $secret, 'scope' => 'https://graph.microsoft.com/.default' // 应用权限固定使用此scope ]; $ch = curl_init($tokenUrl); curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($tokenParams)); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type: application/x-www-form-urlencoded']); $tokenResponse = json_decode(curl_exec($ch), true); curl_close($ch); if (!isset($tokenResponse['access_token'])) { die("获取Token失败: " . json_encode($tokenResponse)); } $accessToken = $tokenResponse['access_token']; // 2. 调用Graph API抓取目标邮箱收件箱邮件 $mailApiUrl = "https://graph.microsoft.com/v1.0/users/{$targetMailbox}/mailFolders/Inbox/messages"; $ch = curl_init($mailApiUrl); curl_setopt($ch, CURLOPT_HTTPHEADER, [ "Authorization: Bearer {$accessToken}", "Content-Type: application/json" ]); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); $mailResponse = json_decode(curl_exec($ch), true); curl_close($ch); if (isset($mailResponse['error'])) { die("获取邮件失败: " . json_encode($mailResponse['error'])); } // 示例:输出邮件基本信息 foreach ($mailResponse['value'] as $mail) { echo "邮件主题: {$mail['subject']}\n"; echo "发件人: {$mail['from']['emailAddress']['name']} <{$mail['from']['emailAddress']['address']}>\n"; echo "-------------------------\n"; } ?>
关键说明
- 客户端凭证流无需用户登录,直接通过App ID和Secret获取Token,完全适配定时任务的后台运行场景。
- 必须使用应用权限并完成管理员同意,否则Graph API会返回权限不足的错误。
- 原代码中的Session、前端跳转逻辑全部移除,因为定时任务是无状态的后台进程,无需用户交互环节。
targetMailbox需指定具体的邮箱地址,客户端凭证流可访问租户内所有已授权的邮箱(取决于配置的权限范围)。
内容的提问来源于stack exchange,提问作者Sarin Krish
相关产品推荐
相关产品推荐

