从“救火”到“种树”:一个老码农的技术探索日常

郑刚
2025-12-29 12:12
阅读 722

早上八点,上海的天刚蒙蒙亮,我泡了杯速溶咖啡——别笑,35岁了,家里没时间磨豆子,公司楼下星巴克又太贵。坐在工位上,打开终端,先 kubectl get pods -n prod 瞅一眼昨晚部署的服务有没有炸。还好,一切正常。今天周五,得赶在下班前把新资源调度策略的文档写完,不然 PM 又要追着问:“这个功能下周能上线吗?”

我是那种典型“还没秃但快了”的老程序员,在上海一家中型互联网公司混了快十年,从 PHP 写到 Go,从虚拟机迁到 K8s,眼看着 DevOps 从 buzzword 变成每天的呼吸。最近半年,团队在搞成本优化,老板说:“云账单太高了,能不能省点?”——这不,技术探索和实践,往往不是出于兴趣,而是被现实狠狠推了一把。


被“资源”逼出来的技术升级

去年双11前两周,运维群里突然炸锅:集群 CPU 利用率持续飙到 90%+,但业务量只涨了 20%。我当时正在改一个 API 的超时逻辑,抬头一看监控图,心凉了半截——典型的“资源浪费型跑满”。

我们用的是标准 K8s 集群,每个 Pod 都设置了 requestslimits,但问题是:大部分服务都是按峰值预留资源的。比如一个订单服务,平时 0.5 核就能跑得很欢,但为了扛住秒杀峰值,硬生生申请了 4 核。结果呢?白天利用率不到 20%,晚上干脆睡大觉,但钱照付。

产品经理还一脸无辜:“这不是你们 DevOps 的事吗?我们只要系统稳。”——行吧,背锅侠上线。

于是我和 SRE 同事一起翻遍了 Prometheus 数据,搞了个脚本分析过去 30 天每个 Pod 的 CPU/MEM 使用情况,发现 70% 的服务资源申请严重超标。更离谱的是,有些服务压根没设 HPA(Horizontal Pod Autoscaler),全靠手动扩容,半夜值班的小哥都快神经衰弱了。

动手干:从静态分配到动态调度

我们决定三步走:

  1. 精细化资源画像:基于历史指标,用 VerticalPodAutoscaler(VPA)推荐合理的 requests/limits
  2. 启用 HPA + 自定义指标:不仅看 CPU,还要看队列长度、错误率等业务指标
  3. 引入 Keda 做事件驱动扩缩容:比如 Kafka 消息积压才拉起消费者

关键配置长这样:

apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
  name: order-service-hpa
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: order-service
  minReplicas: 2
  maxReplicas: 20
  metrics:
  - type: Resource
    resource:
      name: cpu
      target:
        type: Utilization
        averageUtilization: 60
  - type: Pods
    pods:
      metric:
        name: queue_length
      target:
        type: AverageValue
        averageValue: "10"

你以为这就完了?Too young。K8s 的坑,永远在你最自信的时候冒出来

第一次上线 VPA 推荐值,结果有个 Java 服务因为 JVM 堆内存没调,OOM 了三次。为啥?VPA 看的是容器内存使用,但 JVM 自己管堆,容器看到的内存包含 Metaspace、Direct Buffer 等,一压缩就崩。最后我们不得不给这类服务打上 vpa-ignore: "true" 标签,手动调优。


求职市场的“技术雷达”倒逼学习

说起来有点惭愧——如果不是去年偷偷更新简历,我可能还在用 Helm 2。

那会儿刷脉脉,看到有人发帖:“35 岁后端,面阿里云原生岗,被问 Service Mesh 和 eBPF,直接挂了。” 我心头一紧。虽然现在工作稳定,但谁不怕哪天被“优化”?于是咬咬牙,把周末献给了 Istio 和 Cilium

我不是为了跳槽真去面大厂(房贷压力不允许),而是发现:现在的招聘 JD 里,“熟悉云原生生态”已经不是加分项,是门槛。连中小厂都开始问:“你怎么做多集群管理?”、“如何实现 GitOps?”

于是我搞了个 side project:用 ArgoCD + Kustomize + Crossplane 搭了个玩具级多云平台,模拟从开发到生产的完整链路。过程中踩了不少雷:

  • ArgoCD 默认 sync 策略太激进,差点把测试环境数据库删了(还好有 backup)
  • Crossplane 的 Provider 抽象很好,但文档烂得像草稿,很多参数得翻源码
  • GitOps 的“声明式”听起来很美,但回滚比想象中复杂——你得保证 Git 历史干净,否则 rollback 会带出一堆无关变更

