你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn

教程:使用 GitOps with Flux v2 部署应用程序

本教程介绍如何在 Kubernetes 群集中使用 GitOps。 在已启用 Azure Arc 的 Kubernetes 群集或 Azure Kubernetes 服务 (AKS) 群集中,启用了带有 Flux v2 的 GitOps 作为群集扩展。 安装 microsoft.flux 群集扩展后,可以创建一个或多个 fluxConfigurations 资源,用于将 Git 存储库源同步到群集,并将群集调整到所需状态。 借助 GitOps,可将 Git 存储库用作群集配置和应用程序部署的事实来源。

在本教程中,我们将使用包含两个 kustomization 的示例 GitOps 配置,以便你可以了解一个 kustomization 如何依赖于另一个。 可以根据需要添加更多自定义和依赖项,具体取决于你的方案。

在开始之前,请花点时间了解 GitOps with Flux 在概念上的工作原理

提示

虽然本教程中的源是 Git 存储库,但 Flux 还提供了对其他常见文件源的支持,如 Helm 存储库、Buckets 和 Azure Blob 存储。

还可以使用 Bicep、ARM 模板或 Terraform AzAPI 提供程序创建 Flux 配置。 有关详细信息,请参阅 Microsoft.KubernetesConfiguration fluxConfigurations

重要

microsoft.flux 扩展发布了主要版本 1.0.0。 这包括多租户功能。 如果现有的 GitOps Flux v2 配置使用以前版本的 microsoft.flux 扩展,则可以使用 Azure CLI:az k8s-extension create -g <RESOURCE_GROUP> -c <CLUSTER_NAME> -n flux --extension-type microsoft.flux -t <CLUSTER_TYPE>(对于 Arc 群集,使用 -t connectedClusters;对于 AKS 群集,使用 -t managedClusters)手动升级到最新版本

先决条件

若要将 GitOps 与 Flux v2 配合使用来部署应用程序,需要满足以下条件:

对于已启用 Azure Arc 的 Kubernetes 群集

对于 Azure Kubernetes 服务群集

  • 一个已启动并运行的基于 MSI 的 AKS 群集。

    重要

    确保 AKS 群集是使用 MSI(而不是 SPN)创建的,因为 microsoft.flux 扩展不适用于基于 SPN 的 AKS 群集。 对于使用 az aks create 创建的新 AKS 群集,群集默认基于 MSI。 对于已创建的、需要转换为 MSI 的基于 SPN 的群集,请运行 az aks update -g $RESOURCE_GROUP -n $CLUSTER_NAME --enable-managed-identity。 有关详细信息,请参阅在 AKS 中使用托管标识

  • Microsoft.ContainerService/managedClusters 资源类型的读写权限。

通用于上述两种群集类型

  • 对这些资源类型的读取和写入权限:

    • Microsoft.KubernetesConfiguration/extensions
    • Microsoft.KubernetesConfiguration/fluxConfigurations
  • Azure CLI 2.15 或更高版本。 安装 Azure CLI 或使用以下命令更新到最新版本:

    az version
    az upgrade
    
  • Kubernetes 命令行客户端 kubectl。 如果使用的是 Azure Cloud Shell,则 kubectl 已安装。

    在本地使用 az aks install-cli 命令安装 kubectl

    az aks install-cli
    
  • 注册以下 Azure 资源提供程序:

    az provider register --namespace Microsoft.Kubernetes
    az provider register --namespace Microsoft.ContainerService
    az provider register --namespace Microsoft.KubernetesConfiguration
    

    注册是一个异步过程,在 10 分钟内应会完成。 可以使用以下命令来监视注册过程:

    az provider show -n Microsoft.KubernetesConfiguration -o table
    
    Namespace                          RegistrationPolicy    RegistrationState
    ---------------------------------  --------------------  -------------------
    Microsoft.KubernetesConfiguration  RegistrationRequired  Registered
    

版本和区域支持

目前,已启用 Azure Arc 的 Kubernetes 所支持的所有区域都支持 GitOps。 目前,AKS 所支持的一部分区域支持 GitOps。 GitOps 服务会定期添加新的受支持区域。

