Skip to content

HTTP 请求

HTTP 通过宿主代理执行。插件声明 network.request 并取得授权后,可访问公网 HTTP(S);localhost、局域网和其他私网地址还需 network.private

从本地数组走向服务器

搜索教程把歌曲写在数组中。连接真实服务后,变化的是“这些歌曲从哪里来”:用 HTTP 取回服务端数据,再整理成同样的歌曲格式。

本页的 music.example.com 是示例地址,不能直接获取音乐。练习网络调用前,需要你自己的、允许访问的服务地址。

创建客户端

ts
const client = ctx.http.create({
  baseURL: 'https://music.example.com/',
  permissionKey: 'api',
  requestPermission: true,
  headers: { Accept: 'application/json' }
})

music.example.com 是占位地址,运行前换成你有权使用的服务。清单中声明 { key: 'api', name: 'network.request', reason: '读取音乐服务' }

创建参数类型 / 默认说明
baseURLstring,可选相对路径基准;缺省时请求必须是绝对 URL
permissionKeystring 或 (url: URL) => string;默认 network匹配 Manifest 的 key,不是域名白名单
requestPermissionboolean;默认不自动申请true 时向宿主请求授权;仍由宿主决定是否显示提示
headers字符串映射默认头,与单次请求头合并

SDK 注释与部分实现对拒绝后的重试描述不同。应以宿主的用户决定为准:不要通过自动重复调用绕过拒绝。

请求方法与返回

ts
client.request<T>(address, options): Promise<HttpResponse<T>>
client.get<T>(address, options): Promise<T>
client.post<T>(address, options): Promise<T>
client.authorize(key, origin, operation): Promise<void>

request 返回 { status: number, headers: Record<string, string>, data: T }get/post 直接返回 data,不是 AxiosResponse。authorize 仅处理授权,origin 不会收紧到域名级权限。

请求参数类型 / 默认说明
operationOperationContext,必需使用宿主传入的上下文,支持取消
permissionKeystring,可选覆盖客户端默认 key
query键值映射;值可为数组字符串/数字/布尔;忽略 null/undefined;数组编码为重复 query
methodstring,默认 GETget/post 方法会固定相应方法
headers字符串映射不能含换行;部分连接头由宿主管理
jsonJSON 可序列化值JSON 请求体
form简单键值映射URL 编码表单,忽略 null/undefined
bodystring原始文本请求体
timeoutMsnumber,可选受宿主上下限约束
throwHttpErrorsboolean,默认 true非 2xx 抛 HttpError;false 时自行检查状态码
credentialCredentialRef,可选SDK 契约;当前桌面未接入凭据引用服务

json / form / body 三选一,同时设置会失败。URL 中不能包含 username/password,不支持 file、data 等协议。

可复用的请求示例

以下函数由 Provider 或 Action 回调调用,把原始 operation 传入:

ts
import { HttpError } from '@shiqianjiang/ceru-plugin-sdk'
import type { OperationContext, PluginContext } from '@shiqianjiang/ceru-plugin-sdk'

export async function searchRemote(ctx: PluginContext, operation: OperationContext, query: string) {
  const client = ctx.http.create({
    baseURL: 'https://music.example.com/',
    permissionKey: 'api',
    requestPermission: true
  })
  try {
    return await client.get<{ items: { id: string; title: string }[] }>('tracks', {
      query: { q: query, limit: 20 },
      operation,
      timeoutMs: 10000
    })
  } catch (error) {
    if (error instanceof HttpError && error.status === 429) {
      ctx.log.warn('服务暂时限流')
    }
    throw error
  }
}

T 只提供类型提示,不会校验上游 JSON。转换为标准歌曲前应检查数组与必要字段,见Provider

低层请求

ctx.http.request({ permissionKey, url, operation, method?, headers?, body?, timeoutMs?, credential? }) 返回 Promise<{ status, headers, body }>。这里的响应字段叫 body,与便捷客户端的 data 区分。

低层接口通常保留非 2xx 状态;业务自行处理。新代码推荐使用 create,避免重复实现 JSON、表单与错误转换。

当前资源限制

限制CLI 工作台澜音 2.0 桌面
默认 HTTP 超时15,000 ms30,000 ms
timeoutMs 有效区间1,000–30,000 ms1,000–60,000 ms
请求体1 MiB4 MiB
响应体2 MiB16 MiB
自动跟随重定向最多 5 次最多 5 次
自动业务重试
响应转换UTF-8 文本,JSON 可解析则返回 JSON同左

以上为网络代理限额。工作台 RPC 的整个请求 JSON 还受 256 KiB 输入上限约束,包含参数和请求体,因此实际请求也必须满足这一更小的限制。不要仅按 HTTP 的 1 MiB 计算。避免用此文本接口传音乐文件或大块二进制。

工作台拒绝保留连接头(如 Host、Connection、Content-Length、Accept-Encoding),桌面过滤部分保留头。两者重定向实现也不同:桌面会在跨源时移除敏感请求头;不要假定工作台具备同样行为,避免把带凭据请求发往不可控重定向地址。

私网授权在重定向目标上也会检查。工作台还保留自己的服务端口和调试端口,不能把它们作为插件请求目标。

取消、限流与错误

操作取消会传递给桌面网络请求;回调中也应检查 operation.signal。用户拒绝权限、DNS/连接失败、超时、超额响应和无效请求会拒绝 Promise。

HttpError 提供 statusresponseorigin。返回给播放器时应转换为 MusicFault,区分 NETWORK_ERROR、RATE_LIMITED、AUTH_REQUIRED 等,不把所有错误都当作没有歌曲。

旧代码中的 httpFetch(...).promise 可用 SDK legacy-http 辅助迁移,但新插件优先使用上述客户端;旧 HTTP 地址可能被适配器升级为 HTTPS。

Released under the Apache License 2.0 License.