5.4 KiB
API 与认证
API 基础路径为 /api/v1。完整端点、请求字段、权限和响应以 OpenAPI 源文件为准,运行中的实例在 GET /api/v1/openapi.json 提供同一文档。测试 TestOpenAPICoversRoutes 核对路由覆盖。
脚本接入
在「设置 → 账户与安全 → API 令牌」创建只读或读写令牌。受保护 API 只接受 Authorization: Bearer <token>,不接受 Cookie,也不要将主令牌放进 URL。
以下只读示例从环境变量读取凭据:
# 先在本机环境中设置 RAWMARK_URL 和 RAWMARK_TOKEN,不要提交真实值。
curl --fail-with-body \
-H "Authorization: Bearer $RAWMARK_TOKEN" \
"$RAWMARK_URL/api/v1/tree"
rm_ API 令牌在服务端只存哈希,保留 read/write 权限。只读令牌可读取笔记、搜索和执行只读 POST 导出,不能写入;API 令牌不能管理账户、令牌、维护或资源票据,不能为自身扩权。管理操作需要浏览器登录会话。
JSON 与 HTTP 语义
普通 JSON 成功响应:
{
"code": 0,
"data": { "ok": true },
"message": "成功"
}
code = 0 表示成功,非零表示失败;失败时 message 是可展示的原因。保留真实 HTTP 状态,不把错误全部转为 200。通用错误码为 HTTP 状态乘 100,特定业务码如下:
| HTTP | code | 含义 |
|---|---|---|
| 400 | 40001 | 验证码错误、无效或已使用 |
| 400 | 40002 | 验证码过期 |
| 400 | 40003 | 修改密码时当前密码错误,不清理身份 |
| 401 | 40101 | 登录密码错误 |
| 412 | 41200 | 文件版本冲突,当前版本在 data.rev |
401 表示需要重新认证;403 表示当前身份没有权限,不能据此注销用户。维护输入或备份内容无效返回 400,占用或空间不足返回 503,文件系统/数据库内部故障返回 500。
文件原文、下载、WebSocket、204 及 OpenAPI 文档不包 JSON 外壳。GET /files/{path} 返回 Markdown 原文和 ETag;PUT /files/{path} 接收原文,成功返回包含 rev 的 JSON。用 If-Match: "rev" 防止覆盖新版本,或 If-None-Match: * 要求目标不存在;都不带会直接覆盖,不适合需要冲突保护的写入。
浏览器登录
实例没有用户名、注册或角色系统。尚未初始化时,POST /auth/setup 使用 { password } 设置密码并返回会话;已经初始化的实例不能再次初始化。
正常登录流程:
POST /auth/captcha获取{ captchaId, imageDataUrl, expiresAt }。- 展示图片,用户填写密码与六位数字验证码。
POST /auth/login提交{ password, captchaId, captchaCode }。- 成功返回
{ token, expiresAt },再通过GET /auth/me恢复真实身份与权限。
以上字段均位于普通响应的 data 中。刷新验证码时传 { replaceId } 使旧挑战失效。挑战绑定来源,五分钟过期;每次登录提交一次性消费,即使密码或验证码错误也不能重用,失败必须刷新。签发与登录均保留限流。
rms_ 浏览器会话 Token 保存在 localStorage 的 rawmark.token,固定三十天有效、不滑动续期,服务端仅存哈希。退出调用 POST /auth/logout,服务端撤销成功返回 204 后才清理本地身份;请求失败时保留身份并提示错误,不能仅删除本地 Token 宣称注销完成。
localStorage 可被同源脚本读取;有完整前端权限的插件必须视为可信代码,不能承诺凭据隔离。
原生资源与事件
原生图片、字体、插件模块与浏览器 WebSocket 不能统一设置认证头,通过 POST /auth/tickets 获取受限资源 URL;主 Token 不进入 URL。票据服务端只保存哈希,每次读取检查父会话,父会话退出后即失效。
- 图片/字体票据不超过父会话有效期。
- 插件票据额外绑定插件 ID 和版本,支持相对模块导入。
- 事件握手票据一分钟有效、仅消费一次;已连接事件仍会检查父凭据。
- 脚本 WebSocket 客户端可以通过 Bearer 请求头继续连接
/api/v1/events。
私有响应使用 Cache-Control: no-store 与 Referrer-Policy: no-referrer,API 和私有资源不进入 PWA 静态缓存。代理日志也需脱敏,见部署文档。
前端请求责任
请求处理、认证与路由守卫分别位于 http/、pinia/ 和 router/。匿名跳登录并保留合法站内回跳,拒绝外部地址与循环跳转。401 清理当前身份、权限与动态路由,403 保留身份。
每次替换或退出会话更新代号、取消旧请求。用户信息、路由安装、异步响应与排队写入均须检查所属会话;旧结果按 Axios 取消语义拒绝,不能覆盖或注销新身份,也不提示取消错误。
同一错误只由一个责任层提示。请求默认负责展示,已有行内状态、保存重试或批量汇总的 API 使用 errorOwner: 'caller';失败依然 reject,不以空列表或默认值伪装成功。
旧客户端迁移
统一协议需要前后端同时更新,不保留 Cookie/Bearer 或两种 JSON 格式兜底。旧 rm_ API 令牌无需重建,但调用方要改为读取 { code, data, message } 中的 data;文件及导出字节语义不变。旧浏览器页面需重新登录,不能连接新旧混用的后端。