支持 Flux v2 扩展的最新版本和前两个版本 (N-2)。 我们通常建议使用最新版本的扩展。

网络要求

GitOps 代理必须通过出站(出口)TCP 连接到端口 22 (SSH) 或端口 443 (HTTPS) 上的存储库源才能正常运行。 代理还需要以下出站 URL 的访问权限:

终结点 (DNS) 说明
https://management.azure.com 必须提供此终结点才能使代理能够与 Kubernetes 配置服务通信。
https://<region>.dp.kubernetesconfiguration.azure.com 代理的数据平面终结点,用于推送状态和提取配置信息。 取决于 <region>(前面提到的受支持区域)。
https://login.microsoftonline.com 提取和更新 Azure 资源管理器令牌所需的终结点。
https://mcr.microsoft.com 必须提供此终结点才能拉取 Flux 控制器的容器映像。

启用 CLI 扩展

安装最新的 k8s-configurationk8s-extension CLI 扩展包:

az extension add -n k8s-configuration
az extension add -n k8s-extension

将这些包更新到最新版本:

az extension update -n k8s-configuration
az extension update -n k8s-extension

若要查看已安装的 Azure CLI 扩展列表及其版本,请使用以下命令:

az extension list -o table

Experimental   ExtensionType   Name                   Path                                                       Preview   Version
-------------  --------------  -----------------      -----------------------------------------------------      --------  --------
False          whl             connectedk8s           C:\Users\somename\.azure\cliextensions\connectedk8s         False     1.2.7
False          whl             k8s-configuration      C:\Users\somename\.azure\cliextensions\k8s-configuration    False     1.5.0
False          whl             k8s-extension          C:\Users\somename\.azure\cliextensions\k8s-extension        False     1.1.0

提示

有关解决任何错误的帮助,请参阅排查已启用 Azure Arc 的 Kubernetes 群集的扩展问题的 GitOps (Flux v2) 部分。

应用 Flux 配置

使用 k8s-configuration Azure CLI 扩展或 Azure 门户在 AKS 群集或已启用 Arc 的 Kubernetes 群集中启用 GitOps。 要进行演示,请使用公共 gitops-flux2-kustomize-helm-mt 存储库。

重要

演示存储库旨在简化本教程的使用,演示了一些关键原则。 为了保持最新状态,存储库有时会从版本升级中获取中断性变更。 这些变更不会影响本教程的新应用程序,仅影响尚未删除的以前的教程应用程序。 若要了解如何处理这些变更,请参阅中断性变更免责声明

以下示例通过 az k8s-configuration create 命令使用以下值和设置将 Flux 配置应用于群集:

  • 包含群集的资源组是 flux-demo-rg
  • Azure Arc 群集的名称是 flux-demo-arc
  • 群集类型是 Azure Arc (-t connectedClusters),但此示例也适用于 AKS (-t managedClusters)。
  • Flux 配置名称是 cluster-config
  • 用于配置安装的命名空间是 cluster-config
  • 公共 Git 存储库的 URL 是 https://github.com/Azure/gitops-flux2-kustomize-helm-mt
  • Git 存储库分支是 main
  • 配置范围是 cluster。 此范围授予操作员在整个群集中进行更改的权限。 若要在本教程中使用 namespace 范围,请参阅所需的变更
  • 使用名称 infraapps 指定了两个自定义项。 每个自定义项与存储库中的某个路径相关联。
  • apps 自定义项依赖于 infra 自定义项。 (infra 自定义项必须在 apps 自定义项运行之前完成。)
  • 在两个自定义项上设置 prune=true。 此设置确保在从存储库中删除了由 Flux 部署到群集的对象时,或者在删除了 Flux 配置或自定义项时,会清理这些对象。
az k8s-configuration flux create -g flux-demo-rg \
-c flux-demo-arc \
-n cluster-config \
--namespace cluster-config \
-t connectedClusters \
--scope cluster \
-u https://github.com/Azure/gitops-flux2-kustomize-helm-mt \
--branch main  \
--kustomization name=infra path=./infrastructure prune=true \
--kustomization name=apps path=./apps/staging prune=true dependsOn=\["infra"\]

