生产环境部署:推式部署(Push-based)与拉式部署(Pull-based / GitOps)部署方式详解(Argo CD / Flux、GHCR、kubectl apply、GitOps)
  • 推式(push-based):流水线(如 Github Actions) SSH 到主机执行 deploy.sh,用 GitHub Environment + required reviewer 做人工放行闸门。代价是生产 SSH 凭据进 GitHub Secrets(可用 command= 强制命令的受限 key 把权限收窄到"只能跑 deploy.sh")。
  • 拉式(pull-based / GitOps):主机上跑一个 agent 监听 GHCR/git 变化并自行应用。凭据方向反过来,GitHub 拿不到生产权限。K8s 世界的 Argo CD / Flux 就是这一派,也正因如此,"从 CI 里 kubectl apply"这种做法本身在今天已经算过时了。

介绍一下这两种部署方式

文章目录

  • 推式(Push-based)与拉式(Pull-based / GitOps)部署方式详解
    • 一、推式部署(Push-based)
      • 工作原理
      • 典型流程
      • 安全闸门设计
      • 优点
      • 缺点
    • 二、拉式部署(Pull-based / GitOps)
      • 工作原理
      • 典型流程
      • 关键架构优势
      • 优点
      • 缺点
    • 三、对比总结
    • 四、一句话总结

推式(Push-based)与拉式(Pull-based / GitOps)部署方式详解

一、推式部署(Push-based)

工作原理

┌─────────────┐ SSH / API 调用 ┌─────────────┐ │ CI/CD │ ───────────────────▶ │ 生产环境 │ │ 流水线 │ "我来帮你部署" │ 主机/K8s │ └─────────────┘ └─────────────┘

CI/CD 流水线主动连接到目标环境,把构建好的制品(镜像、二进制、配置文件等)推送过去,并执行部署动作。

典型流程

  1. 开发者 push 代码 → 触发 CI
  2. CI 构建镜像 / 编译产物
  3. CI 通过SSH连接到生产主机,执行deploy.sh
  4. 或者 CI 调用kubectl apply把 manifest 推到集群

安全闸门设计

  • GitHub Environment + required reviewer做人工审批——流水线跑到生产阶段前必须有人点"Approve"
  • SSH 密钥存入 GitHub Secrets,可用command=受限密钥收窄权限:
# ~/.ssh/authorized_keys command="/opt/deploy/deploy.sh",no-pty,no-port-forwarding ssh-rsa AAAA...

这样即使密钥泄露,攻击者也只能执行deploy.sh,无法获得交互式 shell。

优点

优点说明
简单直观一条脚本就能搞定,适合小团队 / 早期项目
反馈即时部署日志直接出现在 CI 输出里,成功失败一目了然
无需额外组件不需要在目标环境运行 agent

缺点

缺点说明
凭据暴露面大生产环境 SSH 密钥 / kubeconfig 必须放在 CI 侧(GitHub Secrets)
权限蔓延风险一旦 CI 被攻破(恶意 PR 触发 workflow),攻击者拿到生产凭据
环境漂移如果有人绕过 CI 手动改了生产环境,CI 不知道,也没有记录
扩展性差环境越多,要管理的凭据和连接就越多

二、拉式部署(Pull-based / GitOps)

工作原理

┌─────────────┐ ┌─────────────────────┐ │ Git Repo │ ◀── 持续轮询/监听 ── │ 生产环境内的 Agent │ │ (单一真相源) │ │ (Argo CD / Flux) │ └─────────────┘ └─────────────────────┘ ▲ │ │ ▼ CI 只负责 自行 apply 变更 构建 & push 镜像 "我来拉取最新状态"

注:Argo CD / Flux 是目前最主流的两款 GitOps 持续交付(CD)工具

生产环境内部运行一个 Agent(指运行在生产环境(Kubernetes 集群)内部的代理程序/控制器。它们负责持续监控 Git 仓库中的配置,并自动将这些配置同步、应用到生产集群中,它持续监听 Git 仓库或镜像仓库(如 GHCR)的变化,发现新版本后自行拉取并应用

典型流程

  1. 开发者 push 代码 → 触发 CI
  2. CI只负责构建镜像并 push 到 GHCR(或更新 Git 仓库里的 manifest)
  3. 生产环境中的Argo CD / Flux Agent检测到变更
  4. Agent在集群内部执行kubectl apply,完成部署
  5. 如需人工放行,Agent 会暂停等待审批(如 Argo CD 的 Sync 审批)

关键架构优势

┌──────────────────────────┐ │ 信任边界(防火墙) │ │ │ CI 侧(不可信) │ 生产侧(高信任) │ ──────────────── │ ────────────────────── │ GitHub Actions │ Argo CD Agent │ ❌ 没有 kubeconfig│ ✅ 有集群权限 │ ❌ 没有 SSH 密钥 │ ✅ 有镜像拉取凭据 │ │ │ └──────────────────────────┘

凭据方向反过来了:CI 永远拿不到生产环境的权限,生产凭据只存在于生产环境内部。

优点

优点说明
安全性高CI 侧零生产凭据,攻击面大幅缩小
环境一致性Git 是"单一真相源"(Single Source of Truth),环境状态可随时审计和回滚
自动修复漂移Agent 持续对比 Git 期望状态与实际状态,有人手动改集群会被自动纠正
多环境扩展好每个环境跑自己的 Agent,各自监听不同的 Git path/branch

缺点

缺点说明
复杂度更高需要在生产环境部署和维护 Argo CD / Flux
反馈延迟部署结果不在 CI 日志里,需要去看 Agent 的状态面板
学习曲线团队需要理解 GitOps 理念、Reconciliation Loop 等概念

三、对比总结

维度推式(Push)拉式(Pull / GitOps)
谁执行部署CI 流水线生产环境内的 Agent
凭据在哪CI 侧(GitHub Secrets)生产侧(Agent 本地)
安全模型CI 信任 → 生产生产自治,CI 不信任
典型工具GitHub Actions + SSH/kubectlArgo CD, Flux
适用场景小团队、早期项目、简单主机部署中大规模、K8s 原生、多环境
kubectl apply 在哪跑CI 里(已过时 ❌)(参考文章:为什么说“CI 里跑 kubectl apply“已过时?)集群内 Agent 里(推荐 ✅)

四、一句话总结

推式:CI “拿着钥匙去开门”——简单但钥匙容易丢。
拉式:生产环境"自己看门、自己取快递"——CI 只负责把包裹放到门口。

在现代 K8s 环境下,拉式 / GitOps 已经成为行业共识。如果你还在 CI 里写kubectl apply -f,确实是时候考虑迁移到 Argo CD 或 Flux 了。