使用Python调用Dropbox认证API获取access_token失败求助
解决Dropbox OAuth2
invalid_grant错误及正确刷新access_token的方法 问题根源分析
你遇到的400 invalid_grant错误,核心原因有两个:
- 概念混淆:你的代码使用
grant_type: authorization_code,但你填入的是access_token而非授权码(authorization code)。授权码是OAuth2流程中用户授权后返回的一次性代码,用来兑换初始的access_token和refresh_token,和access_token是完全不同的东西。 - 授权码特性:授权码只能使用一次,用过就会失效,重复使用必然报“code doesn't exist or has expired”。
另外,你要实现“用refresh_token刷新access_token”的需求,当前代码逻辑完全不对——authorization_code模式是用来获取初始令牌的,刷新令牌需要用refresh_token模式。
修正后的代码实现
1. 获取初始的access_token和refresh_token(仅需执行一次)
确保你从Dropbox OAuth授权流程中拿到有效的授权码(authorization code),填入access_code变量,执行这段代码获取初始令牌:
import base64 import requests app_key = '<APP KEY>' app_secret = '<APP SECRET HERE>' redirect_uri = 'http://localhost/callback' access_code = '从OAuth授权流程获取的授权码' def get_initial_tokens(app_key, app_secret, access_code, redirect_uri): headers = { 'Authorization': 'Basic ' + base64.b64encode(f"{app_key}:{app_secret}".encode()).decode(), 'Content-Type': 'application/x-www-form-urlencoded' } data = { 'code': access_code, 'grant_type': 'authorization_code', 'redirect_uri': redirect_uri } response = requests.post('https://api.dropboxapi.com/oauth2/token', headers=headers, data=data) if response.status_code == 200: response_data = response.json() print("Access Token:", response_data.get('access_token')) print("Refresh Token:", response_data.get('refresh_token')) # 建议把refresh_token保存到本地文件或数据库,后续刷新用 else: print(f"Error: {response.status_code} - {response.text}") get_initial_tokens(app_key, app_secret, access_code, redirect_uri)
2. 使用refresh_token刷新access_token(access_token过期时执行)
保存好上面得到的refresh_token,用下面的代码刷新:
import base64 import requests app_key = '<APP KEY>' app_secret = '<APP SECRET HERE>' refresh_token = '之前保存的refresh_token' def refresh_access_token(app_key, app_secret, refresh_token): headers = { 'Authorization': 'Basic ' + base64.b64encode(f"{app_key}:{app_secret}".encode()).decode(), 'Content-Type': 'application/x-www-form-urlencoded' } data = { 'refresh_token': refresh_token, 'grant_type': 'refresh_token' } response = requests.post('https://api.dropboxapi.com/oauth2/token', headers=headers, data=data) if response.status_code == 200: response_data = response.json() print("新的Access Token:", response_data.get('access_token')) # Dropbox的refresh_token长期有效,不需要更新保存(除非用户主动吊销权限) else: print(f"Error: {response.status_code} - {response.text}") refresh_access_token(app_key, app_secret, refresh_token)
关键注意事项
- 授权码(authorization code)只能用一次,用完即失效,若初始令牌丢失,需重新走OAuth授权流程获取新的授权码。
- Dropbox的refresh_token长期有效,除非用户主动撤销应用权限,否则可一直用来刷新access_token。
- 不要将access_token填入需要授权码的参数中,二者是完全不同的令牌类型。
内容的提问来源于stack exchange,提问作者Ahmed Murtaza
相关产品推荐
相关产品推荐

