今年述职,我把 PPT 封面换成了“运维部的 2024:从救火到拆弹”。这不是标题党,而是我们部门过去一年最真实的转变。让我心里有底的,不是又处理了多少工单,而是自从把 Sealos 引入生产环境以后,运维部终于从重复的部署、排查、救火里爬了出来,开始做那些早该做却一直没时间做的正经事。如果你也在管几十台上百台服务器,对 Kubernetes 安装、升级、中间件部署、监控告警这些事情熟得不能再熟,你应该能理解我们这一年到底经历了什么。
先给还不熟悉的朋友一句话总结:Sealos 不是什么玄学工具,可以把它理解成一个以应用为中心的云操作系统。打个比方,Kubernetes 是内核,Sealos 就是那个把内核包装成普通人都能用的发行版。它把集群初始化、节点管理、依赖组件、常用中间件都做成了可重复执行的交付物,我们不再需要每个环境都靠手工敲命令喂出来。后面这篇文章我不讲述职的漂亮话,只讲我们当时怎么评估、怎么落地、怎么踩坑,以及省下来的时间到底花到了哪里。
1. 先说结论:为什么运维团队越忙,说明越危险
1.1 忙不等于有价值:运维部的“救火陷阱”
我记得 2023 年有段时间,凌晨两点被告警叫醒是常态。有一次生产数据库磁盘告警,我爬起来连上服务器,三行命令清掉日志,睡意全无。第二天白天还要继续处理白天的事,晚上继续盯变更。这种状态持续了几个月,团队每个人都很忙,但我们年底复盘时突然发现:数据库磁盘为什么会满?日志为什么没轮转?告警阈值为什么没设对?这些问题一个都没真正解决。
这是典型的“救火陷阱”。运维团队越忙,越说明基础设施的确定性越差。你天天在处理故障,但故障的根因还留在系统里:环境配置漂移、中间件版本没人记录、升级步骤严重依赖某个人的记忆。每处理完一次故障,只是把眼前的问题按下去了,下次换个姿势继续爆。更麻烦的是,这种忙会消耗掉团队所有的学习意愿,因为白天的精力全被突发事件切碎了,根本没法静下心做技术沉淀。
我后来面试运维工程师时,最怕听到的一句话就是“我每天都很忙,天天处理故障”。听起来经验丰富,但如果你说不清楚某个故障的根因,也说不出怎么通过机制避免同类故障再发生,那这种忙只是用战术上的勤奋掩盖战略上的懒惰。运维的价值不应该体现在故障处理次数上,而应该体现在“本可以发生的故障没有发生”上。
1.2 Sealos 在中间扮演的角色:把 Kubernetes 变成“能用”的云操作系统
我们开始认真考虑 Sealos,是因为发现团队的大部分时间都耗在了 Kubernetes 本身,而不是业务上。用过原生 K8s 的同学都清楚,从裸机上装出一个可用的集群,背后要处理一堆事:容器运行时、网络插件、DNS、证书、kubelet 配置、etcd 备份、控制面高可用。装完之后还有更麻烦的:升级、证书过期、节点故障替换、中间件部署。
Sealos 解决的就是这一层。它把 Kubernetes 集群的创建变成一条命令,把常用组件打包成可复现的镜像,把 MySQL、Redis、Kafka、监控这些高频中间件变成应用商店里可以一键部署的对象。你可以继续用 kubectl 做任何事情,但不再需要从零开始搭地基。
类比一下:Linux 内核本身很强大,但没有人会在裸内核上直接跑业务。我们会选 Ubuntu、CentOS,因为这些发行版把内核之外的工具链、包管理、系统服务都封装好了。Sealos 对 Kubernetes 来说,就是这一层发行版。它对运维的价值不是“替代 kubectl”,而是把集群生命周期里最耗时的部分标准化、产品化,让团队把精力释放出来,去关心业务运行得好不好,而不是关心集群本身还能不能跑。
2. Sealos 到底帮我们省掉了哪些事
2.1 环境一致性:从“每套环境都是独生子”到“一套模板交付所有环境”
没上 Sealos 之前,我们的测试环境、预发布环境、生产环境虽然名字上都叫 K8s,但实际上配置差异非常大。测试环境的网络插件是早期手工装的,预发布环境是另一个同事按另一个文档搭的,生产环境则是从裸机一步步升上来的。每个环境都是“独生子”,没有一套标准能对得上。
这带来的直接后果就是:开发在测试环境验证没问题,到了预发布就出现镜像拉不下来、Ingress 冲突、存储类不存在。我们排查这些问题,往往要花掉半天。上了 Sealos 之后,我们用同一套集群镜像和配置模板去初始化所有环境。新环境不再是一个一个手工点出来的,而是执行同一个初始化动作,得到的集群版本、网络插件、运行时配置完全一致。环境差异导致的那种“本地好的,线上炸的”,数量明显下降。
2.2 中间件交付:从“折腾三天”到“提货即用”
我们团队以前最痛苦的事情之一是搭中间件。以 Kafka 为例,最早一次搭建,我们照着网上文章手动装了三台节点,配了 ZooKeeper,调了 JVM 参数,折腾了整整一个迭代周期。更麻烦的是,半年后需要扩容一个新的 Kafka 集群,当初怎么装的已经没人能完整说清楚,最后只能靠翻聊天记录和 shell history 勉强拼出来。
Sealos 的应用商店把这些高频中间件变成了标准化交付物。现在我们要开一套 Redis 或者 Kafka,只需要在平台上选择版本、指定资源规格、配置存储和访问方式,剩下的事情由平台处理。不需要再去记“当时那条配置文件里的 broker.id 为什么是 2”,因为这些都是模板的一部分,重新创建一遍也能得到同样结果。对我们这种业务节奏快、环境数量多的团队来说,这种一致性非常值钱。
2.3 集群生命周期管理:安装、升级、节点扩缩容
Sealos 在集群生命周期管理上的帮助是最直观的。以前我们新起一套三节点生产集群,要安装运行时、初始化 master、加入 worker、装网络插件、配存储类。顺利的话两天,不顺利的话一周。现在我们执行一条初始化命令,把节点 IP 传进去,十几分钟到半小时,一个集群就出来了。节点扩缩容也一样,不需要再去手动跑 kubeadm join 拼 token,直接通过 sealos 的 add/delete 节点操作完成。
这些能力释放出来的时间,让我们终于有余力去维护集群版本和补丁节奏。以前升级 K8s 版本,需要提前准备好几页升级文档,而且每次升级都像做一次高风险变更。现在升级动作本身被封装得更可靠,我们只需要关注版本间的不兼容变更,而不是在升级过程中还要处理 kubeadm 的琐碎细节。对一个运维团队来说,“能快速环境再造”和“能安全升级”,是两条非常硬核的指标。
3. Sealos 落地实录:从评估到稳定运行
3.1 选型前的三个评估维度
我们决定引入 Sealos 之前,团队内部列了一张评估清单。第一是项目本身的活跃度,包括 GitHub 更新频率、社区反馈、Issue 处理速度。这一条很重要,因为运维工具如果没人维护,将来就是新的技术债。第二是它能不能覆盖我们的真实痛点:集群生命周期、中间件交付、应用管理、监控运维,如果只能装 K8s 而不能解决中间件,对我们就少了一大半价值。第三是学习成本:团队不能为了引入一个工具再花三个月学一套新体系,命令越少越好,能兼容 kubectl 生态最好。
最终选择 Sealos,除了上面三条,还有一个关键因素:它以应用为中心的设计思路和我们运维团队的理念一致。我们不想维护一堆碎片化工具,而是想有一个统一的入口,从建集群到跑业务,都能在一个体系里完成。当然,后来的实际使用也证明,选型评估时的很多判断是对的,但也有一些当时没想到的坑,这个后面单独说。
3.2 环境准备与初始化
落地第一步是准备环境。我们当时的做法是先用三台测试机验证:三台 x86_64 架构的虚拟机,每台 8C16G,操作系统是主流 Linux 发行版,节点之间内网互通。规划上,master 节点建议奇数个,生产环境我们用了三 master 多 worker 的架构,方便 etcd 选主。另外提前确认了时间同步、DNS 解析、主机名不重复这些基础项,这些细节在分布式环境里最容易出问题。
初始化前需要安装 sealos 命令行工具。以下是当前主流版本的常见安装方式:
# 安装 sealos 命令行工具(以 v4.x 为例,具体版本以官方文档为准) curl -sfL https://raw.githubusercontent.com/labring/sealos/v4.5.0/scripts/install.sh | sh -s v4.5.0 # 查看安装结果 sealos version注意:不同版本的安装方式和命令参数会有差异,建议安装前查一下官方 Release 页,不要直接复制网上的旧命令。我们在测试时就因为版本差异吃过亏,后面会讲。
3.3 集群初始化与节点加入
环境准备好之后,执行集群初始化。命令本身不复杂,关键是把版本固定住,不要随手写成 latest,否则同一个命令在三个月后跑出来可能就不是同一个集群了。我们的做法是用固定的镜像 tag,并且把初始化命令放到团队内部的文档和脚本里,作为唯一的部署标准。
# 单 master 测试集群(资源有限时可以这样先跑) sealos run kubernetes:v1.28.0 \ --masters 192.168.10.11 # 生产多节点集群示例 sealos run kubernetes:v1.28.0 \ calico:v3.26.1 \ helm:v3.12.3 \ --masters 192.168.10.11,192.168.10.12,192.168.10.13 \ --nodes 192.168.10.21,192.168.10.22,192.168.10.23初始化完成后,我们做的第一件事不是急着部署业务,而是验证集群基础状态:
kubectl get nodes kubectl get pods -n kube-system确认所有节点 Ready,核心系统组件全部 Running,再执行下一步。这里我强烈建议团队把这一步作为强制 check,因为集群装好不代表状态健康,后面很多诡异问题都是因为基础组件没有全部就绪就继续往上堆业务。
3.4 应用商店与业务接入
集群稳定之后,我们把监控和中间件逐步接入。Sealos 自带的应用商店里有常见组件,像 Prometheus、Grafana、MySQL、Redis 这些,直接选择版本和资源配置部署。这一步的价值像手机装 App,你不用再从源码编译、手工调配置。但有一点要注意:应用商店里的组件只是帮你把部署动作标准化了,不代表你可以完全不看参数。数据库的内存配额、磁盘大小、备份策略,还是要根据业务需求去调。
业务应用接入是我们从传统方式切换过来的重点。我们的做法是给不同业务建独立命名空间,镜像推送到内部镜像仓库,然后通过 Deployment 部署:
apiVersion: apps/v1 kind: Deployment metadata: name: demo-app namespace: biz spec: replicas: 3 selector: matchLabels: app: demo-app template: metadata: labels: app: demo-app spec: containers: - name: app image: registry.internal/demo/demo-app:v1.0.0 ports: - containerPort: 8080 resources: requests: cpu: 250m memory: 256Mi limits: cpu: "1" memory: 1Gi应用部署好以后,再通过 Service 暴露端口,Ingress 接入域名。这个过程里我们保留了原有的 CI/CD 流水线,只是把部署目标从旧的虚拟机分组切到了集群命名空间。团队成员不需要改变太多习惯,kubectl 该用还是用。
3.5 迁移策略:先无状态,后有状态
这里必须强调一下我们的迁移顺序。很多团队一上来就想把数据库迁进集群,结果遇到性能问题、数据同步问题,最后铩羽而归。我们的策略是先迁无状态应用,再迁有状态应用。
第一批是无状态服务:Web 后端、API 网关、定时任务。这些服务没有本地数据依赖,扩容缩容方便,回滚也方便。我们在老环境和新集群之间用负载均衡做灰度,按权重切流量,观察一小段时间后再全量切换。第二批才是数据库、消息队列这类有状态服务。即使是这些,我们也先做演练迁移,验证备份恢复和时间点还原,确认没问题之后再动生产。
每一批迁移都要求可回滚。所有操作前必须有备份,所有切换窗口必须预留回退手段。这套纪律比工具本身更重要。Sealos 可以让集群创建得更快,但业务迁移的节奏还是要自己掌控。
4. 腾出来的时间,我们都花在了哪些“正经事”上
4.1 稳定性治理:故障演练与容量规划
以前我们根本没有时间做故障演练。系统是能跑就跑,不敢乱动。上了 Sealos 之后,环境拉起成本变低,我们终于有条件在隔离环境里做混沌测试和故障注入:模拟一台 worker 节点宕机、模拟网络分区、模拟 etcd 节点故障,看系统能不能自动恢复、告警会不会准确发出。
第一次演练的结果不太好看,告警是发了,但值班同学的响应流程不清晰,有些服务在节点恢复后没有自动重新调度到位。这些问题如果等真故障发生时才发现,代价会大得多。通过几轮演练,我们重新整理了应急预案,把“什么时候 DDoS 防护要接入、什么时候该切备份、什么时候该联系谁”这类问题写成了明确 checklist。稳定性的提升不是靠买更多机器堆出来的,是靠在可控环境下反复验证出来的。
4.2 监控告警体系:不再靠群里艾特
以前我们告警体系很原始:一部分靠云平台的基础监控,一部分靠群里人工反馈。告警来了就处理,但告警为什么来、影响范围多大、是否误报,完全没有统一视图。现在我们基于 Prometheus + Grafana + Alertmanager 搭了一套完整的监控体系,按业务维度收集指标,按服务等级配置告警规则。
告警规则的设计我们花了不少心思。早期告警太多,半夜三更一堆非关键告警把值班同学轰起来,时间长了大家反而对告警麻木。后来我们按 P0/P1/P2 分级,P0 是核心业务不可用,必须立即处理;P1 是性能明显劣化,需要持续跟进;P2 是资源水位预警,白天处理即可。同时收敛了重复告警,同一个根因只发一次。这套机制落地以后,值班体验提升明显,真正的问题也不会被夹杂在垃圾告警里漏掉。
4.3 自动化运维与流程沉淀
省下来的时间,我们还用来做了一件一直被拖延的事:把重复操作变成脚本和工具。现在团队内部维护了一套 Ansible Playbook,负责日常巡检、日志清理、配置分发、补丁更新。以前这些操作分散在每个同事的脑子里,现在统一收编到代码仓库,有版本记录,有执行日志,任何人执行都能得到一致结果。
linux 常用命令这些东西当然没丢,反而成了我们排障的第一层抓手。我们内部也整理了一份“常用命令速查手册”,不是网上那种大杂烩,而是把我们在集群环境里最常用的命令、最常踩的坑、最有效的排查路径沉淀下来。这类内部知识库,需要团队有闲下来的时候才有精力做。以前想都不敢想。
4.4 成本优化与资源水位治理
还有一个直接可量化的成果:成本优化。以前资源申请很随意,每个应用都要最大规格,集群里大量资源被闲置,但账单还是照着峰值在走。我们通过统一监控大盘查看各命名空间的资源使用率,把长期 Request 远高于实际使用的应用梳理出来,逐个调低 request 和 limit。
这个动作看起来简单,做起来需要耐心。调低配置可能导致重启,重启可能带来抖动,所以要分批做、小步走,每次只调整一小批,观察指标稳定后再继续。经过两个月的治理,我们整体资源利用率提升了 20% 左右,折算成费用是实打实的成本下降。给老板汇报的时候,这个数字比一百个“我们在努力”都管用。
5. 踩坑记录:不会踩坑的运维不是好运维
5.1 迁移初期的“三个没想到”
第一个没想到是镜像拉取问题。测试环境可以访问外网,一切顺利;到了生产环境,网络策略严格,很多镜像源不可达,集群初始化后大量 Pod 处于 ImagePullBackOff。当时我们的应对方案是提前把所有需要的镜像拉到内网镜像仓库,同时配置好 mirror,业务镜像也全部走内部仓库。这个动作不复杂,但没提前做的话,会非常影响时间窗口。
第二个没想到是存储性能。我们最初图省事,用了节点本地的默认存储来跑数据库,结果性能表现跟原来物理机上的 SAN 差了不少,IO 延迟明显升高。后来我们把有状态应用的存储切换到独立的高性能存储方案,性能才回到稳定水位。这里我的经验是:跑测试环境可以先用普通存储,但生产环境的数据库一定要认真规划存储,不能“先跑起来再说”。
第三个没想到是资源配额。平台默认的资源请求有时候很“客气”,对于没有显式声明 resources 的 Pod,调度器给的默认值很低,业务流量一上来,Pod 就被 OOMKilled 或者驱逐。排查起来也很迷惑,明明代码没变,突然就不稳定了。最后我们要求所有业务 Deployment 必须显式声明 resources,并且把默认资源策略调整到了合理区间。
5.2 一次升级事故的完整复盘
有一次我们升级集群小版本,提前看了 Release Notes,也做了测试环境验证,看起来没什么问题。但升级到生产环境后,部分节点迟迟没有 Ready,调度过来的新 Pod 卡在 ContainerCreating。排查顺序是从下往上:先看节点状态,再看网络插件 Pod 日志,最后发现是某条自定义网络策略和升级后的 CNI 版本兼容性出了问题。
当时第一反应是回滚。好在我们的升级流程里预设了回滚点,etcd 有备份,可以恢复到升级前状态。确认影响面后,我们执行了回滚,业务很快恢复。随后我们花了几天时间,把自定义策略逐一比对,重新设计了一套兼容新版 CNI 的方案,再选低峰期重新升级,这次就成功了。
这次事故给我的教训有三条:一是升级前不仅要看官方文档,还要检查自己环境里的“自定义部分”,越是自己改过的地方越要小心;二是回滚预案不是写在文档里给审计看的,必须真的演练过;三是升级窗口的流量要提前降级,宁愿多花点时间验证,也不要为了赶进度冒险。
5.3 常见问题速查表
| 问题 | 可能原因 | 排查方法 | 解决建议 |
|---|---|---|---|
| 节点一直 NotReady | 网络插件异常、kubelet 未启动、时间不同步 | kubectl describe node,检查 kubelet 日志 | 检查容器网络配置,同步时间,必要时重新加入节点 |
| 镜像拉不下来 | 镜像源不可达、未配 mirror | crictl images,看 Pod 事件 | 提前拉镜像到内网仓库,配置镜像加速和 mirror |
| Pod 反复重启 | 资源不足、健康检查失败、代码 OOM | kubectl logs,kubectl describe pod | 显式配置 resources,调整探针参数,扩容节点 |
| Service 访问不通 | 网络策略限制、Endpoint 为空 | kubectl get endpoints,测试 DNS | 检查网络策略和 Pod 标签,确认 Service selector 正确 |
| 升级后部分 Pod 异常 | 版本兼容性、自定义配置冲突 | 查看 Rancher 或 Sealos 升级日志,查看 CNI 日志 | 回滚到升级前,逐项排查兼容性后再升级 |
| 存储性能明显下降 | 存储方案选型不当、配额限制 | iostat,看延迟 | 更换高性能存储,评估资源配额 |
| etcd 不稳定 | 磁盘 IO 慢、节点时钟漂移 | etcdctl endpoint health | 确保专用高性能磁盘,配置好 NTP |
这个表格不是标准答案,但可以作为团队排查问题的起点。真实场景往往交织着多个原因,建议每排查一次,就把这次的问题和最终根因补充进自己的速查表,慢慢就会成为团队内部最值钱的文档。
5.4 给打算上 Sealos 的团队 5 条建议
第一,小步快跑,不要一开始就把所有业务塞进去。先挑无状态、低风险的服务试水,验证整个流程跑得通,再逐步扩大范围。第二,备份要提前做,不能等到要迁移数据库了才想起来备份策略没定好。第三,权限要收敛,不同团队不同命名空间,权限最小化,避免一个操作影响整个集群。第四,告警要克制,宁可先少配,也不要一次配太多把自己淹没,然后再根据实际故障案例逐步补充。第五,文档要随操作同步更新,每一次变更、每一次踩坑都要记录,不然半年后又会变成“当时怎么搞的来着”。
6. 写在最后:省下来的时间,到底值在哪
前几天有人问我:“你们运维部现在是不是闲了?”我说恰恰相反,我们比以前更忙了,但忙的内容完全不同。以前是忙着处理一个又一个重复问题,像在水下踩水,一刻不停却原地不动;现在是忙着建设、规划、复盘,忙完一件事,下一件事就可以做得更轻松。我个人实际用下来最大的体会是:工具的收益不在于第一天帮你省了多少时间,而在于它把团队从重复劳动中解放出来之后,你能把这些时间投入到哪里。
Sealos 解决的是基础设施的确定性问题,但它不是银弹。如果你所在团队连最基本的故障复盘、变更管理、备份纪律都没有,那换任何工具都只是换一个地方踩坑。我的建议是,把工具当成一个支点,真正要撬动的,是团队工作方式的一次转变。先把最耗时的重复事务交给平台,把人挪到更有长期价值的工作上,再用制度和文档把这种状态固化下来。这样到了下一次年终述职,你讲出来的就不再是“我们今年处理了多少故障”,而是“我们今年让多少故障根本没有机会发生”。