Kubernetes GitOps工具
前言
在这篇文章中,我将回顾我最喜欢的 GitOps的工具。 在我看来,Kubernetes的主要优势在于它的声明性,同时也是 Kubernetes的主要优势在于它的声明性和控制循环,后者持续观察集群的实时状态,确保它与存储在.NET中的理想状态相匹配。 etcd.这个想法本身是非常强大的,但它仅限于数据库,因为它不能提供足够的可见性。 etcd数据库,它不能提供足够的可见性。这就限制了应用于集群的变化的责任和可审计性。另一个缺点是,我们最终会有两个真相来源,即etcd和代码库,这可能会造成配置漂移,这是很难管理的。
开发人员长期以来一直在使用代码库,以便以安全和完全可追溯的方式轻松存储代码。 工作流程为了有效地管理中央资源库,不同的团队成员可以并行工作而没有太多的摩擦,同时确保任何变化都是可审查、可追踪和易于回滚的。
如果我们能从围绕Git存储库创建的流程中获取所有这些巨大的优势,并将其扩展到基础设施中,那不是很好吗?Kubernetes怎么样? GitOps的世界!
首先,我将谈一谈什么是GitOps以及如何将其应用于Kubernetes,然后转向声明式GitOps工具,即用于在Kubernetes中实现GitOps的工具,最后回顾一些对GitOps友好的工具,即它们是声明式的,以代码形式实现。
什么是GitOps?
GitOps的目标是将这种声明性的特性从etcd一直延伸到代码所在的Git 存储库中,从而创造一个单一的真理源。通过这样做,我们还能获得Git流程的所有优势,比如代码审查、历史记录、快速回滚、可追溯性等等。
GitOps的核心思想是有一个Git仓库,它总是包含对生产环境中当前所需的基础设施的声明性描述,并有一个自动流程使生产环境与仓库中的描述状态相匹配。如果你想部署一个新的应用程序或更新一个现有的应用程序,你只需要更新仓库--自动化流程会处理其他一切。这就像在生产中管理你的应用程序的巡航控制。-www.gitops.tech/
GitOps并不是Kubernetes所特有的,事实上,它的创建是为了将应用程序代码的最佳实践也扩展到基础设施中,即通过存储在 基础设施即代码在Git Repositories中。这被一些工具所推广,如 Terraform.请注意,"声明式基础设施即代码"在实施GitOps方面发挥了巨大的作用,但它并不只是这样。GitOps将整个生态系统和围绕Git的工具应用于基础设施。仅仅把Terraform文件放在Git中,并不能保证基础设施的状态永远与生产环境的状态一致。你需要不断地运行Terraform命令(terraform apply )来观察实时版本,你还需要在你的管道中实施手动审批,以及更多。
GitOps的理念是持续观察集群的状态,并将其与Git仓库进行比较,在出现配置漂移的情况下立即做出任何改变。除此之外,你还可以得到Git的所有好处,比如可以用于人工审批的代码审查。
对我来说,这个想法是革命性的,如果做得好的话,将使企业能够更多地关注功能,而不是为自动化编写脚本。这个概念可以扩展到软件开发的其他领域,例如,你可以在代码中存储你的文档,以跟踪变化的历史,并确保文档是最新的;或者使用以下方法跟踪架构决策 ADRs.
Kubernetes中的GitOps
Kubernetes从一开始就采用了控制循环的理念,这意味着Kubernetes一直在观察集群的状态,以确保它与期望的状态相匹配,例如,运行的复制数量与期望的复制数量相匹配。GitOps的理念是将其扩展到应用中,因此你可以将服务定义为代码,例如通过定义 舵手图表,并使用一个利用K8s功能的工具来监控你的应用程序的状态,并相应地调整集群。也就是说,如果更新你的代码库,或者你的舵手图,生产集群也会被更新。这是真的 持续部署.核心原则是,应用程序的部署和生命周期管理应该是自动化的,可审计的,并且易于理解。
我们的想法是在每个环境中都有一个代码库,在那里你可以定义给定集群的理想状态。然后,Kubernetes 操作员将继续监控一个特定的分支(通常是主分支),当在Git中检测到一个变化时,它将被传播到集群中,并在etcd中更新状态。这样一来,etcd只是作为一个数据库,而不是作为集群的单一真理源。在包含声明式Kubernetes基础设施的Git仓库中,你可以有Helm图表定义来定义你的应用程序。此外,你可以将仓库连锁起来,让一个仓库监视另一个仓库,如此类推。Kubernetes的GitOps工具可以监视其他仓库,比如Helm图表仓库,这样你的集群环境仓库不需要有Helm图表本身,而是有一个链接到Helm仓库,这个仓库也被监视着变化,所以当你发布一个新的图表,那么它就会自动部署到集群中。这样,你就可以拥有自动的端到端声明式CI/CD管道。
声明式 GitOps 工具
如果我们要讨论Kubernetes中的GitOps,我们应该先谈谈在Kubernetes中实现GitOps原则的工具,负责观察Git的状态并将其与集群同步。
ArgoCD
在我看来,Kubernetes中最好的GitOps工具是 ArgoCD.你可以在这里阅读更多关于它的信息。ArgoCD是Argo生态系统的一部分,它包括其他一些伟大的工具,其中一些,我们将在后面讨论。
通过ArgoCD,你可以在一个代码库中拥有每个环境,在那里你可以定义该环境的所有配置。Argo CD可以在指定的目标环境中自动部署所需的应用程序状态。


