Skip to content

WordForge v1.0 客户端对接 — 接口变更清单

:本文为 v1.0.0 一次性迁移历史快照,v1.1+ 变更见 更新日志 / api-endpoints.md

基线:v0.6.0-beta.4 → v1.0.0 起草日期:2026-05-22 覆盖范围:仅变更部分(Breaking + 新增 + 字段调整 + SSE 事件 + 头部约束) 完整 OpenAPI:docs/openapi.yaml · 完整端点参考:docs/api-endpoints.md

目录

  1. ⚠️ Breaking — 必须迁移
  2. 🆕 新增端点
  3. 📝 字段变更(已有端点)
  4. 📡 SSE 事件表 — v1 新增 8 种
  5. 🔒 strict-mode 头部强制
  6. 🔗 OpenAPI 规格
  7. 🛡️ Release 签名验证
  8. 迁移检查清单

1. ⚠️ Breaking — 必须迁移

1.1 /api/v1/* 全部废止(M0-C5)

老路径全部返回 410 Gone

json
{
  "error": "GONE",
  "message": "该端点已永久废止,请迁移至 /api/learning/* 或 /api/records/*",
  "sunset": "2027-01-01"
}

附响应头(RFC 8594):

http
Deprecation: true
Sunset: Fri, 01 Jan 2027 00:00:00 GMT
Link: </api/learning>; rel="successor-version"

迁移对照/api/v1/records/api/records,其余 v1 路径同理(详见 api-endpoints.md 第 18 节)。

1.2 WordState wire 序列化改 lowercase(M0-C1)

之前 PascalCase → 现在 lowercase

Newnew
Learninglearning
Reviewingreviewing
Masteredmastered
Forgottenforgotten

涉及所有 records / word-states / favorites 端点的 state 字段读写(含请求 body 与响应 body)。


2. 🆕 新增端点

2.1 GET /api/users/me/export — GDPR 数据导出(M1-G1)

http
GET /api/users/me/export
Authorization: Bearer <token>

响应application/x-ndjson,流式逐行):

jsonl
{"table":"profile","data":{...}}
{"table":"study_config","data":{...}}
{"table":"records","data":[...]}
{"table":"word_states","data":[...]}
{"table":"favorites","data":[...]}
{"table":"notes","data":[...]}
{"table":"sessions","data":[...]}

频率限制:每用户每 24h 1 次。超限返回 429

json
{ "success": false, "code": "GDPR_EXPORT_RATE_LIMITED", "message": "每 24 小时只能导出一次数据" }

Retry-After: <秒数> 响应头。

2.2 POST /api/telemetry/error — 前端 ErrorBoundary 上报(S6)

无鉴权(错误火焰即忘,不落库只 tracing log),body limit 64 KB:

http
POST /api/telemetry/error
Content-Type: application/json

{
  "message": "ReferenceError: x is not defined",
  "stack": "at App.tsx:42:5\n  ...",
  "url": "https://wordforge.app/learning/session/abc",
  "userAgent": "Mozilla/5.0...",
  "componentStack": "in <SessionPage>\n  in <App>"
}

响应{"received": true},失败 500 不影响 UX。

2.3 PATCH /api/admin/feedback/:id — admin 反馈状态更新(M1-G3)

http
PATCH /api/admin/feedback/{id}
Authorization: Bearer <admin-token>
Content-Type: application/json

{
  "priority": "high",              // low / normal / high / urgent
  "status": "in_progress",         // open / in_progress / resolved / closed
  "assigneeAdminId": "admin_xyz",  // 或 null 取消指派
  "resolution": "已重现,分配给后端组"
}

所有字段均为 Optional,只传需要更新的字段。响应返回更新后的完整 feedback item。404 表示 id 不存在。

2.4 POST /api/admin/settings/maintenance — 维护模式即时切换(S4)

http
POST /api/admin/settings/maintenance
Authorization: Bearer <admin-token>
Content-Type: application/json

{ "active": true }

立即写库 + 触发 SseEvent::Maintenance { active } 广播给所有在线 admin 与用户 SSE 连接。

2.5 GET /metrics — Prometheus 端点(M0-P1,admin / 监控用)

文本格式(非 JSON):

# HELP http_requests_total Total HTTP requests
# TYPE http_requests_total counter
http_requests_total{method="GET",path="/api/learning/session",status="200"} 1234
...
amas_process_event_duration_seconds_bucket{le="0.01"} ...
http_request_duration_seconds_bucket{...} ...
worker_last_run_timestamp_seconds{worker="error_rate_watchdog"} ...

客户端通常不直接消费,admin 监控面板与 Prometheus scraper 用。


3. 📝 字段变更(已有端点)

3.1 GET /api/healtherror_rate(S7)

json
{
  "status": "ok",
  "version": "1.0.0",
  "uptime_seconds": 86400,
  "error_rate": 0.0012   // ← 新增:滚动 5 分钟 5xx/total
}

3.2 GET /api/feedback/items 列表项新增 4 字段(M1-G3)

json
{
  "id": "fb_xxx",
  "category": "bug",
  "content": "...",
  // —— 新增 4 字段 ——
  "priority": "normal",
  "status": "open",
  "assigneeAdminId": null,
  "resolvedAt": null,
  "resolution": null
}

3.3 GET /api/admin/settings 加 LLM 月度成本上限(M1-G2)

json
{
  "max_users": 100,
  "registration_enabled": true,
  "maintenance_mode": false,
  "default_daily_words": 20,
  // —— 新增 ——
  "llm_advisor_max_cost_per_month_yuan": 100.0,
  "llm_advisor_current_month_spent_yuan": 23.45
}

4. 📡 SSE 事件表 — v1 新增 8 种

统一格式{"type":"<rename>", ...payload},事件名一律 snake_case,payload 字段一律 camelCase

type新增于payload
new_llm_suggestionM0-C3{ "suggestionId": i64 }
release_availableM0-C3{ "latestTag": "v1.0.0", "channel": "stable" | "beta" }
update_progressM0-C3{ "phase": "downloading", "percent": 45 }
probe_requestM0-C3{ "requestId", "batchId", "scriptB64", "timeoutMs", "ctxVersion" }
probe_confirmM0-C3{ "requestId", "confirmToken" }
incidentM0-P4{ "errorRate": 0.025, "windowSecs": 300 }
worker_missedM1-A5{ "workerName", "missCount": 3 }
llm_budget_exceededM1-G2{ "spentYuan", "capYuan", "resumeMonth": "2026-06" }

注意update_available payload 重新设计含 channel 字段(v0.6.0-beta.3 加),客户端需按通道分类显示。

完整事件清单(14 个):maintenance · telemetry_request · banned · unbanned · data_corrupted · new_llm_suggestion · release_available · update_progress · update_available · probe_request · probe_confirm · incident · worker_missed · llm_budget_exceeded

权威定义:src/state.rs pub enum SseEvent


5. 🔒 strict-mode 头部强制

strict-mode 是挂在 /api/* 上的全局中间件(豁免 admin / status / realtime / telemetry / v1 五组路由)。开启时受检请求必须携带:

http
X-Device-Id: <设备唯一 ID>
X-Device-Platform: ios | android | web | macos | windows | linux

注:session_start 不是独立端点,而是 /api/telemetryeventType 取值。telemetry 路由本身豁免上述全局中间件,校验由 routes/telemetry.rs 在 body 解析后单独完成,分两层(见下)。

5.1 ⚠️ 遥测四要素硬校验(m038,无灰度开关、上线即生效)

自 v1.1.2-beta.4 起,/api/telemetry四要素硬校验不受 strict-mode 开关控制——任一缺失立即 4xx,与 hard_block 无关。四要素载体:

要素载体缺失返回
平台X-Device-Platform 头(不能为空或 unknown400 MISSING_OS
版本X-App-Version 头(不能为空)400 MISSING_APP_VERSION
时区payload.device.timezone400 MISSING_TIMEZONE
型号payload.device.modelv1.1.2-beta.4 新增必填400 MISSING_DEVICE_MODEL

四要素通过后做三态归属核验(设备须已注册且归属一致):

设备状态行为
未注册(client_devices 无此 device_id403 DEVICE_NOT_REGISTERED——须先正常登录使用后再上报
已注册、归属他人(user_id ≠ 当前 token 用户)403 DEVICE_OWNERSHIP_MISMATCH
已注册、归属未认领(user_idNULL由首个带 token 的用户 claim 放行(老匿名设备不误伤)
已注册、归属一致放行

客户端要求:所有遥测上报必须带 X-Device-Platform + X-App-Version 头,且 payload.device 至少含 timezone + model。Web 端无可靠真型号时落 browserName+osName 派生标识或 web-admin 占位。403 场景客户端应停止重试该设备的遥测并降级(不阻断学习主功能)。

5.2 strict-mode payload 软校验(受 hard_block 开关控制)

四要素之外的字段仍走 strict-mode 软门控,hard_block=true 时缺失 400、否则仅 warn log:

json
{
  "device": {
    "language": "zh-CN",
    // session_start 还要:
    "screenWidth": 390,
    "screenHeight": 844,
    "pixelRatio": 3.0,
    "cpuCores": 6
  }
}
code含义hard_block 控制
MISSING_DEVICE_IDX-Device-Id否(始终 400)
MISSING_OSX-Device-Platform否(四要素硬校验,始终 400)
MISSING_APP_VERSIONX-App-Version否(四要素硬校验,始终 400)
MISSING_TIMEZONEpayload 缺 device.timezone否(四要素硬校验,始终 400)
MISSING_DEVICE_MODELpayload 缺 device.model否(四要素硬校验,始终 400)
DEVICE_NOT_REGISTERED设备未注册否(始终 403)
DEVICE_OWNERSHIP_MISMATCH设备归属与当前账号不符否(始终 403)
MISSING_LANGUAGEpayload 缺 device.language
MISSING_DEVICE_FINGERPRINTsession_start 缺指纹四件套

生产环境(8.135.57.148):strict-mode 已启用 hard_block=true,软校验缺失也立即 400;四要素与归属核验则无视该开关始终硬拦截。


6. 🔗 OpenAPI 规格

资源路径
静态规格(仓库)docs/openapi.yaml
运行时端点GET /api/openapi.json
详细端点参考docs/api-endpoints.md
SSE 事件枚举src/state.rs SseEvent

注意:当前 docs/openapi.yamlinfo.version 还是 0.6.0-beta.4,未跟 v1.0.0 bump。这是已知 v1.1 修复项,不影响契约本身。

OpenAPI 当前覆盖 v1 stable 档约 25 个端点(utoipa 自动生成 + CI drift 防漂),未覆盖的端点请直接读源码 + 本文档。


7. 🛡️ Release 签名验证

客户端如实现自动升级(/api/admin/updates/apply 流程),必须验证 release tarball minisign 签名。

资源
公钥文件docs/security/wordforge-release.pub
公钥指纹RWQIHmTQvseWZo0Vc1npFBKZ/mMhi1S6eWT8hQ85Cmum5ftRgz87Yqll
验签库(Rust)minisign-verify crate
验签 CLIbrew install minisign
算法Ed25519

binary 本身已编译期内嵌公钥(MINISIGN_PUBKEY env),自更新 worker 自动验签,无签名或公钥不匹配 → 拒绝安装并回滚(M0-R2/R3)。

手动验证示例

bash
gh release download v1.0.0 --pattern '*x86_64*'
minisign -Vm wordforge-linux-x86_64.tar.gz \
  -P RWQIHmTQvseWZo0Vc1npFBKZ/mMhi1S6eWT8hQ85Cmum5ftRgz87Yqll
# 期望:Signature and comment signature verified

8. 迁移检查清单

客户端升级到 v1.0 兼容版前请逐项确认:

  • [ ] 代码搜索 /api/v1/ — 全部替换为新路径或下线
  • [ ] 代码搜索 "WordState" 序列化处 — 全部改为 lowercase(含枚举映射 / 反序列化器)
  • [ ] GDPR 入口 — 设置页加"导出我的数据"按钮,处理 429 退避
  • [ ] ErrorBoundary — 接入 /api/telemetry/error
  • [ ] admin feedback UI — 加 priority / status / assignee / resolution 四列编辑
  • [ ] admin settings — 加 maintenance toggle + LLM 月度成本可视化
  • [ ] SSE handler — 注册 8 个新事件类型;老的 update_availablechannel 字段
  • [ ] strict-mode 头X-Device-Id + X-Device-Platform 全请求挂载
  • [ ] strict-mode payload — telemetry / session-start 加 device 指纹
  • [ ] health 监控 — 取 error_rate 字段(如客户端有运维面板)
  • [ ] 自动升级 — minisign 验签链路联调(如客户端实现自更新)

9. 反馈

迁移过程中发现的契约问题(缺字段 / 类型不一致 / 文档错漏)请提 issue 到: https://github.com/Heartcoolman/wordforge/issues

标记 client-migration label,团队 24h 内响应。

WordForge — 智能英语学习平台