e4e995854d
- 新增忘记密码页面与重置密码确认流程(前端+后端) - 修复注册验证码页登录跳转路由 - 新增用户搜索API(按邮箱查询) - 简化infra脚本,统一为app.sh - 补充密码重置与用户API测试覆盖 - 更新runtime文档与AGENTS配置
248 lines
8.1 KiB
Markdown
248 lines
8.1 KiB
Markdown
# Runtime Runbook
|
|
|
|
**Date:** 2026-02-25
|
|
**Status:** Active
|
|
**Audience:** 运维 / 后端值班
|
|
|
|
## Scope & Preconditions
|
|
|
|
本手册用于日常值班、发布前检查、故障处置与回滚。
|
|
|
|
### 前置条件
|
|
|
|
- 已配置 `.env`(仓库根目录)。
|
|
- 主机可用:`docker`、`docker compose`、`tmux`、`uv`。
|
|
- 已拉取最新代码并确认当前分支与目标发布版本一致。
|
|
|
|
### 红线规则
|
|
|
|
- 禁止跳过 bootstrap gate 直接启动 web/worker。
|
|
- 迁移/初始化容器执行时必须带 `--build`,避免旧镜像导致迁移不生效。
|
|
|
|
---
|
|
|
|
## Bootstrap Gate (Mandatory)
|
|
|
|
以下流程必须按顺序执行。
|
|
|
|
### Step 1: 启动基础设施
|
|
|
|
```bash
|
|
docker compose --env-file .env -f infra/docker/docker-compose.yml up -d
|
|
```
|
|
|
|
通过标准:`docker compose ... ps` 中 redis/supabase 相关容器为 `running`。
|
|
|
|
### Step 2: 执行迁移与初始化
|
|
|
|
```bash
|
|
docker compose --env-file .env -f infra/docker/docker-compose.yml run --rm --build init-job bootstrap
|
|
```
|
|
|
|
通过标准:命令退出码为 0,日志中无 migration/init-data 错误。
|
|
|
|
### Step 3: 版本核对(建议)
|
|
|
|
```bash
|
|
docker compose --env-file .env -f infra/docker/docker-compose.yml exec -T db \
|
|
psql -U postgres -d postgres -c "SELECT version_num FROM public.alembic_version;"
|
|
```
|
|
|
|
通过标准:返回 1 行版本号,且与发布预期版本一致。
|
|
|
|
---
|
|
|
|
## Service Start / Stop (tmux)
|
|
|
|
### 启动应用进程
|
|
|
|
```bash
|
|
bash infra/scripts/app-up.sh
|
|
```
|
|
|
|
该脚本会在 tmux `social-dev` 会话中拉起:
|
|
|
|
- web
|
|
- worker-critical
|
|
- worker-default
|
|
- worker-bulk
|
|
|
|
通过标准:`tmux list-windows -t social-dev` 可见上述窗口。
|
|
|
|
### 常用 tmux 命令
|
|
|
|
```bash
|
|
tmux list-windows -t social-dev
|
|
tmux attach -t social-dev
|
|
tmux kill-session -t social-dev
|
|
```
|
|
|
|
### 日志文件
|
|
|
|
| 服务 | 日志文件 |
|
|
|------|---------|
|
|
| Web | `logs/web.log`, `logs/errors/web.error.log` |
|
|
| Worker Critical | `logs/worker-critical.log`, `logs/errors/worker-critical.error.log` |
|
|
| Worker Default | `logs/worker-default.log`, `logs/errors/worker-default.error.log` |
|
|
| Worker Bulk | `logs/worker-bulk.log`, `logs/errors/worker-bulk.error.log` |
|
|
|
|
---
|
|
|
|
## Operational Verification
|
|
|
|
按优先级分层执行。
|
|
|
|
### L1 必跑(发布前/故障恢复后必须)
|
|
|
|
```bash
|
|
# 先导入 .env,确保端口与配置一致
|
|
set -a
|
|
. ./.env
|
|
set +a
|
|
|
|
WEB_BASE_URL="http://127.0.0.1:${SOCIAL_WEB__PORT:-5775}"
|
|
|
|
# 基础健康
|
|
curl -fsS http://127.0.0.1:${SOCIAL_SUPABASE__KONG_HTTP_PORT:-8000}/health
|
|
|
|
# compose 状态
|
|
docker compose --env-file .env -f infra/docker/docker-compose.yml ps
|
|
|
|
# 核心接口 smoke
|
|
curl -sS -X POST "${WEB_BASE_URL}/api/v1/auth/login" \
|
|
-H 'Content-Type: application/json' \
|
|
-d '{"email":"demo@example.com","password":"secret123"}'
|
|
```
|
|
|
|
通过标准:health 返回 2xx,关键容器 `running`,核心接口返回预期业务状态码。
|
|
|
|
### L2 可选(Auth/Profile 业务回归)
|
|
|
|
```bash
|
|
# signup start
|
|
curl -sS -X POST "${WEB_BASE_URL}/api/v1/auth/signup/start" \
|
|
-H 'Content-Type: application/json' \
|
|
-d '{"username":"demo","email":"demo@example.com","password":"secret123"}'
|
|
|
|
# signup verify
|
|
curl -sS -X POST "${WEB_BASE_URL}/api/v1/auth/signup/verify" \
|
|
-H 'Content-Type: application/json' \
|
|
-d '{"email":"demo@example.com","token":"123456"}'
|
|
|
|
# profile patch
|
|
curl -sS -X PATCH "${WEB_BASE_URL}/api/v1/profile/me" \
|
|
-H 'Content-Type: application/json' \
|
|
-H "Authorization: Bearer <access_token>" \
|
|
-d '{"username":"demo2","bio":"hello"}'
|
|
```
|
|
|
|
通过标准:接口返回符合预期的 2xx 或受控业务错误,无 5xx。
|
|
|
|
### L3 可选(Agent Chat 回归)
|
|
|
|
```bash
|
|
PYTHONPATH=backend/src uv run pytest backend/tests/unit -k agent_chat -q
|
|
PYTHONPATH=backend/src uv run pytest backend/tests/integration -k agent_chat -q
|
|
PYTHONPATH=backend/src uv run pytest backend/tests/e2e/test_agent_chat_flow.py backend/tests/e2e/test_agent_chat_recent_session_home.py -q
|
|
|
|
curl -sS -X POST "${WEB_BASE_URL}/api/v1/agent-chat/run" \
|
|
-H 'Content-Type: application/json' \
|
|
-d '{"message":"hello"}'
|
|
```
|
|
|
|
通过标准:测试通过,`/api/v1/agent-chat/run` 返回有效 `session_id` 与事件序列。
|
|
|
|
---
|
|
|
|
## Incident Playbook
|
|
|
|
### 1) 迁移未生效(常见于旧镜像)
|
|
|
|
- 症状:字段/表结构与代码不一致,接口报 schema 错误。
|
|
- 定位:检查 `alembic_version` 与容器镜像构建时间。
|
|
- 修复:重新执行 `init-job --build`,并复核版本号。
|
|
|
|
### 2) Worker 不消费任务
|
|
|
|
- 症状:队列堆积,任务长时间 pending。
|
|
- 定位:检查 `worker-*` tmux 窗口和对应日志文件。
|
|
- 修复:重启 tmux 会话,确认并发配置与队列名(critical/default/bulk)。
|
|
|
|
### 3) JWT 或认证异常
|
|
|
|
- 症状:接口持续 401/403。
|
|
- 定位:核对 `.env` 中 Supabase JWT 配置与签发方设置。
|
|
- 修复:修正配置后重启 web 进程并执行 L1/L2 验证。
|
|
|
|
### 4) Agent Chat 启动后异常
|
|
|
|
- 症状:`/api/v1/agent-chat/run` 返回 5xx 或事件不完整。
|
|
- 定位:先跑 L3 测试,再看 `logs/errors/web.error.log`。
|
|
- 修复:先恢复到可用版本,再排查迁移、配置与依赖差异。
|
|
|
|
### 5) Auth 邮件模板未生效 / 注册返回超时但邮件已发送
|
|
|
|
- 症状:
|
|
- 收到默认英文模板(非 `infra/mail-templates`)。
|
|
- `signup/start` 偶发 500 或超时,但邮箱仍收到验证码邮件。
|
|
- 根因:容器配置漂移(旧容器未按最新 compose/.env 重建),导致:
|
|
- `supabase-auth` 缺少 `GOTRUE_MAILER_TEMPLATES_*` 环境变量。
|
|
- `supabase-mail-templates` 仍挂载旧路径。
|
|
- 定位:
|
|
|
|
```bash
|
|
docker inspect supabase-auth --format '{{ range .Config.Env }}{{ println . }}{{ end }}' | grep GOTRUE_MAILER_TEMPLATES
|
|
docker inspect supabase-mail-templates --format '{{ range .Mounts }}{{ .Source }} -> {{ .Destination }}{{ println }}{{ end }}'
|
|
```
|
|
|
|
- 修复:强制重建 auth 和 mail-templates(不改其他服务):
|
|
|
|
```bash
|
|
docker compose --env-file .env -f infra/docker/docker-compose.yml up -d --force-recreate --no-deps mail-templates auth
|
|
```
|
|
|
|
- 复核标准:
|
|
- `docker inspect supabase-auth` 能看到 `GOTRUE_MAILER_TEMPLATES_CONFIRMATION/RECOVERY`。
|
|
- `supabase-mail-templates` 挂载源为 `infra/mail-templates`。
|
|
- `POST /api/v1/auth/signup/start` 返回 `202` 且耗时恢复正常。
|
|
|
|
---
|
|
|
|
## Rollback Procedure
|
|
|
|
### 回滚前检查
|
|
|
|
- 确认目标回滚提交或版本号。
|
|
- 确认是否涉及不可逆数据变更。
|
|
|
|
### 回滚执行
|
|
|
|
1. 停止应用进程:`tmux kill-session -t social-dev`
|
|
2. 切换代码到目标版本。
|
|
3. 按目标版本要求执行迁移回滚(如有)。
|
|
4. 重新执行 bootstrap gate 与 service 启动。
|
|
|
|
### 回滚后复核
|
|
|
|
- 执行 L1 必跑检查。
|
|
- 记录回滚原因、时间、影响范围和后续修复计划。
|
|
|
|
---
|
|
|
|
## Change Log
|
|
|
|
| 日期 | 变更 |
|
|
|------|------|
|
|
| 2026-02-24 | 创建运行时手册,删除 legacy 脚本,统一使用 gunicorn |
|
|
| 2026-02-24 | 清理配置:合并 AppSettings 到 WebSettings,删除 Worker 旧配置 (enabled_queues/queues),统一使用 SOCIAL_WEB__GUNICORN__* 命名 |
|
|
| 2026-02-24 | 开发阶段 compose 暂不编排 web/worker,仅保留 redis/supabase 与 init-job |
|
|
| 2026-02-24 | 新增 dev-app-up 脚本:手动基础设施后,一键 bootstrap + tmux 拉起 web/worker |
|
|
| 2026-02-25 | 补充迁移防遗漏规则:容器迁移命令统一追加 --build;开发调试优先使用本地 CLI 一次性迁移脚本 |
|
|
| 2026-02-25 | Auth 注册切换为 OTP 三段式:signup/start、signup/verify、signup/resend;邮件模板改为纯验证码展示 |
|
|
| 2026-02-25 | 清理未使用配置类:删除 WebSettings/GunicornSettings/WorkerSettings/WorkerGroupSettings(脚本仍使用环境变量启动服务) |
|
|
| 2026-02-25 | 新增 Agent Chat 验证章节:bootstrap gate、分层测试命令与 run 接口 smoke 示例 |
|
|
| 2026-02-25 | 简化启动方式:dev-app-up -> app-up,分离 bootstrap 与服务启动 |
|
|
| 2026-02-25 | 重构为运维分层手册:Bootstrap Gate、分层验证、故障与回滚流程 |
|
|
| 2026-02-25 | 新增配置漂移故障条目:修复 Auth 邮件模板失效与 signup 超时场景 |
|
|
| 2026-02-27 | 用户搜索支持邮箱精确匹配:query 含 @ 符号时走 auth.users → profiles 两步查询 |
|