ArgoCD架构
Argo CD被实现为一个kubernetes控制器 ,它持续监控正在运行的应用程序,并将当前的实时状态与期望的目标状态(如Git repo中指定的)进行比较。Argo CD报告和可视化差异,并能自动或手动将实时状态同步回所需的目标状态。


ArgoCD的操作
ArgoCD有一个优秀的用户界面,支持SSO,它是安全的,可升级的,而且非常容易使用。
Flux
Flux是另一个非常受欢迎的ArgoCD的替代品。新版本包括许多改进,并具有与ArgoCD非常相似的功能。Flux是一个CNCF的孵化项目。


Flux的特点
GitOps工具
在本节中,我们将回顾一些我最喜欢的 GitOps友好工具。简而言之,任何基于 定制资源定义(CRD的工具,都应该是对GitOps友好的。
舵手
舵手不需要介绍,它是Kubernetes最著名的 包管理器。是的,你应该在K8s中使用包管理器,就像你在编程语言中使用它一样。Helm允许你将你的应用程序打包在 图表它将复杂的应用程序抽象成可重用的简单组件,易于定义、安装和更新。
它还提供了一个强大的模板引擎。Helm很成熟,有很多预设的图表,支持力度很大,而且很容易使用。
Helm与ArgoCD或Flux完美结合,因为两者都可以观察Helm存储库,并在发布新图表时进行部署。其原理是将ArgoCD或Flux指向一个Helm存储库,并指定一个特定的版本或通配符版本。如果你使用通配符,只要有新的版本发布,就会自动部署。你可以使用主版本或次版本。我通常喜欢用图表打包我的应用程序,作为CI/CD的一部分进行构建,然后让ArgoCD监视一个特定的存储库。这种关注点的分离允许开发人员在独立于环境的单独的存储库中管理他们的应用程序,然后让ArgoCD选择哪些图表被部署到哪些环境。你可以使用几个Helm存储库,并根据不同的环境执行推广。例如,在一个PR被合并后,你可以做一个 "bronce "构建,作为Helm图表发布到 "bronce "存储库。开发环境的ArgoCD仓库将指向 "bronce "仓库,并在可用时部署新版本。暂存环境的ArgoCD版本库将指向 "银色 "版本库,而生产环境则指向金色版本库。当你想把一些东西推广到暂存或生产时,你的CI/CD只需要把图表发布到下一个仓库。
ArgoCD可以覆盖任何特定环境的Helm值。
自定义是Helm的一个较新的、伟大的替代方案,它不使用模板引擎,而是使用覆盖引擎,你有基本的定义和覆盖在它们之上。
Argo工作流程和Argo事件
在Kubernetes中,你可能还需要运行批量作业或复杂的工作流程。这可能是你的数据管道的一部分,异步流程甚至是CI/CD。在此基础上,你可能需要运行甚至驱动的微服务,对某些事件做出反应,如文件被上传或消息被发送到队列。对于所有这些,我们有 Argo工作流程和 Argo事件.
虽然它们是独立的项目,但它们往往被部署在一起。
Argo Workflows是一个类似于Apache Airflow的协调 引擎,但原生于Kubernetes。它使用自定义CRD来定义复杂的工作流程,使用步骤或 DAGs使用YAML,在K8s中感觉更自然。它有一个漂亮的用户界面,重试机制,基于cron的工作,输入和输出的处理等等。你可以用它来协调数据管道、批处理作业和更多。
有时,你可能想将你的管道与异步服务集成,如流引擎(如 卡夫卡)、队列、Webhooks或深度存储服务。例如,你可能想对上传到S3的文件等事件做出反应。为此,你将使用 Argo事件.
Argo事件
这两个工具结合起来为你的所有管道需求提供了一个简单而强大的解决方案,包括CI/CD管道,这将使你能够在Kubernetes中原生地运行你的CI/CD管道。
正如你所期望的,Argo Workflows与ArgoCD完美整合,因为所有的工作流程定义都是CRD,可以在Helm图表中打包。
对于ML管线,你可以使用 Kubeflow ,它是为此目的而建立的。
对于CI/CD管线,你可以使用 泰克顿.
Istio
Istio是市场上最著名的 服务网市场上最著名的.NET,它是开源的,非常流行。我不会详述什么是服务网状结构,因为这是一个巨大的话题。 微服务那么你将需要一个服务网状结构来管理通信、可观察性、错误处理、安全和所有其他作为微服务架构一部分的交叉方面。与其用重复的逻辑来污染每个微服务的代码,不如利用服务网来为你做这件事。
Istio架构
简而言之,服务网是一个专门的基础设施层,你可以将其添加到你的应用程序中。它允许你透明地添加诸如可观察性、流量管理和安全等功能,而无需将它们添加到你自己的代码中。
Istio使用CRD来实现其所有功能,因此虚拟服务、网关、策略等都可以定义为代码,打包为Helm图表,并与ArgoCD或Flux一起使用,使Istio不仅非常强大,而且对GitOps友好。
凌克德(Linkerd 或 领事都是 Istio的最佳替代品 。
Argo推广
我们已经提到,你可以使用Kubernetes来运行你的CI/CD管道,使用Argo工作流或类似工具。下一个合乎逻辑的步骤是继续做持续部署。由于涉及到高风险,这在实际场景中是非常具有挑战性的,这就是为什么大多数公司只是做持续交付,这意味着他们有自动化的地方,但他们仍然有人工批准和验证,这个人工步骤是由于团队不能完全信任他们的自动化。
那么,你如何建立这种信任,以便能够摆脱所有的脚本,并将一切从源代码一直到生产的过程完全自动化?答案是:可观察性。你需要把资源更多地集中在指标上,并收集所有需要的数据,以准确表示你的应用程序的状态。我们的目标是使用一套指标来建立这种信任。如果你有所有的数据 普罗米修斯那么你就可以实现部署的自动化,因为你可以根据这些指标自动地逐步推出你的应用程序。
简而言之,你需要比K8s所提供的更高级的部署技术,即 滚动更新.我们需要使用金丝雀部署的渐进式交付。我们的目标是逐步将流量路由到新版本的应用程序,等待指标的收集,分析它们并将它们与预先定义的规则相匹配。如果一切正常,我们就增加流量;如果有任何问题,我们就退回部署。
要在Kubernetes中做到这一点,你可以使用 Argo滚动更新它提供了Canary版本和更多。
Argo Rollouts是一个 Kubernetes控制器 和一套 CRD 它为Kubernetes提供了先进的部署能力,如蓝绿、金丝雀、金丝雀分析、实验和渐进式交付功能。
虽然服务网格如 Istio提供金丝雀发布,但Argo Rollouts使这一过程更容易,而且以开发者为中心,因为它是专门为此目的而建立的。除此之外, Argo Rollouts还可以与任何服务网格集成。
Argo Rollouts 对GitOps友好,并与Argo Workflows 和ArgoCD完美集成**;**结合这3个工具,你可以创建一个非常强大的声明式工具集,满足你所有的部署需求。
FlaggerArgo Rollouts与Argo Rollouts非常相似,它与Argo Rollouts的集成度很高。 Flux所以如果你在使用Flux,可以考虑Flagger。
Crossplane 交叉飞机
Crossplane是我最喜欢的K8s工具,它为Kubernetes带来了一个关键的缺失部分:将第三方服务作为K8s资源来管理。这意味着,你可以像配置AWS RDS或GCP Cloud SQL,就像你在K8s中配置数据库一样,使用YAML中定义的K8s资源。


有了Crossplane,就不需要使用不同的工具和方法来分离基础设施和代码。你可以使用K8s资源来定义一切。这样一来,你就不需要学习新的工具,如 Terraform并将它们分开保存。
Crossplane是一个开源的Kubernetes插件,使平台团队能够从多个供应商那里组装基础设施,并为应用团队提供更高级别的自助服务API,而无需编写任何代码。
Crossplane扩展了你的Kubernetes集群,为你提供了任何基础设施或管理云服务的CRD。此外,它允许你完全实现持续部署,因为与Terraform等其他工具相反,Crossplane使用现有的K8s功能,如控制循环,持续观察你的集群,并检测任何配置漂移自动作用于它。例如,如果你定义了一个管理的数据库实例,而有人手动改变了它,Crossplane会自动检测到这个问题,并将其设置为以前的值。这就使得基础设施作为代码和 GitOps原则。
Crossplane与Argo CD配合得很好,Argo CD可以观察源代码,确保你的代码库是唯一的真理来源,代码中的任何变化都会传播到集群和外部云服务。
如果没有Crossplane,你只能在K8s服务中实现 GitOps在你的K8s服务中,而不是在你的云服务中,不使用一个单独的过程,现在你可以做到这一点,这是非常好的。
kyverno 启维诺
Kubernetes提供了巨大的灵活性,以增强敏捷的自主团队,但巨大的力量伴随着巨大的责任。必须有一套最佳实践和规则 ,以确保以一致的、有凝聚力的方式来部署和管理符合公司政策和安全要求的工作负载。
有几个工具可以实现这一点,但没有一个是Kubernetes的原生工具...直到现在。 凯威诺Kyverno是一个为Kubernetes设计的策略引擎,策略作为Kubernetes资源被管理,编写策略不需要新语言。Kyverno策略可以验证、变异和生成Kubernetes资源。


一个Kyverno策略是一个规则的集合。每个规则由一个 [match](https://kyverno.io/docs/writing-policies/match-exclude/)子句、一个可选的 [exclude](https://kyverno.io/docs/writing-policies/match-exclude/)子句,以及一个 [validate](https://kyverno.io/docs/writing-policies/validate/), [mutate](https://kyverno.io/docs/writing-policies/mutate/),或 [generate](https://kyverno.io/docs/writing-policies/generate)子句。一个规则定义只能包含一个validate,mutate, 或generate 子节点。
你可以应用任何一种有关最佳实践、网络或安全的政策。例如,你可以强制要求你的所有服务都有标签,或者所有的容器都以非root身份运行。你可以在这里查看一些策略的例子。策略可以应用于整个集群或一个特定的命名空间。你也可以选择是否只想审计政策或强制执行政策,阻止用户部署资源。
Kubevela
Kubernetes的一个问题是,开发者需要很好地了解和理解平台和集群配置。很多人会认为, K8s的抽象水平太低,这给那些只想专注于编写和发送应用程序的开发者带来了很多摩擦。
开放应用模型 (OAM)是为了克服这个问题而创建的。这个想法是围绕应用程序创建一个更高层次的抽象,它独立于底层运行时间。你可以在这里阅读该规范。
开放应用模型[OAM]专注于应用,而不是容器或协调器,为建模应用部署带来了模块化、可扩展和可移植的设计,具有更高层次但一致的API。
KubevelaKubeVela是OAM模型的一个实现。KubeVela与运行时无关,具有原生的可扩展性,但最重要的是,以_应用为中心_ 。在Kubevela中,应用程序是作为Kubernetes资源实现的第一等公民。集群操作员(平台团队)和开发人员(应用团队)之间有区别。集群操作员通过定义组件(可部署/可提供的实体,组成你的应用程序,如舵手图)和 特质**.**开发人员通过组装组件和特征来定义应用程序。


平台团队。将平台能力作为组件或特质进行建模和管理,同时还包括目标环境规范。应用团队。选择一个环境,根据需要用组件和特征组装应用程序,并将其部署到目标环境。
KubeVela是云原生计算基金会的一个沙盒项目,尽管它仍处于起步阶段,但它可以在不久的将来改变我们使用Kubernetes的方式,使开发人员能够专注于应用程序,而不是Kubernetes专家。然而,我确实对OAM在现实世界中的适用性有一些担忧,因为一些服务,如系统应用、ML或大数据流程,在很大程度上依赖于低级别的细节,而这些细节可能很难被纳入OAM模型中。
SchemaHero 模式英雄
软件开发中的另一个常见过程是在使用关系型数据库时管理模式的演变。
SchemaHero是一个开源的数据库模式迁移工具,它将模式定义转换为可在任何环境中应用的迁移脚本。它使用Kubernetes的声明性来管理数据库模式迁移。你只需指定所需的状态,其余的由SchemaHero来管理。
Bitnami密封的秘密
我们已经涵盖了许多GitOps工具,如 ArgoCD.我们的目标是把所有东西都放在Git中,并利用Kubernetes的声明性来保持环境的同步。我们刚刚看到了我们如何能够(也应该)把我们的真理之源保存在Git中,并由自动化流程处理配置变化。
有一件事通常很难保存在Git中,那就是DB密码或API密钥等秘密,这是因为**你不应该在代码仓库中存储秘密。**一个常见的解决方案是使用外部保险库,如 AWS秘密管理器 或 HashiCorp 金库 来存储秘密,但这产生了很多摩擦,因为你需要有一个单独的过程来处理秘密。理想情况下,我们希望有一种方法可以像其他资源一样在Git中安全存储秘密。
封闭的秘密Bitnami Sealed Secrets就是为了克服这个问题而创建的,它允许你通过使用强大的加密技术在Git中存储你的敏感数据。BitnamiSealed Secrets在Kubernetes中原生集成,只允许在Kubernetes中运行的Kubernetes控制器解密秘密,其他任何人都不能。控制器将解密数据并创建安全存储的本地K8s秘密。这使我们能够将所有的东西作为代码存储在我们的 repo 中,使我们能够在没有任何外部依赖的情况下安全地执行持续部署。
Sealed Secrets由两部分组成。
- 一个集群侧的控制器
- 一个客户端工具。
kubeseal
kubeseal 工具使用非对称加密技术对秘密进行加密,只有控制器可以解密。这些加密的秘密被编码在一个SealedSecret K8s资源中,你可以将其存储在Git中。
Capsule 胶囊
许多公司使用多租户来管理不同的客户。这在软件开发中很常见,但在Kubernetes中很难实现。命名空间是创建集群的逻辑分区作为隔离_片_ 的好方法,但这还不够,为了安全地隔离客户,我们需要执行网络策略、配额等。你可以为每个名称空间创建网络策略和规则,但这是一个繁琐的过程,很难扩展。此外,租户将不能使用一个以上的命名空间,这是一个很大的限制。
分层命名空间为了克服其中的一些问题,我们创建了一个新的K8系统。这个想法是为每个租户提供一个父命名空间,并为租户提供共同的网络策略和配额,允许创建子命名空间。这是一个很大的改进,但在安全和治理方面,它没有对租户的本地支持。此外,它还没有达到生产状态,但1.0版本预计将在未来几个月内发布。
目前解决这个问题的常见方法是为每个客户创建一个集群,这很安全,并提供租户所需的一切,但这很难管理,而且非常昂贵。
胶囊Capsule是一个工具,为单个集群内的多个租户提供原生Kubernetes**支持。**使用Capsule,你可以为你的所有租户提供一个集群。Capsule将为租户提供 "几乎 "原生的体验(有一些小的限制),他们将能够创建多个命名空间并使用集群,因为它是完全为他们提供的,隐藏了集群实际上是共享的事实。


Capsule 胶囊架构
在一个集群中,胶囊控制器将多个命名空间聚集在一个轻量级的Kubernetes抽象中,称为 租户,它是Kubernetes命名空间的一个分组。在每个租户内,用户可以自由地创建他们的命名空间,并共享所有分配的资源,同时策略引擎保持不同租户之间的隔离。
网络和安全策略、资源配额、限制范围、_RBAC_和其他在租户层面定义的策略,会自动被租户中的所有命名空间继承,类似于分层命名空间。然后,用户可以自由地自主操作他们的租户,不需要集群管理员的干预。
Capsule为GitOps做好了准备,因为它是声明式的,所有的配置都可以存储在Git中。
总结
在这篇文章中,我们回顾了我最喜欢的GitOps友好型Kubernetes工具。我把重点放在可以被纳入任何Kubernetes发行版的开源项目上。
我的目标是告诉你,由于GitOps的最佳实践,你可以在Kubernetes中 利用其声明性的特点做一切事情 。