使用Microsoft Graph API获取OneNote数据时遇404错误求助
问题分析与解决建议
你的问题核心在于OneNote Graph API不支持应用权限(Application Permissions),只能使用委派权限(Delegated Permissions),而你当前脚本用的是客户端凭据流(acquire_token_for_client),属于应用权限范畴,这就是导致404错误的根本原因。
为什么Graph Explorer能正常工作?
Graph Explorer使用的是委派权限流:它会引导你登录用户账号,获取包含用户上下文的令牌,令牌里带有Notes.Read这类委派权限的scope,OneNote API会认可这种令牌并返回数据。而你用客户端凭据流生成的令牌,本质是应用身份的令牌,OneNote API不接受这种身份的请求,因此返回404(实际是权限不匹配,但API返回404而非403)。
解决步骤
1. 切换到委派权限流
放弃客户端凭据流,改用授权码流(Authorization Code Flow)(推荐,符合OAuth最佳实践)或交互式登录流(适合桌面/测试场景)。
2. 配置Azure AD权限
在Azure AD应用注册中:
- 切换到「API权限」面板,添加Microsoft Graph的委派权限:比如
Notes.Read、Notes.ReadWrite等,根据你的需求选择。 - 点击「授予管理员同意」(如果是租户内应用),确保权限生效。
3. 修改脚本示例(交互式登录流)
用MSAL的交互式方式获取委派权限令牌:
from msal import PublicClientApplication import requests client_id = "你的客户端ID" authority = "https://login.microsoftonline.com/你的租户ID" scopes = ["Notes.Read"] # 对应你配置的委派权限 app = PublicClientApplication(client_id, authority=authority) result = app.acquire_token_interactive(scopes=scopes) if "access_token" in result: print('Access Token: ', result["access_token"]) # 确保URL中的myuser是用户UPN或ID,page-id是正确的页面ID response = requests.get( "https://graph.microsoft.com/v1.0/users/myuser/onenote/pages/page-id/content", headers={'Authorization': 'Bearer ' + result["access_token"]} ) print(response.status_code) print(response.json())
4. 验证令牌权限
用jwt.ms解析你生成的令牌,检查scp字段是否包含你配置的委派权限(比如Notes.Read)。客户端凭据流生成的令牌scp字段为空,只有roles字段,这是区分两种令牌的关键。
5. 检查API端点正确性
确认URL中的myuser是目标用户的用户主体名称(UPN)或对象ID,page-id是OneNote页面的正确ID,没有拼写错误或多余字符。
内容的提问来源于stack exchange,提问作者19jmrs
相关产品推荐
相关产品推荐

