AWS Cognito提交授权码换令牌报invalid_grant错误,如何测试获取ID与访问令牌
invalid_grant 错误核心诱因
- 编码实现存在硬伤
Python3 环境下base64.b64encode()仅支持字节类型入参,你当前的写法直接传入字符串会触发类型错误;即使强制完成类型转换,没有将编码后的字节结果解码为字符串,最终生成的认证值会携带Python bytes对象的原生前缀(类似b'xxxxxx'),直接塞入Authorization头会导致客户端身份认证失效。 - 违反授权码的固有规则
AWS Cognito 颁发的授权码有严格的使用约束:单次有效、有效期仅60秒。授权码生成时就与申请阶段传入的client_id、redirect_uri做了强绑定,换token阶段这两个参数和申请阶段存在任何字符差异(比如末尾多/少一个斜杠、端口不一致、http/https协议混淆),就会直接返回invalid_grant;重复使用同一授权码换token、拿到code后间隔超过60秒再发起请求,也会触发该错误。 - 客户端配置不匹配
若使用的是未开启客户端密钥的公共客户端(适配前端、移动端场景),携带Basic认证头本身就是不符合规则的;若为机密客户端,需提前确认已开启授权码授权类型、且实际使用的redirect_uri已加入控制台允许的回调URL列表,否则换token请求会被拦截。
正确获取ID令牌、访问令牌的测试流程
- 生成合规认证值(仅机密客户端需要)
修正Base64编码逻辑,确保生成的Basic认证字符串格式正确,参考可直接运行的编码代码:
公共客户端直接跳过该步骤,无需添加Authorization请求头。import base64 origin_str = "my_client_id_string:my_client_secret_string" auth_header_value = base64.b64encode(origin_str.encode("utf-8")).decode("utf-8") # 最终请求头的格式为:Authorization: Basic <auth_header_value> - 保证全流程参数一致性
从跳转链接拿到授权码后立刻发起换token请求,不要缓存授权码延后调用;换token时使用的client_id、redirect_uri必须和申请授权码时的参数完全一致,无任何字符差异;提前在Cognito控制台完成回调地址授权、开启对应授权类型。 - 合规的curl请求示例
#!/usr/bin/env sh curl --location --request POST 'https://<domain>.auth.us-east-2.amazoncognito.com/oauth2/token' \ --header 'Content-Type: application/x-www-form-urlencoded' \ --header 'Authorization: Basic <上一步生成的合规编码字符串>' \ --data-urlencode 'grant_type=authorization_code' \ --data-urlencode 'code=<刚从跳转地址获取的未过期授权码>' \ --data-urlencode 'redirect_uri=http://localhost:8000/my_redirect'
注意:携带合规Basic认证头时,请求体中无需重复传递
client_id、client_secret参数,Cognito会直接从认证头解析客户端身份信息。
内容的提问来源于stack exchange,提问作者anon_dcs3spp
相关产品推荐
相关产品推荐

