Files
MusicServer/sdk/types.ts
T
snowy-yang 3381e9b906 refactor(api)!: 平台 id 改两字母短码——qian→bd、joox→jx、5sing→5s、bili→bl
对外 id 统一为两字母短码,与既有的 kw/kg/tx/wy/qs/xm/me/qt/lr 对齐;
migu 与 apple 保持原样(Apple Music 没有自然的短码)。

**破坏性变更**:id 出现在所有 URL、/sources 返回、OpenAPI 示例以及
data/auth.json 的凭据键里,这四个平台已存的登录态会失效,需重新登录。

- sdk/index.ts:id 与 supportQuality 映射键
- sdk/types.ts:Source 联合类型
- src/routes.ts 与 routes-login.ts:路由路径与 schema 描述
  (/login/bili/qr → /login/bl/qr 等)、/login/status 的响应键
- test/smoke-test.ts、README.md、docs/API.md 同步

有意未改:sdk 目录与文件名仍用平台名(sdk/qian/、sdk/apis/joox.ts …),
规则定为「目录=平台名,id=对外短码」,映射只在 SUPPORTED_SOURCES 一处声明。
域名与正则(joox.com、5sing.kugou.com、/joox\.com\//)、jooxSign 等标识符、
错误文案里的中文平台名、以及 kg 榜单名(含「joox本地热歌榜」)全部保持原样——
它们只是恰好含平台名,并不是 id。

验证:typecheck ✓、pnpm test 112/112 ✓;另起临时实例实证 /sources 与
/login/status 的新 id 与展示名,新旧 id 均无残留。
2026-10-03 11:03:06 +08:00

155 lines
4.1 KiB
TypeScript
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.
// SDK 共享类型定义
// 所有平台模块与根模块的类型锚点。类型只描述实际返回的数据形状,不改变运行时行为。
/** 音乐平台标识 */
export type Source =
| 'kw' | 'kg' | 'tx' | 'wy' | 'qs'
| 'migu' | 'bd' | 'jx' | 'bl' | '5s' | 'apple'
| 'xm' | 'me' | 'qt' | 'lr'
/** 音质标识(wav 仅部分接口声明使用) */
export type Quality = '128k' | '320k' | 'flac' | 'flac24bit' | 'wav'
/** 单音质资源描述(搜索结果 types 数组项) */
export interface SongType {
type: Quality
size: string
}
/** 单音质详情(搜索结果 _types 映射项) */
export interface QualityInfo {
size: string
}
/** 歌曲信息(搜索结果项 / 取流入参) */
export interface SongInfo {
songmid?: string
hash?: string
copyrightId?: string
songStringId?: string
albumId?: string
name?: string | null
singer?: string
source?: Source
interval?: string | number
albumName?: string
img?: string | null
lrc?: string | null
otherSource?: string | null
types?: SongType[]
_types?: Partial<Record<Quality, QualityInfo>>
typeUrl?: Partial<Record<Quality, string>>
[key: string]: unknown
}
/** httpFetch 响应(与 common/request.ts 契约一致) */
export interface HttpResponse {
statusCode: number
statusMessage?: string
headers: Record<string, string | string[]>
body: any
raw?: Buffer
}
/** httpFetch 返回的可取消请求对象 */
export interface HttpRequestObject {
promise: Promise<HttpResponse>
cancelHttp(): void
}
/** httpFetch 选项(common/request.ts 子集) */
export interface HttpOptions {
method?: string
headers?: Record<string, string>
body?: string | object
form?: Record<string, unknown>
timeout?: number
lookup?: unknown
family?: number
}
/** 带取消句柄的异步结果(getMusicUrl/getLyric 等的统一返回形态) */
export interface RequestObj<T> {
promise: Promise<T>
cancelHttp(): void
}
/** 请求句柄的宽松形态:SDK 内 promise 会在 .then() 中改写为对应结果类型 */
export interface AnyRequestObj {
promise: Promise<any>
cancelHttp(): void
}
/** 取流结果 */
export interface MusicUrlResult {
type: string
url: string
}
/** 歌词结果 */
export interface LyricInfo {
lyric: string
tlyric: string
rlyric?: string
yrc?: string
}
/** 搜索结果 */
export interface SearchResult {
list: SongInfo[]
allPage: number
total: number
limit: number
source: Source
}
/** 搜索模块(平台 musicSearch 子模块) */
export interface MusicSearchModule {
search(str: string, page?: number, limit?: number, retryNum?: number): Promise<SearchResult>
[key: string]: unknown
}
/** 歌词模块 */
export interface LyricModule {
getLyric(songInfo: SongInfo, ...rest: unknown[]): Promise<LyricInfo> | RequestObj<LyricInfo>
[key: string]: unknown
}
/** 封面模块 */
export interface PicModule {
getPic(songInfo: SongInfo, ...rest: unknown[]): Promise<string> | RequestObj<string>
[key: string]: unknown
}
/** 热搜模块 */
export interface HotSearchModule {
getList(): Promise<any>
[key: string]: unknown
}
/** 评论模块 */
export interface CommentModule {
getComment(songInfo: any, page?: number, limit?: number): Promise<any>
getHotComment(songInfo: any, page?: number, limit?: number): Promise<any>
[key: string]: unknown
}
/** 平台模块(各平台默认导出需满足的最小形状)
* 注:SDK 内部实现大量返回 httpFetch 原生的 HttpRequestObject,
* 实际 promise 会在 .then() 中被改写为对应结果类型;此处只约束调用侧可见形态。
*/
export interface PlatformModule {
init?(): Promise<unknown> | void
musicSearch?: MusicSearchModule
leaderboard?: any
songList?: any
hotSearch?: HotSearchModule
comment?: CommentModule
getMusicUrl?(songInfo: SongInfo, type: Quality): AnyRequestObj | Promise<any>
getLyric?(songInfo: SongInfo, ...rest: unknown[]): AnyRequestObj
getPic?(songInfo: SongInfo, ...rest: unknown[]): AnyRequestObj | Promise<any>
getMusicInfo?(songInfo: SongInfo): AnyRequestObj | Promise<any>
getMusicDetailPageUrl?(songInfo: SongInfo): string
[key: string]: any
}