运维开发要不要自研发布平台?217台机器踩坑后我换成GitOps+Ansible

🔑 关键词:运维开发,自研发布平台,GitOps,Ansible,CMDB

📖 摘要:从217台ECS和18个K8s集群的踩坑经历出发,对比纯Ansible、自研发布平台、GitOps+Ansible三条路线,给出change-gate、runbook-executor、audit-sink的落地步骤和具体参数。

先说结论:自研发布平台,大多数团队其实是在给未来的自己挖坑

2019 年我在一家 300 人左右的电商公司做运维开发,手里管着 217 台阿里云 ECS、18 个 K8s 集群、3 套 IDC 物理机。我们花了 480 人日做了一套“万能发布平台”:Django 2.2 + MySQL 5.7 + Redis 3.2 + Celery 4.4,前端 Vue 2,功能清单 14 页。上线半年,发布平均耗时 23 分钟,失败率 7.7%,回滚全靠人工看日志。最惨的一次是凌晨 2:17,支付服务发版,平台先执行了数据库变更,再发代码;代码回滚成功,SQL 回滚脚本却没跑完。37 分钟不可用,直接损失按订单算大概 46 万。那天之后我才承认:我们把平台做成了“执行按钮”,没做成“状态机”。运维开发的核心不是写多少行代码,而是把不可逆操作变成可逆操作。如果回滚不能在 15 分钟内完成,发布平台再漂亮也是负债。

图片

三条路线,我按 8 个维度重新算了一遍账

后来我跳槽到一家 2000 台机器、43 个 K8s 集群的公司,重新选型。我把路线压成三条:纯 Ansible+Shell、自研发布平台、GitOps+Argo CD+Ansible 混合。纯脚本路线初始投入约 15 人日,年维护 10 人日,适合 50 台以下,但审计和并发是硬伤;自研平台初始 480 人日,年维护 96 人日,至少 3 个全职,故障域集中,平台挂全挂;GitOps 混合初始 60 人日,年维护 35 人日,K8s 用 Argo CD,虚机用 Ansible,回滚就是 git revert,适合 200 到 2000 台。我的独立观点很直接:执行器不要自研,Ansible、Argo CD、Terraform 已经够好;控制面才值得自研,也就是审批、冻结、审计、状态机。还有一个反常识的结论:CMDB 不应该先建,应该由变更流水线反哺。你先让每次变更都带 change_id、artifact_digest、operator、rollback_artifact_digest,跑三个月,CMDB 的准确率比人工录入高得多。我们当时人工维护 CMDB,字段准确率只有 68%,变更流水线反哺后到 96%。

图片

我们最后只保留了 3 个自研组件

第一,change-gate:FastAPI + PostgreSQL 14 + Redis 6,只存变更单和状态机。核心字段有 change_id、service、env、artifact_digest、rollback_artifact_digest、operator、approver、status、created_at、finished_at。唯一索引建在 (service, env, artifact_digest) 上,防重复发布。状态只有 5 个:draft、approved、running、success、failed。第二,runbook-executor:Ansible 2.15 + ansible-runner,不存状态,只执行幂等 playbook。每个 playbook 必须配 check.yml 和 rollback.yml,没有 rollback.yml 直接 CI 失败。第三,audit-sink:把 Argo CD events、Ansible callback、K8s events 写进 Loki 和 S3,保留 180 天。Prometheus 告警规则很简单:change_gate_failed_total > 0 持续 3 分钟,就打电话。具体步骤我们跑了 6 个月:第一步,梳理 50 个服务,标记可 GitOps 和不可 GitOps;第二步,K8s 服务接 Argo CD,同步策略用 manual,生产必须人工点 sync;第三步,虚机服务用 Ansible,playbook 放 GitLab,MR 审批后触发;第四步,数据库变更单独走 Flyway/Liquibase,不允许在发布平台执行 DDL/DML;第五步,每月随机抽 2 个服务做回滚演练,目标 15 分钟内完成。

图片

结果和代价:省下来的不是机器,是人

6 个月后,发布平均耗时从 23 分钟降到 8 分钟,K8s 服务甚至到 4 分钟;失败率从 7.7% 降到 1.9%;MTTR 从 58 分钟降到 11 分钟;自研组件代码从 8.7 万行砍到 1.1 万行,年维护从 96 人日降到 28 人日。但代价也有:GitOps 对非 K8s 中间件不友好,Redis、MySQL、Kafka 的配置漂移还是得靠 Ansible 和人工巡检;Argo CD 默认 3 分钟 reconcile,我们生产集群调到 1 分钟,结果 18 个集群的 apiserver_request_total 涨了 12%,后来只对生产调 1 分钟,测试保持 3 分钟;Ansible forks 从 5 调到 20,200 台机器部署从 14 分钟降到 6 分钟,但跳板机 SSH 连接打满,加了 ControlPersist=60s 和 pipelining=True 才稳住。所以别信“一套平台包治百病”,故障域隔离比功能大全重要。我们现在的原则是:K8s 走 GitOps,虚机走 Ansible,数据库走 Flyway,审批和审计走 change-gate,监控告警走 Prometheus + Loki。每个组件都能单独挂,挂了不影响其他链路。

图片

如果你也在纠结,先回答这 6 个问题

1)你们有多少台机器、多少个 K8s 集群?2)发布频率是每天 1 次还是每天 200 次?3)回滚能不能在 15 分钟内完成?4)有没有至少 2 到 3 个全职维护平台?5)审计日志要求保留 90 天还是 3 年?6)是否接受 Git 作为唯一事实源?我的建议很粗暴:50 台以下,别自研,Ansible+GitLab CI 够用;50 到 200 台,上 GitOps+Ansible,审批用 MR;200 到 500 台,加一个轻量 change-gate;500 台以上且多租户,才考虑自研控制面,但执行器一定不要自研。最后一句,运维开发最该写的不是“平台”,而是“把不可逆操作变可逆”的那段代码。你如果正在选型,可以先把回滚脚本补齐,再谈发布平台。

图片