商城里的 王者荣耀战绩查询 是一条接口,不是五套地址。你每次带上自己的王者营地登录态,再用 action 换:搜人、列角色、拉战报、点进某场看十人面板、看当前营地资料。完整字段在该页「接口文档」,以及 原始文档。它和 王者战力查询 不是同一条——那条查英雄区服战力,不查对局。

地址只有一条,方法是 POST:
POST https://v1.apizero.cn/api/wzry-battle
Content-Type: application/json。密钥在 API Key 建。头写成 Authorization: Bearer 你的密钥。也认 X-API-Key,以及 Query api_key / apikey。这条标成免费,匿名也可以不带头,额度更低。不要把 Key 或营地登录态写进页面、安装包。
商城页目前只展开三个标签:搜索玩家、角色列表、历史战绩。接口本身还有 battle_detail 和 me。接到项目时按下面五个 action 写,不要只抄页上那三栏。页上返回示例常写成 total / list,真实回包是 `count` / `players`(或 `roles` / `battles`),以实际 JSON 为准。
先不用写代码。打开 王者荣耀战绩查询 扫一次营地码,把搜人 → 选角色 → 看对局走一遍。登录态只存在你这台浏览器,刷新还在,点「清除登录态」才删。本站账号和营地登录不是一回事:工具页要先登录本站,再扫营地码。也可以用商城「在线调试」或 接口调试 打一次。在线调试是真调用,会计入当日额度。