microsoft.flux 扩展安装在群集上(如果尚未在之前的 GitOps 部署中安装)。

提示

az k8s-configuration create 命令会将 microsoft.flux 扩展部署到群集并创建配置。 在某些情况下,可能需要先单独创建 flux 扩展实例,然后再创建配置资源。 为此,请使用 az k8s-extension create 命令在群集上创建扩展的实例

安装 flux 配置后,初始符合性状态可能是 PendingNon-compliant,因为状态仍在核查中。 一分钟后,可以再次查询配置并查看最终的符合性状态。

az k8s-configuration flux show -g flux-demo-rg -c flux-demo-arc -n cluster-config -t connectedClusters

若要确认部署是否成功,请运行以下命令:

az k8s-configuration flux show -g flux-demo-rg -c flux-demo-arc -n cluster-config -t connectedClusters

成功部署后,将创建以下命名空间:

  • flux-system:保存 Flux 扩展控制器。
  • cluster-config:保存 Flux 配置对象。
  • nginxpodinforedis:Git 存储库的清单中描述的工作负载的命名空间。

若要确认命名空间,请运行以下命令:

kubectl get namespaces

flux-system 命名空间包含 Flux 扩展对象:

  • Azure Flux 控制器:fluxconfig-agentfluxconfig-controller
  • OSS Flux 控制器:source-controllerkustomize-controllerhelm-controllernotification-controller

Flux 代理和控制器 pod 应处于正在运行状态。 使用以下命令确认这一点:

kubectl get pods -n flux-system

NAME                                      READY   STATUS    RESTARTS   AGE
fluxconfig-agent-9554ffb65-jqm8g          2/2     Running   0          21m
fluxconfig-controller-9d99c54c8-nztg8     2/2     Running   0          21m
helm-controller-59cc74dbc5-77772          1/1     Running   0          21m
kustomize-controller-5fb7d7b9d5-cjdhx     1/1     Running   0          21m
notification-controller-7d45678bc-fvlvr   1/1     Running   0          21m
source-controller-df7dc97cd-4drh2         1/1     Running   0          21m

命名空间 cluster-config 包含 Flux 配置对象。

kubectl get crds

NAME                                                   CREATED AT
alerts.notification.toolkit.fluxcd.io                  2022-04-06T17:15:48Z
arccertificates.clusterconfig.azure.com                2022-03-28T21:45:19Z
azureclusteridentityrequests.clusterconfig.azure.com   2022-03-28T21:45:19Z
azureextensionidentities.clusterconfig.azure.com       2022-03-28T21:45:19Z
buckets.source.toolkit.fluxcd.io                       2022-04-06T17:15:48Z
connectedclusters.arc.azure.com                        2022-03-28T21:45:19Z
customlocationsettings.clusterconfig.azure.com         2022-03-28T21:45:19Z
extensionconfigs.clusterconfig.azure.com               2022-03-28T21:45:19Z
fluxconfigs.clusterconfig.azure.com                    2022-04-06T17:15:48Z
gitconfigs.clusterconfig.azure.com                     2022-03-28T21:45:19Z
gitrepositories.source.toolkit.fluxcd.io               2022-04-06T17:15:48Z
helmcharts.source.toolkit.fluxcd.io                    2022-04-06T17:15:48Z
helmreleases.helm.toolkit.fluxcd.io                    2022-04-06T17:15:48Z
helmrepositories.source.toolkit.fluxcd.io              2022-04-06T17:15:48Z
imagepolicies.image.toolkit.fluxcd.io                  2022-04-06T17:15:48Z
imagerepositories.image.toolkit.fluxcd.io              2022-04-06T17:15:48Z
imageupdateautomations.image.toolkit.fluxcd.io         2022-04-06T17:15:48Z
kustomizations.kustomize.toolkit.fluxcd.io             2022-04-06T17:15:48Z
providers.notification.toolkit.fluxcd.io               2022-04-06T17:15:48Z
receivers.notification.toolkit.fluxcd.io               2022-04-06T17:15:48Z
volumesnapshotclasses.snapshot.storage.k8s.io          2022-03-28T21:06:12Z
volumesnapshotcontents.snapshot.storage.k8s.io         2022-03-28T21:06:12Z
volumesnapshots.snapshot.storage.k8s.io                2022-03-28T21:06:12Z
websites.extensions.example.com                        2022-03-30T23:42:32Z

