处理Apple消费请求通知调用接口返回401,JWT生成及.p8密钥获取咨询
Apple Send Consumption Info接口401授权问题解决方案
1 .p8格式密钥的正确获取方式
- 登录Apple Developer后台,进入「Certificates, Identifiers & Profiles」板块
- 左侧菜单选择「Keys」,点击右上角「+」新建密钥
- 勾选「In-App Purchase」权限选项,填写密钥名称后完成创建
- 创建成功后点击「Download」即可获取.p8格式私钥,该文件仅支持下载一次,请妥善保存
注意:不要混用推送、其他Apple服务的.p8密钥,必须是单独开启内购权限的密钥,无法确认正确性可重新生成替换。
2 JWT Token生成规则
调用接口使用的JWT采用ES256算法签名,由Header、Payload、Signature三部分用.拼接组成,各部分参数要求如下:
2.1 Header参数
alg:固定值为ES256kid:填写创建密钥时Apple生成的10位字符密钥IDtyp:固定值为JWT
2.2 Payload参数
iss:填写你的Apple Developer团队ID,可在开发者后台「Membership」页面查询iat:令牌签发时间,使用秒级Unix时间戳,禁止使用毫秒级exp:令牌过期时间,最大不能超过签发时间后60分钟,同样使用秒级Unix时间戳aud:固定值为appstoreconnect-v1bid:填写对应App的Bundle ID
2.3 签名规则
使用下载的.p8私钥,通过ES256算法对Base64Url编码后的Header和Payload的拼接内容(中间用.分隔)进行签名,签名结果做Base64Url编码后作为第三部分,和前两部分拼接得到完整JWT。
3 生成示例(Python版本)
首先安装依赖:pip install pyjwt cryptography
示例代码:
import jwt from datetime import datetime, timedelta # 替换为自身对应参数 KEY_ID = "你的10位密钥ID" TEAM_ID = "你的开发者团队ID" BUNDLE_ID = "你的App Bundle ID" P8_FILE_PATH = "./你的私钥文件.p8" # 读取私钥内容 with open(P8_FILE_PATH, "r") as f: private_key = f.read() # 构造Header headers = { "alg": "ES256", "kid": KEY_ID, "typ": "JWT" } # 构造Payload payload = { "iss": TEAM_ID, "iat": datetime.now().timestamp(), "exp": (datetime.now() + timedelta(minutes=30)).timestamp(), "aud": "appstoreconnect-v1", "bid": BUNDLE_ID } # 生成JWT jwt_token = jwt.encode(payload, private_key, algorithm="ES256", headers=headers) print(jwt_token)
4 常见401问题排查
- 本地服务器时间和标准时间偏差不能超过5分钟,避免时间校验失败
- 确认所有参数无拼写错误,尤其是
kid、iss、bid三个参数必须和开发者后台信息完全一致 - JWT过期时间不要超过60分钟,也不要设置为当前时间之前
- 确认.p8密钥没有损坏,读取内容完整无多余字符
内容的提问来源于stack exchange,提问作者lintiyan
相关产品推荐
相关产品推荐