每次都要带登录态
没有营地登录态,五个 action 都走不下去。服务端不落盘、不全站共用,只用这一次。过期了回工具页重新扫,或把工具页「下载 JSON」再传一次。
三种带法,选一种:
- JSON 字段
session(推荐)。对象或 JSON 字符串都行,至少有ssoopenid、ssotoken。其余头(ssoappid、ssobusinessid、cgameid等)缺了接口会补默认值。 - multipart 上传文件。字段名
session、session_file或session_json,内容同上,上限 64KB。 - 扁平字段:
ssoopenid+ssotoken和别的参数平铺在一起。
工具页 QQ / 微信扫码换到的是营地票,能搜人。列角色、拉网页战报有时还要小程序那一套登录态;失败时接口不会把当页登录态当过期清掉,换一种票再试,不要立刻丢掉刚扫的 JSON。
五个 action 怎么排
一条请求只做一件事。查别人的完整链路是:
search → 记下 userId → roles → 记下 roleId → battles → 用列表里的钥匙打 battle_detail
查自己可以先 me,再 battles(role_id 可空)。
合法值只有这五个。空着或写错会直接校验失败。
搜索玩家:action=search
必填:session、action=search、keyword(昵称关键词)。
export APIZERO_API_KEY="你的密钥"
curl -sS -X POST https://v1.apizero.cn/api/wzry-battle \
-H "Authorization: Bearer $APIZERO_API_KEY" \
-H "Content-Type: application/json" \
-d '{"action":"search","keyword":"韩信","session":{"ssoopenid":"...","ssotoken":"..."}}'成功时最外层 code 为 0,正文在 data。读这些:
count:命中条数players:列表。每条至少有userId、nickname- 搜到角色时还会带
roleId、roleName、roleDesc、areaName、rankName、avatar
下一步优先用 userId。结果里已经带区服、段位的那条,可以直接拿 roleId 去查战报,少打一次 roles。没有 roleId 的条目不要硬点,换带区服的那条,或再走 roles。
search 不缓存。同一关键词连打会重复计次。
角色列表:action=roles
必填:session、action=roles、user_id(来自 search)。可选再传 keyword,只筛这个玩家名下匹配的角色。
{
"action": "roles",
"user_id": "123456789",
"session": {
"ssoopenid": "...",
"ssotoken": "..."
}
}data.roles 里每条:
roleId:给战报用roleName/roleDescareaName:微信区、手 Q 安卓等rankName/rankLevelisMain:是否主角色gameLevel
同一登录态、同一 userId(加上可选 keyword)大约 5 分钟内会走缓存。换号查同一个人不会串到上一把的票。
历史战绩:action=battles
必填:session、action=battles、user_id。role_id 查别人时带上;查自己近况可以空。
另外三个可选:
option:0全部(默认)、1排位、2巅峰、3娱乐。写别的数字会校验失败last_time:翻页游标,Unix 秒。0或不传是最新pages:一次拉几页,1–3,每页大约 30 条,默认 1
{
"action": "battles",
"user_id": "123456789",
"role_id": "111",
"option": 1,
"last_time": 0,
"pages": 1,
"session": {
"ssoopenid": "...",
"ssotoken": "..."
}
}先看统计,再看列表:
stats.total/wins/losses/winRatestats.avgKill/avgDeath/avgAssist:本页场均straightWin/straightLose:连胜连败hasMore、lastTime:还有下一页就把lastTime填回下一次的last_timebattles:对局数组
每一场:
time/timestamp、mapName、heroId/heroNameresult:win或losekill/death/assistmvp/loseMvpgameTime:时长,例如18:22- 钥匙(给详情用):
gameSeq、gameSvr、relaySvr、battleType(没有时用pvpType)
detailUrl 常常是营地 App 的 scheme 或空字符串,不要当网页打开。battles 不缓存。对方关了战绩会失败,文案是「该玩家已关闭战绩查询」,不是登录失效,不要清 session。
对局详情:action=battle_detail
用列表里那四把钥匙,再加当前查看的 roleId:
{
"action": "battle_detail",
"game_seq": "1234567890",
"game_svr": "1234",
"relay_svr": "5678",
"battle_type": 4,
"target_role_id": "111",
"session": {
"ssoopenid": "...",
"ssotoken": "..."
}
}参数也认驼峰:gameSeq / gameSvr / relaySvr / battleType。target_role_id 也可写成 role_id。缺钥匙会报「缺少对局钥匙」。
data.head 是本场摘要:胜负 win、地图、评分 grade、kda、击杀死亡助攻、英雄、高光 labels、时长 usedTime、开局 startTime。
data.blue / data.red 是两边面板。每人:
userId/roleId/roleName/areaName/isMeheroId/heroNamekill/death/assist/money/grade/mvphurt伤害、taken承伤、teamRate参团equips:出装,name+icon
卡片用 head + 两边英雄和 KDA。点战友头像查对方时,带上详情里的 userId + roleId 再走 battles;没有 userId 再退回按昵称 search。自己那一行点了只是回到列表。
当前营地资料:action=me
只要 session 和 action=me。回包是这份票对应的营地账号:userId、nickname、avatar。工具页「查我自己」先打这个,再拿 userId 去拉战报。做「登录后默认看自己」也用它,不要猜 userId。
接到自己的网站
浏览器只打你的后端。服务器再带 Key(或走匿名额度)和用户自己的 session 去 v1.apizero.cn。不要在服务端写死一份全站共用的营地票。
async function wzryBattle(action, extra, session) {
const res = await fetch("https://v1.apizero.cn/api/wzry-battle", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.APIZERO_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({ action, session, ...extra }),
});
const json = await res.json();
if (json.code !== 0) throw new Error(json.msg || "wzry-battle failed");
return json.data;
}
const found = await wzryBattle("search", { keyword }, session);
const userId = found.players[0].userId;
const roles = await wzryBattle("roles", { user_id: userId }, session);
const roleId = roles.roles[0].roleId;
const page = await wzryBattle(
"battles",
{ user_id: userId, role_id: roleId, option: 0, last_time: 0, pages: 1 },
session,
);
const first = page.battles[0];
const detail = await wzryBattle(
"battle_detail",
{
game_seq: first.gameSeq,
game_svr: first.gameSvr,
relay_svr: first.relaySvr,
battle_type: first.battleType,
target_role_id: roleId,
},
session,
);列表用 stats + battles 的英雄、胜负、KDA。点进一场再打详情。App、小程序同样把请求放在服务端。回包用 JSON 工具 抽 data.players、data.battles、data.head 核对一次再抄进项目。
这是战绩展示,不是官方对局公证。对方关战绩、登录态过期、模式筛空,都正常。
额度
这条按次计,每个 action 各算一次。具体每日次数和 QPS 看商城页「访问限制」,以当时页上的为准。写这篇时:
- 不带头:每日 5 次,QPS 1
- 登录免费(带 Key):每日 20 次,QPS 2
- 黄金会员:每日 50,000 次,QPS 10
- 企业会员:每日 1,000,000 次,QPS 120
免费次数用完再看套餐。工具页扫码换票不走这条计费;查战绩才计。
常见卡住
请上传王者营地登录态:session没带上,或 JSON 坏了。对照工具页下载的那份,至少要有ssoopenid、ssotokenaction 不能为空/无效的 action:只能是search/roles/battles/battle_detail/mekeyword 不能为空/user_id 不能为空:当前 action 缺对应字段缺少对局钥匙:详情少了game_seq、game_svr、relay_svr或target_role_id。回列表确认这四项不是空的该玩家已关闭战绩查询:对方隐私开关,换人王者营地登录态已过期,请重新扫码:回工具页重扫,或换一份新 JSON。code常见5020无效的 option:只能是 0 / 1 / 2 / 3- 搜得到人、列角色或战报失败:多半是 App 票和网页战报不匹配。session 先留着,换小程序登录态再打
roles/battles - 浏览器
Failed to fetch:页面直连了网关。改成打你自己的后端,或用接口调试代发 - 次数用完:看该接口今日已用
字段对过、额度还在,再接到网站。换玩家只改 keyword / user_id / role_id,地址不用换。