使用以下命令确认配置的其他详细信息。

kubectl get fluxconfigs -A

NAMESPACE        NAME             SCOPE     URL                                                       PROVISION   AGE
cluster-config   cluster-config   cluster   https://github.com/Azure/gitops-flux2-kustomize-helm-mt   Succeeded   44m
kubectl get gitrepositories -A

NAMESPACE        NAME             URL                                                       READY   STATUS                                                            AGE
cluster-config   cluster-config   https://github.com/Azure/gitops-flux2-kustomize-helm-mt   True    Fetched revision: main/4f1bdad4d0a54b939a5e3d52c51464f67e474fcf   45m
kubectl get helmreleases -A

NAMESPACE        NAME      READY   STATUS                             AGE
cluster-config   nginx     True    Release reconciliation succeeded   66m
cluster-config   podinfo   True    Release reconciliation succeeded   66m
cluster-config   redis     True    Release reconciliation succeeded   66m
kubectl get kustomizations -A


NAMESPACE        NAME                   READY   STATUS                                                            AGE
cluster-config   cluster-config-apps    True    Applied revision: main/4f1bdad4d0a54b939a5e3d52c51464f67e474fcf   65m
cluster-config   cluster-config-infra   True    Applied revision: main/4f1bdad4d0a54b939a5e3d52c51464f67e474fcf   65m

工作负载是从 Git 存储库中的清单部署的。

kubectl get deploy -n nginx

NAME                                       READY   UP-TO-DATE   AVAILABLE   AGE
nginx-ingress-controller                   1/1     1            1           67m
nginx-ingress-controller-default-backend   1/1     1            1           67m

kubectl get deploy -n podinfo

NAME      READY   UP-TO-DATE   AVAILABLE   AGE
podinfo   1/1     1            1           68m

kubectl get all -n redis

NAME                 READY   STATUS    RESTARTS   AGE
pod/redis-master-0   1/1     Running   0          68m

NAME                     TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)    AGE
service/redis-headless   ClusterIP   None          <none>        6379/TCP   68m
service/redis-master     ClusterIP   10.0.13.182   <none>        6379/TCP   68m

NAME                            READY   AGE
statefulset.apps/redis-master   1/1     68m

控制使用 Flux 群集扩展部署哪些控制器

在某些情况下,你可能希望更改随 Flux 群集扩展一起安装的 Flux 控制器。

默认已安装 sourcehelmkustomizenotification Flux 控制器。 在新的容器映像可用时,用于更新 Git 存储库的 image-automationimage-reflector 控制器必须显式启用。

