三种处置方式
回退(rollback)指恢复变更前的状态,适用于配置类、版本类变更:保留旧版本文件、旧镜像或旧配置包即可切回。补偿(compensation)适用于无法简单回退的动作,例如已经发送的通知、已经创建的资源,需要用反向动作抵消影响。冻结与人工接管适用于既不能回退也无法补偿的场景,此时正确的动作是停止继续变更、保留现场并交由人工判断,而不是让自动化继续重试。
基本信息
| 回退适用 | 配置、版本、镜像等可保留旧状态的变更 |
|---|---|
| 补偿适用 | 已产生外部副作用的动作 |
| 冻结适用 | 不可逆且影响范围待判断的操作 |
| 共同前提 | 变更前保留现场,失败时能判定当前处于哪一步 |
设计要点
- 变更前留底:改配置前备份原文件,发布前保留上一个可用版本。
- 分步提交:把一次大变更拆成若干可独立验证的小步,失败时只需回退最后一步。
- 回退幂等:回退动作重复执行不产生副作用,避免回退本身出问题。
- 回退可验证:回退后要用与变更前相同的检查手段确认已恢复。
- 补偿有兜底:补偿失败时的升级路径与人工入口写清楚。
- 演练过:回退流程至少在演练或非生产环境执行过一次。
带回退的变更结构
带回退的变更结构
conf=/etc/app/app.conf
backup="${conf}.bak.$(date +%s%N)" # 保留原始现场
cp -p "${conf}" "${backup}"
if render_and_reload "${conf}"; then
echo "变更成功,保留备份 ${backup}" # 成功时也记录备份位置
else
cp -p "${backup}" "${conf}" # 失败立即回退
reload_service # 回退后重新加载
exit 1 # 显式返回失败,避免被当成成功
fi处置方式对照
| 场景 | 处置 | 关键动作 |
|---|---|---|
| 配置写入失败 | 回退 | 恢复备份文件并重新加载 |
| 新版本启动异常 | 回退 | 切回上一版本并验证健康检查 |
| 已下发通知 | 补偿 | 重发更正说明或标记作废 |
| 已创建云资源 | 补偿 | 按标签回收并核对残留 |
| 数据已修改 | 冻结加人工 | 停止后续步骤,保留现场与日志 |
| 无法判定影响 | 冻结 | 暂停自动化并升级人工 |
回退不是万能的:数据库结构变更、已对外承诺的接口行为等往往无法真正回到从前。这类变更应在执行前就把不可回退点标出来,并在到达该点前设置人工确认。
回退路径要像主流程一样被维护:很多团队的回退脚本只在写的时候跑过一次,真正需要时才发现路径已经失效。