运维与维护
检查健康状态、排查请求、监控用量与成本、备份和恢复数据、安全升级并处理常见故障。
本手册用于生产 Compose 技术栈启动后的日常操作。请在 Cordy Gateway 交付目录执行命令。每条 Compose 命令都保留 docker-compose.production-overrides.yml;省略它可能在重建容器时悄然恢复开发模式的安全行为并关闭信用 WAL。Compose 通过 --env-file .env 获得插值;make 脚本不会,因此运行 make 目标前,要在 shell 中导出同一组 DB_*、REDIS_URL、备份与健康检查变量。
检查技术栈
先查看容器状态与近期日志:
docker compose -f docker-compose.prod.yml -f docker-compose.production-overrides.yml --env-file .env ps
docker compose -f docker-compose.prod.yml -f docker-compose.production-overrides.yml --env-file .env logs --tail=200 admin gateway worker nginx
再检查公开数据平面接口:
curl -sS http://<host>:8002/health
curl -sS http://<host>:8002/health/ready
curl -sS http://<host>:8002/health/providers
curl -sS http://<host>:8002/health/detailed
/health 证明进程存活。至少有一条通道能服务流量之前,就绪与详细健康会返回 503。/health/providers 定位受影响的服务商或通道;/health/detailed 还报告数据库、Redis、能力与许可证状态。
如需从主机检查 PostgreSQL、Redis、详细健康、备份新鲜度和目录可写性,运行:
make health-check
只有在生产验收环境已配置 WAL 归档后才设置 REQUIRE_PITR=1;它会把“缺少 PITR”从警告提升为失败。
排查单个请求
- 从错误响应体复制
request_id,或记录成功响应中的X-Channel-Id、X-Provider、X-Failover-Count等请求头。 - 打开 Admin → Monitoring → Request logs,按请求 ID、用户邮箱、API 密钥名称或通道搜索。
- 检查状态、延迟、token、所选通道、成本证据与追踪链接。请求日志是只读证据。
- 在 Usage stats 查看每日聚合;成员可在自助门户查看自己的最近 50 条请求。
- 已启用追踪时,打开 Tempo 或 Langfuse 链接。Langfuse 链接要求在生产 Compose 覆盖文件中配置
ADMIN_LANGFUSE_TRACE_URL_TEMPLATE。
修改配置前先区分账户限制:402 insufficient_credits 表示预付余额为空;429 quota_exceeded 表示该 API 密钥的 token 配额耗尽。速率限制是另一种 429 rate_limit_exceeded,并附 Retry-After。
监控指标与追踪
Gateway 位于公开 nginx 之后时,在 .env 设置 GATEWAY_METRICS_TOKEN、让 GATEWAY_METRICS_ALLOWED_CIDRS 保持为空,并应用生产覆盖文件:
docker compose \
-f docker-compose.prod.yml \
-f docker-compose.production-overrides.yml \
--env-file .env up -d gateway nginx
配置现有 Prometheus 兼容抓取器之前,先验证令牌路径:
curl -fsS https://gateway.example.com/metrics/prometheus \
-H "Authorization: Bearer $GATEWAY_METRICS_TOKEN"
CIDR 绕过会先于令牌校验,并检查直接 socket 对端。位于公开 nginx 之后时,允许 nginx 或其网络会放行它代理的全部请求。只为直接、隔离的受信抓取路径使用 CIDR。生产抓取器示例见部署。
关注请求/错误量、token 与美元成本、故障转移成功率、路由开销和服务商熔断器状态。
追踪应按配置为可达且由运维管理的 collector 设置 OTEL_TRACING_ENABLED 与全部所需 OTEL_*,再用相同生产文件重建 Gateway:
docker compose \
-f docker-compose.prod.yml \
-f docker-compose.production-overrides.yml \
--env-file .env up -d gateway
随附的 monitoring、tracing 与 observability Compose 文件都是开发/参考配置,其网络不能到达生产 Gateway;observability 配置还带 CHANGEME 默认值。若未另行设计并验证部署,请勿把它们加入生产命令。
保护信用结算证据
每次更换镜像或 UID 后,确认挂载的 WAL 目录存在且可写:
docker compose -f docker-compose.prod.yml -f docker-compose.production-overrides.yml --env-file .env \
exec gateway sh -c 'test -d /var/lib/cordy && test -w /var/lib/cordy'
Redis 错误导致信用扣减缓冲写入失败时,请求仍会成功,Gateway 会把 {user_id, cost_usd, ts} JSON Lines 追加到 /var/lib/cordy/credit-consume.jsonl。如果追加也失败,日志会报告已计数的 consume_drop_total 少扣款。请为这些条件设置告警,并在替换容器时保留具名 gateway_wal 卷。
仓库没有自动重放命令。进行任何调整前,先把 WAL 复制为不可变证据,再将其中的用户、成本与时间戳同 Request logs、信用流水和对应上游账单逐行核对,并记录已应用的行。审核后只执行一次人工信用调整;保留该审计轨迹可避免以后重复扣款。
备份并验证恢复
在执行命令的主机安装 PostgreSQL 客户端工具,设置生产 DB_*,并选择持久备份目录:
BACKUP_DIR=/var/backups/cordy BACKUP_RETENTION=7 make backup
命令会写出以数据库名和 UTC 时间命名、可恢复的 SQL dump,打印路径,并只保留所配置数量的最新备份。请按恢复策略把备份复制到应用主机之外。
定期证明 dump 能恢复到临时数据库:
make dr-drill
演练排除 pg_cron,把应用数据恢复到 DR_DB_NAME(默认 cordy_link_drtest),检查 VERIFY_TABLE(默认 django_migrations),报告恢复耗时;除非设置 KEEP_DR_DB=1,否则随后删除临时库。它不能证明时间点恢复或高可用;部署需要这些能力时应另行实测。
升级与回滚
升级前记录当前代码引用并确认备份目录。先无变更预览:
make preflight
DRY_RUN=1 make upgrade
部署目标源码或镜像后,执行真实流程:
BACKUP_DIR=/var/backups/cordy make upgrade
make health-check
升级会执行预检、创建数据库备份、应用由 Admin 拥有的迁移并验证健康。保留输出中的备份与 manifest 路径。
若验证失败且发布流程决定回滚,请重新部署上一版本代码/镜像,并恢复与之对应的数据库 dump:
make upgrade-rollback BACKUP=/var/backups/cordy/cordy-<timestamp>.sql PREV_REF=<previous-ref>
数据库恢复具有破坏性。该命令恢复 dump 并打印代码引用步骤,但不会替你执行 git checkout。
扩展数据平面
只扩展 nginx 后面的 gateway 副本:
docker compose \
-f docker-compose.prod.yml \
-f docker-compose.production-overrides.yml \
--env-file .env up -d --scale gateway=4
所有副本共享 PostgreSQL 与 Redis,因此限速、配额预留、幂等与冷却状态保持全局一致。每次变更后重新检查就绪、错误、延迟、数据库连接池与上游限制。
常见故障
| 现象 | 检查 | 处理 |
|---|---|---|
所有密钥都返回 401 | Gateway 的 DB_NAME、DB_USER、DB_PASSWORD 与日志 | 与 Admin 数据库值保持一致;数据平面不读取 DATABASE_URL。 |
404 model_not_found | 公开模型、供应商模型、通道与活动绑定 | 补全或启用五记录模型链。 |
就绪为 503 / 无通道 | /health/providers、通道状态、Test connection | 修正上游凭据/端点,或启用健康绑定。 |
402 insufficient_credits | 成员余额与信用流水 | 通过 Admin 用户操作充值,不要直接编辑余额字段。 |
429 quota_exceeded | API 密钥配额上限与已用值 | 按策略提高/重置配额,或等待配额周期。 |
403 scope_denied | 错误中的 required_scope 与密钥作用域 | 只增加所需作用域。 |
指标返回 403 | 抓取器 bearer 令牌 | 让抓取器 bearer 凭据与 GATEWAY_METRICS_TOKEN 一致。不要允许共享的公开 nginx 对端。 |
| CORS 意外允许任意 Origin | 实际 ENVIRONMENT 与已应用的 Compose 文件 | 使用 docker-compose.production-overrides.yml 重建;只用基础生产文件会让 Gateway 保持 development。 |
| Redis 信用扣减写入失败 | Gateway 日志、gateway_wal 与目录权限 | 保留并核对 JSONL 证据。Redis 与 WAL 均写入失败时,调查已计数的少扣款;系统不会自动重放。 |
| 成本未知 | 请求时刻有效的 Price history 记录 | 添加互不重叠的有效价格窗口;不要修改旧请求证据。 |