可以使用 k8s-extension 命令更改默认选项:

  • --config source-controller.enabled=<true/false>(默认为 true
  • --config helm-controller.enabled=<true/false>(默认为 true
  • --config kustomize-controller.enabled=<true/false>(默认为 true
  • --config notification-controller.enabled=<true/false>(默认为 true
  • --config image-automation-controller.enabled=<true/false>(默认为 false
  • --config image-reflector-controller.enabled=<true/false>(默认为 false

例如,若要禁用通知,可以将 notification-controller.enabled 设置为 false

此示例命令安装 image-reflectorimage-automation 控制器。 如果 Flux 扩展是在首次创建 Flux 配置时自动创建的,则扩展名称将是 flux

az k8s-extension create -g <cluster_resource_group> -c <cluster_name> -t <connectedClusters or managedClusters or provisionedClusters> --name flux --extension-type microsoft.flux --config image-automation-controller.enabled=true image-reflector-controller.enabled=true

使用 Kubelet 标识作为 AKS 群集的身份验证方法

对于 AKS 群集,要使用的身份验证选项之一是 Kubelet 标识。 默认情况下,AKS 在托管资源组中创建自己的 kubelet 标识。 如果需要,可以使用预先创建的 kubelet 托管标识。 为此,请在安装 Flux 扩展时添加 --config useKubeletIdentity=true 参数。

az k8s-extension create --resource-group <resource-group> --cluster-name <cluster-name> --cluster-type managedClusters --name flux --extension-type microsoft.flux --config useKubeletIdentity=true

Red Hat OpenShift 载入指南

Flux 控制器需要非根安全上下文约束才能在群集上正确预配 Pod。 在载入 microsoft.flux 扩展之前,必须将这些约束添加到群集。

NS="flux-system"
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:kustomize-controller
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:helm-controller
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:source-controller
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:notification-controller
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:image-automation-controller
oc adm policy add-scc-to-user nonroot system:serviceaccount:$NS:image-reflector-controller

有关载入 Flux 的 OpenShift 指南的详细信息,请参阅 Flux 文档

使用参数

Flux 支持用于实现各种场景的许多参数。 有关 Flux 支持的所有参数的说明,请参阅官方 Flux 文档。 Azure 中的 Flux 尚不支持所有参数。 如果 Azure 实现中缺少你需要的参数,请告诉我们。

有关可用参数及其用法的信息,请参阅 GitOps (Flux v2) 支持的参数

使用 Flux Kustomize 控制器管理群集配置

Flux Kustomize 控制器已安装为 microsoft.flux 群集扩展的一部分。 使用该控制器可以通过从 Git 存储库同步的 Kubernetes 清单对群集配置和应用程序部署进行声明性管理。 这些 Kubernetes 清单可以选择性地包含 kustomize.yaml 文件。

有关用法详细信息,请参阅以下资源:

使用 Flux Helm 控制器管理 Helm 图表版本

Flux Helm 控制器已安装为 microsoft.flux 群集扩展的一部分。 使用该控制器可以通过在 Git 存储库中维护的 Kubernetes 清单以声明方式管理 Helm 图表版本。

有关用法详细信息,请参阅以下资源:

提示

考虑到 Helm 处理索引文件的方式,处理 Helm 图表是一项开销很大的操作,内存占用量可能非常高。 因此,一次性调整大量 Helm 图表可能会导致出现内存峰值和 OOMKilled 错误。 默认情况下,控制器将其内存限制设置为 1Gi,将其内存请求设置为 64Mi。 如果因为存在大量的大型 Helm 图表调整而需要提高此限制和请求数,可以在安装 microsoft.flux 扩展后运行以下命令:

az k8s-extension update -g <resource-group> -c <cluster-name> -n flux -t connectedClusters --config source-controller.resources.limits.memory=2Gi source-controller.resources.requests.memory=300Mi

将 GitRepository 源用于 Helm 图表

如果 Helm 图表存储在配置为 fluxConfigurations 资源一部分的 GitRepository 源中,可以向 HelmRelease yaml 文件添加 clusterconfig.azure.com/use-managed-source: "true",以指示配置的源应用作 Helm 图表的源,如下例所示:

---
apiVersion: helm.toolkit.fluxcd.io/v2beta1
kind: HelmRelease
metadata:
  name: somename
  namespace: somenamespace
  annotations:
    clusterconfig.azure.com/use-managed-source: "true"
spec:
  ...

使用此批注时,将会使用对已配置源的引用来修补部署的 HelmRelease。 目前仅支持 GitRepository 源。

Helm 偏移检测

默认情况下不启用 Helm 版本的偏移检测。 从 microsoft.fluxv1.7.5 开始,可以通过运行以下命令来启用 Helm 偏移检测:

az k8s-extension update --resource-group <resource-group> --cluster-name <cluster-name> --name flux --cluster-type <cluster-type> --config helm-controller.detectDrift=true 

Helm OOM watch

microsoft.fluxv1.7.5 开始,可以启用 Helm OOM watch。 有关详细信息,请参阅启用 Helm 近 OOM 检测

请务必查看潜在的修正策略,并在启用此功能时根据需要应用这些策略。

要启用 OOM watch,请运行以下命令:

az k8s-extension update --resource-group <resource-group> --cluster-name <cluster-name> --name flux --cluster-type <cluster-type> --config helm-controller.outOfMemoryWatch.enabled=true helm-controller.outOfMemoryWatch.memoryThreshold=70 helm-controller.outOfMemoryWatch.interval=700ms

如果未为 memoryThresholdoutOfMemoryWatch 指定值,则默认内存阈值将设置为 95%,并将检查内存利用率的间隔设置为 500 毫秒。

AKS 群集中的工作负载标识

microsoft.flux v1.8.0 开始,可以在启用了工作负载标识的 AKS 群集中创建 Flux 配置。 为此,修改 flux 扩展,如以下步骤所示。

  1. 检索群集的 OIDC 颁发者 URL

  2. 创建托管标识并记下其客户端 ID。

  3. 使用以下命令在群集上创建 flux 扩展:

    az k8s-extension create --resource-group <resource_group_name> --cluster-name <aks_cluster_name> --cluster-type managedClusters --name flux --extension-type microsoft.flux --config workloadIdentity.enable=true workloadIdentity.azureClientId=<user_assigned_client_id>
    
  4. 建立联合标识凭据。 例如:

    # For source-controller
    az identity federated-credential create --name ${FEDERATED_IDENTITY_CREDENTIAL_NAME} --identity-name "${USER_ASSIGNED_IDENTITY_NAME}" --resource-group "${RESOURCE_GROUP}" --issuer "${AKS_OIDC_ISSUER}" --subject system:serviceaccount:"flux-system":"source-controller" --audience api://AzureADTokenExchange
    
    # For image-reflector controller if you plan to enable it during extension creation, it is not deployed by default
    az identity federated-credential create --name ${FEDERATED_IDENTITY_CREDENTIAL_NAME} --identity-name "${USER_ASSIGNED_IDENTITY_NAME}" --resource-group "${RESOURCE_GROUP}" --issuer "${AKS_OIDC_ISSUER}" --subject system:serviceaccount:"flux-system":"image-reflector-controller" --audience api://AzureADTokenExchange
    
  5. 确保需要使用工作负载标识的自定义资源已在清单中将 .spec.provider 值设置为 azure。 例如:

    apiVersion: source.toolkit.fluxcd.io/v1beta2
    kind: HelmRepository
    metadata:
      name: acrrepo
    spec:
      interval: 10m0s
      type: <helm_repository_type>
      url: <helm_repository_link>
      provider: azure
    
  6. 务必为希望源控制器或图像反射器控制器拉取的资源提供适当的工作负载标识权限。 例如,如果使用 Azure 容器注册表,则需要 AcrPull 权限。

删除 Flux 配置和扩展

使用以下命令删除 Flux 配置,并在需要时删除 Flux 扩展本身。

删除 Flux 配置

以下命令会删除 Azure 中的 fluxConfigurations 资源以及群集中的 Flux 配置对象。 Flux 配置最初是使用 kustomization 的 prune=true 参数创建的,因此在删除 Flux 配置时,会删除群集内基于 Git 存储库中的清单创建的所有对象。 但是,此命令不会移除 Flux 扩展本身。

az k8s-configuration flux delete -g flux-demo-rg -c flux-demo-arc -n cluster-config -t connectedClusters --yes

删除 Flux 群集扩展

删除 Flux 扩展时,Azure 中的 microsoft.flux 扩展资源和群集中的 Flux 扩展对象都会被删除。

重要

在删除 Flux 扩展之前,请务必删除群集中的所有 Flux 配置。 如果在删除扩展而不首先删除 Flux 配置,可能会使群集处于不稳定状态。

如果 Flux 扩展是在首次创建 Flux 配置时自动创建的,扩展名称将是 flux

az k8s-extension delete -g flux-demo-rg -c flux-demo-arc -n flux -t connectedClusters --yes

提示

这些命令使用 -t connectedClusters,后者适用于已启用 Azure Arc 的 Kubernetes 群集。 对于 AKS 群集,请改用 -t managedClusters

后续步骤