痛点与分环境矩阵
痛点拆解:① 手工改 .env 导致多机漂移;② 把 prod 令牌同步进共享卷;③ 变更无 deployment_id,排障靠猜。
用一张矩阵锁定职责(💻 运维可贴墙对照 🚀):
| 环境 | 非密钥模板 | 密钥来源 | 典型校验 |
|---|---|---|---|
| dev | 宽日志、调试开关开 | 本地或临时库 | 键齐全、占位符为空 |
| staging | 接近 prod 的限流与 URL | 独立保险库路径 | 与 prod 键集合一致、值不同 |
| prod | 仅生产域名与队列 | 最小挂载 + 轮换 | 审计字段、双签发布 |
密钥目录模型与角色边界详见《凭据最小权限》;与技能版本锁配套可读《技能包版本锁与环境模板》。
步骤 1:模板仓库与分层
仓库只存非密钥片段:config/env.base + config/env.<env>,并在 README 写明 template_revision。
# config/env.staging(片段示例)
LOG_LEVEL=info
QUEUE_URL=https://queue.staging.example
FEATURE_DRY_RUN=false
验证:
git grep -n "BEGIN PRIVATE KEY" && echo "FAIL" || echo "OK"
grep -E '^[A-Z0-9_]+=' config/env.* | cut -d= -f1 | sort | uniq -d
第二行应无重复键名;第一行不得命中私钥 PEM。
步骤 2:渲染与校验
在 CI 或配置机执行合并(示意用 envsubst,团队可换 yq/jinja):
export MESH_ENV=staging
cat config/env.base config/env.${MESH_ENV} | envsubst > .env.rendered
python3 - <<'PY'
import re
t = open(".env.rendered", encoding="utf-8").read()
assert "__VAULT_" not in t
assert not re.search(r"<[A-Z_]+>", t), "placeholder"
PY
验证:shasum -a 256 .env.rendered 记入发布单;各节点同类角色哈希应一致。
步骤 3:最小权限密钥挂载
按环境分目录,进程用户只读所需文件(示例组名 openclaw):
sudo install -d -m 0750 -o root -g openclaw /etc/openclaw/secrets.d/staging
sudo install -m 0440 -o root -g openclaw api.key /etc/openclaw/secrets.d/staging/
sudo stat -f "%Sp %u %g" /etc/openclaw/secrets.d/staging/api.key
验证:输出应为 -r--r----- root openclaw(或等价),其他用户无写权限。
步骤 4:节点差异覆盖
在渲染后加入小补丁(按 NODE_ID 或 NODE_ROLE),避免把整文件拷机:
# config/overlays/node-worker-03.env(示例)
WORKER_CONCURRENCY=2
TMP_DIR=/Volumes/fast/tmp
cat .env.rendered "config/overlays/node-${NODE_ID}.env" > /var/lib/openclaw/.env.new
mv /var/lib/openclaw/.env.new /var/lib/openclaw/.env
补丁文件只放本节点增量键,避免与模板同名冲突;若必须覆盖同键,请在评审记录中注明并在合并脚本中显式「后者优先」。
验证:
grep -E '^[A-Z0-9_]+=' .env.rendered | cut -d= -f1 | sort -u >/tmp/k_base
grep -E '^[A-Z0-9_]+=' /var/lib/openclaw/.env | cut -d= -f1 | sort -u >/tmp/k_node
comm -3 /tmp/k_base /tmp/k_node
comm 输出应仅为补丁新增键名(或为空表示无增量键)。
步骤 5:回滚与审计
发布单记录 GIT_SHA、secret_bundle_version、deployment_id;回滚=恢复上一指针并重新渲染。
git checkout "${PREV_SHA}" -- config/
./scripts/render-env.sh --env prod
sudo launchctl kickstart -k system/com.openclaw.worker
验证:结构化日志含 deployment_id、actor、config_hash_before/after;集中检索应能拼出一次变更全链路。
- 可引用阈值:目录默认
0750、密钥文件0440;保留最近3个可回滚 SHA。 - 审计要点:谁批准、哪条流水线、哪台机渲染、哪版密文包。
- 禁止项:在 Slack/工单贴 prod 令牌明文。
HowTo 清单(收工前勾选)
- 模板:base+env 层合并 →
git grep无密钥 → 记录template_revision。 - 渲染:
MESH_ENV正确 → 占位符检测通过 →shasum写入发布单。 - 密钥:分环境目录 →
stat权限 → 仅角色可读。 - 覆盖:节点补丁最小 → 键级 diff 复核。
- 回滚/审计:保留上一 SHA 与密文包版本 → 日志字段齐全。