Files
MusicServer/docs/API.md
T
snowy-yang aca7928019 feat(login): kg/tx 登录态自动续期(移植 lx-music-api-server 方案)
- kg: login_by_token 续期(AES-256-CBC + RSA 裸加密,参考其 refresh/kg.py),新 token 回写 data/auth.json
- tx: 新增 sdk/auth/tx.ts —— cookie 解析、VIP 检测(vip_login_base)、
  music.login.LoginServer 续期(走既有 musicu.fcg 未签名通道,最佳努力)
- 调度:启动 10s 后首刷 + 每 24h 一次(对齐参考项目 86400s + next_run_time=now)
- /login/tx 支持可选 App 抓包凭据(openId/accessToken/refreshToken/refreshKey)
- 新增 POST /login/refresh 手动续期;/login/status 增补 tx 字段与更新时间
- 补充 /login/tx 文档行与 smoke 测试
2026-09-29 20:16:33 +08:00

118 lines
6.2 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# MusicServer 聚合音乐 API
多平台音乐聚合接口:搜索、播放地址、歌词、封面、榜单、歌单。支持平台:**kw**(酷我)/ **kg**(酷狗)/ **tx**(QQ音乐)/ **wy**(网易云)。
> 本文档为静态速查版。交互式文档以服务器实际输出为准:
>
> - **Swagger UI**:`http://localhost:16688/docs`(可直接调试)
> - **ReDoc**:`http://localhost:16688/redoc`
> - **OpenAPI 3.1**:`http://localhost:16688/openapi.json`(可生成各语言客户端)
## 约定
- 默认端口 **16688**(可用 `PORT` 环境变量修改)。
- 仅支持 `GET` 方法;服务器支持 CORS(`Access-Control-Allow-Origin: *`)。
- **成功**:`200` + `{"code": 0, "data": ...}`
- **失败**:对应 HTTP 状态码 + `{"code": <状态码>, "msg": "...", "detail": ...}`
- `422` 参数校验失败(缺失、非法音质、页码越界等,FastAPI 风格)
- `404` 接口不存在 / 平台不支持该能力
- `405` 方法不允许(响应带 `Allow` 头)
- `502` 上游平台请求失败
- `500` 服务器内部错误
- 资源类接口统一为**路径参数风格**;`/search`、`/find` 搜索类接口使用 query 参数。
- 平台歌曲 id 形态:kw/tx/wy 用 `songmid`,kg 用 `hash`。
## 接口速查
### 系统
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/health` | 健康检查(status / uptime / 平台数) |
| GET | `/sources` | 支持的平台及其音质、能力(search/url/lyric/pic/boards/hotSearch/songList/singer/album) |
| GET | `/` | 302 重定向到 `/docs` |
| GET | `/docs` | Swagger UI 文档页 |
| GET | `/redoc` | ReDoc 阅读版文档 |
| GET | `/openapi.json` | OpenAPI 3.1 规范文档 |
### 搜索
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/search?name=稻香&singer=周杰伦&source=kw&page=1&limit=20` | 搜索歌曲;`source` 省略时聚合全部平台,失败的平台跳过 |
| GET | `/find?name=稻香&singer=周杰伦&albumName=魔杰座&interval=03:43&excludeSource=kw` | 跨平台精确匹配,按歌手/歌名/专辑/时长综合排序 |
### 歌曲资源
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/url/:source/:id` | 播放地址;query 可带 `quality`(128k/320k/flac/flac24bit,默认 128k)与 `albumId`(kg 需要) |
| GET | `/lyric/:source/:id` | 歌词;可带 `name`/`interval`(部分平台搜索歌词时需要) |
| GET | `/pic/:source/:id` | 封面;可带 `albumId`(kg 需要) |
### 榜单
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/boards/:source` | 榜单列表 |
| GET | `/boards/:source/:boardId` | 榜单详情;可带 `page`。`boardId` 兼容榜单列表的带前缀 `id`(`kw__93`)与裸 `bangid`(`93`) |
### 歌单 & 热搜
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/hot-search/:source` | 热搜词 |
| GET | `/song-list/:source` | 歌单列表;可带 `page`/`sortId`/`tagId`。`sortId`/`tagId` 各平台词汇不同(kw `new`/`hot`、tx `5`/`2`、kw 标签为 `173-digest` 形态等),`sortId` 省略时用平台默认 |
### 歌手 & 专辑
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| GET | `/singer/:source/:id` | 歌手信息(name/desc/avatar 与歌曲/专辑数量)。支持 kg/tx/wy |
| GET | `/singer/:source/:id/songs` | 歌手歌曲列表;可带 `page`/`limit`(默认 20)。支持 kg/tx/wy |
| GET | `/singer/:source/:id/albums` | 歌手专辑列表;可带 `page`/`limit`。支持 kg/tx/wy |
| GET | `/album/:source/:id` | 专辑详情与曲目列表;可带 `page`/`limit`(limit 仅 kg 生效,kw 单页固定 1000 条)。支持 kg/kw/tx;tx 的专辑名/作者由曲目数据合成(desc 为空) |
歌手/专辑 id 来源:搜索结果条目包含 `albumId`;歌手 id 需从平台方获取(不在搜索结果中)。
### 登录
| 方法 | 路径 | 说明 |
| --- | --- | --- |
| POST | `/login/wy/qr` | 获取网易云扫码登录二维码(返回 `key`/`qrurl`/`qrimg`,`qrimg` 为 data URL 可直接展示) |
| POST | `/login/wy/qr/check` | 轮询扫码状态,body 传 `{ "key": "..." }`。返回 `code`:800 过期 / 801 等待 / 802 已扫码 / 803 登录成功(自动保存凭据) |
| POST | `/login/wy/cellphone` | 网易云手机号登录;body 传 `phone` + `password`(明文,服务端 MD5 后提交)或 `captcha`,可带 `countrycode`(默认 86) |
| DELETE | `/login/wy` | 退出网易云登录 |
| POST | `/login/kg` | 绑定酷狗 token;body 传 `{ "token": "...", "userid": ... }`(App 抓包获取),服务端向用户中心验证后存储 |
| DELETE | `/login/kg` | 退出酷狗登录 |
| POST | `/login/tx` | 绑定 QQ 音乐 cookie;body 传 `{ "cookie": "..." }`(需含 `uin` 与 `qm_keyst` 字段)。可选附 App 抓包的 `openId`/`accessToken`/`refreshToken`/`refreshKey` 供自动续期 |
| DELETE | `/login/tx` | 退出 QQ 音乐登录 |
| POST | `/login/refresh` | 手动触发 kg/tx 登录态续期(与自动任务同一逻辑;未登录平台跳过,单平台失败不影响其他) |
| GET | `/login/status` | 登录状态(wy 实时校验 / kg、tx 已存凭据,含 `vipType` 与最近更新时间) |
- 登录态持久化于 `data/auth.json`(不入库),登录后取流与平台请求自动携带凭据。
- **登录态自动续期**:服务器启动 10s 后自动对 kg/tx 执行一次续期,此后每 24h 一次(kg 走 `login_by_token` AES/RSA 协议换新 token;tx 走 `music.login.LoginServer`,仅浏览器 cookie 时可能被网关拒绝,需在 `/login/tx` 附 App 抓包的完整凭据才可靠),结果输出到控制台日志。
- VIP 歌曲完整播放地址暂不在支持范围;登录态目前用于提升请求稳定性与为后续能力预留。
## 响应示例
```jsonc
// GET /url/kw/228908?quality=320k
{ "code": 0, "data": { "type": "320k", "url": "https://..." } }
// GET /lyric/kw/228908
{ "code": 0, "data": { "lyric": "[00:00.00]...", "tlyric": "", "yrc": "" } }
// 参数缺失
// 422
{ "code": 422, "msg": "querystring must have required property 'name'", "detail": [...] }
// 平台不支持该能力
// 404
{ "code": 404, "msg": "不支持的平台: xx" }
// 方法不允许
// 405 + Allow: GET
{ "code": 405, "msg": "方法 POST 不允许,请使用 GET" }
```