但好处也明显:一旦跑通,运维效率飞升。以前改个配置要找运维、提工单、等审批,现在 PR 合并自动部署。上周五晚上十点,产品临时改需求,我改完 YAML 提个 PR,CI 过了自动上线——第二天早上咖啡都没凉,功能已经在灰度了。

这种“自动化幸福感”,是 35 岁老码农继续写代码的最大动力之一。


运营视角下的技术决策

很多人觉得程序员只管写代码,其实 越资深,越要懂“运营”——这里的运营不是发公众号,而是系统如何被使用、如何创造价值、如何控制成本

举个例子:我们有个内部日志平台,用 Fluentd + Elasticsearch 搭的。早期为了“方便”,所有服务日志全量采集,结果 ES 集群一个月账单 8 万。老板直接拍桌子:“砍掉一半!”

怎么办?纯技术方案(比如换 Loki)要重构,来不及。我们转而从“运营”角度切入:

  1. 分级采集:核心交易链路全量,边缘服务只采 ERROR
  2. TTL 策略:普通日志保留 7 天,安全审计日志保留 90 天
  3. 用户配额:每个团队有日志额度,超了要申请

甚至搞了个“日志成本看板”,让各团队负责人看到自己花了多少钱。神奇的是,可视化一出来,乱打日志的行为立刻少了 60%——原来大家不是不知道浪费,只是看不见成本。

这让我想起一句老话:“你无法管理你无法衡量的东西”。技术人容易陷入“炫技”陷阱,觉得上了 Service Mesh 就高人一等,但如果你的业务 QPS 才 100,那可能 Nginx + Keepalived 更香。


实践中的权衡:没有银弹,只有取舍

最近在搞一个新项目,要用 Knative 做 Serverless 化。理由很诱人:自动扩缩到零,省钱!但实测下来发现几个问题:

方案 优点 缺点 适用场景
Knative 自动 Scale to Zero,节省闲置成本 冷启动延迟高(Java 应用 3~8s) 低频、非实时任务(如报表生成)
传统 Deployment + HPA 启动快,稳定 无法缩到零,最小副本始终运行 核心 API、实时服务
Keda + Queue 事件驱动,精准扩缩 依赖消息中间件,架构复杂 异步任务处理

我们最终混合使用:核心链路用 Deployment + HPA,确保 SLA;后台任务用 Knative,能省则省。技术选型不是非黑即白,而是“合适”二字

有时候,我会怀念十年前写 PHP 的日子——改一行代码,FTP 上传,刷新页面看效果。现在呢?改个配置要过 CI/CD、安全扫描、多集群同步……但反过来想,复杂度提升的背后,是系统规模和可靠性的飞跃。没有这些“繁琐”,根本撑不住百万 DAU。


写在最后:技术探索的本质是解决问题

经常有年轻同事问我:“哥,现在学什么技术最有前途?” 我一般反问:“你最近被什么问题折磨得睡不着觉?”

真正的技术成长,从来不是追着风口跑,而是在解决实际问题的过程中,被迫拓宽边界
可能是为了省云账单,去研究 VPA 和 FinOps;
可能是为了应对面试,啃下 Istio 的 xDS 协议;
也可能是为了不再半夜被 PagerDuty 叫醒,搭建完善的可观测体系。

上周,我们终于把集群平均 CPU 利用率从 25% 提升到了 58%,月度云成本降了 37%。老板请全组吃了顿火锅(人均 80,别期待太多)。散场时,实习生小王说:“原来 K8s 不只是 yaml 堆砌啊。” 我笑了笑,心想:是啊,它背后是一整套资源、成本、效率的运营哲学

35 岁还在写代码,或许在外人看来有点悲壮。但对我而言,每一次 debug 成功的瞬间,每一行减少资源消耗的配置,都是对“工程师”这个身份最好的致敬

技术探索没有终点,只有下一个待解的问题。
好了,咖啡喝完了,该去 review 今天的 PR 了——毕竟,明天又是新的一天,新的 bug 在等着我。

评论 0

最热最新
暂无评论
匿名用户Lv.1
0
影响力
0
文章
0
粉丝