Flagger(应用自动发布)介绍和原理剖析

本文涉及的产品
容器服务 Serverless 版 ACK Serverless,952元额度 多规格
可观测监控 Prometheus 版,每月50GB免费额度
容器服务 Serverless 版 ACK Serverless,317元额度 多规格
简介: ## 简介 [Flagger](https://github.com/weaveworks/flagger)是一个能使运行在k8s体系上的应用发布流程全自动(无人参与)的工具, 它能减少发布的人为关注时间, 并且在发布过程中能自动识别一些风险(例如:RT,成功率,自定义metrics)并回滚. ## 主要特性 ![features](https://intranetproxy.ali

简介

Flagger是一个能使运行在k8s体系上的应用发布流程全自动(无人参与)的工具, 它能减少发布的人为关注时间, 并且在发布过程中能自动识别一些风险(例如:RT,成功率,自定义metrics)并回滚.

主要特性

features

整体架构

arch
简单介绍下上图含义:
• primary service: 服务稳定版本. 可以理解为已发布在线的服务
• canary service: 即将发布的新版本服务.
• Ingress: 服务网关.
• Flagger: 会通过flagger spec(下面会介绍), 以ingress/service mesh的规范来调整primary和canary的流量策略.以此来达到A/B testing, blue/green, canary(金丝雀)发布效果. 在调整流量过程中, 根据prometheus采集的各项指标(RT,成功率等)来决策是否回滚发布或者继续调整流量比例。在此过程中,用户可以自定义是否人工干预,审核,收到通知等.

实现原理

注: 以下原理介绍, 主要基于以下的官方的实例说明:

apiVersion: flagger.app/v1beta1
kind: Canary
metadata:
  name: podinfo
  namespace: test
spec:
  # service mesh provider (optional)
  # can be: kubernetes, istio, linkerd, appmesh, nginx, contour, gloo, supergloo
  provider: istio
  # deployment reference
  targetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: podinfo
  # the maximum time in seconds for the canary deployment
  # to make progress before it is rollback (default 600s)
  progressDeadlineSeconds: 60
  # HPA reference (optional)
  autoscalerRef:
    apiVersion: autoscaling/v2beta1
    kind: HorizontalPodAutoscaler
    name: podinfo
  service:
    # service name (defaults to targetRef.name)
    name: podinfo
    # ClusterIP port number
    port: 9898
    # container port name or number (optional)
    targetPort: 9898
    # port name can be http or grpc (default http)
    portName: http
    # add all the other container ports
    # to the ClusterIP services (default false)
    portDiscovery: true
    # HTTP match conditions (optional)
    match:
      - uri:
          prefix: /
    # HTTP rewrite (optional)
    rewrite:
      uri: /
    # request timeout (optional)
    timeout: 5s
  # promote the canary without analysing it (default false)
  skipAnalysis: false
  # define the canary analysis timing and KPIs
  analysis:
    # schedule interval (default 60s)
    interval: 1m
    # max number of failed metric checks before rollback
    threshold: 10
    # max traffic percentage routed to canary
    # percentage (0-100)
    maxWeight: 50
    # canary increment step
    # percentage (0-100)
    stepWeight: 5
    # validation (optional)
    metrics:
    - name: request-success-rate
      # builtin Prometheus check
      # minimum req success rate (non 5xx responses)
      # percentage (0-100)
      thresholdRange:
        min: 99
      interval: 1m
    - name: request-duration
      # builtin Prometheus check
      # maximum req duration P99
      # milliseconds
      thresholdRange:
        max: 500
      interval: 30s
    - name: "database connections"
      # custom Prometheus check
      templateRef:
        name: db-connections
      thresholdRange:
        min: 2
        max: 100
      interval: 1m
    # testing (optional)
    webhooks:
      - name: "conformance test"
        type: pre-rollout
        url: http://flagger-helmtester.test/
        timeout: 5m
        metadata:
          type: "helmv3"
          cmd: "test run podinfo -n test"
      - name: "load test"
        type: rollout
        url: http://flagger-loadtester.test/
        metadata:
          cmd: "hey -z 1m -q 10 -c 2 http://podinfo.test:9898/"
    # alerting (optional)
    alerts:
      - name: "dev team Slack"
        severity: error
        providerRef:
          name: dev-slack
          namespace: flagger
      - name: "qa team Discord"
        severity: warn
        providerRef:
          name: qa-discord
      - name: "on-call MS Teams"
        severity: info
        providerRef:
          name: on-call-msteams

简单介绍以上配置含义, 下方会单独详细介绍:
• targetRef: 当前部署的新版本服务(可以是Deployment, 也可以是DaemonSet).
• progressDeadlineSeconds: canary, primary部署超时时间.如果超过这个时间还没有部署好,则不会进行流量调整了。
• autoscalerRef: K8s原生的HPA(自动伸缩).
• service: 可以理解为k8s service概念。当provider是Istio时, 和VirtualSercice(具有调整流量比例,路由策略等能力)相对应
• skipAnalysis:是否跳过metrcis分析. 如果为true, 相当于一次性将primary替换成canary service.
• analysis:
• 包含一些调整primary, canary流量策略配置
• metrics: 指标来源. 例如: avg RT, 成功率, 自定义metrics(可以直接配置prometheus PQL)等
• webhook:可以用来人工审核接入, 压力测试等.
• alerts: 进度详情, 告警通知等

整体流程

flow
说明:
• 上图Start到End的整个流程是在一个定时器中执行
• 上图中cancary和Canary不是同一个含义. Canary一般指Canary(Kind)对象或者指Canary 部署策略, canary指的是targetRef的对象(deployment, service)。
VirtualSerivice(privider是Istio): 是A/B testing, Blue/Green, Canry Release实现的关键. 具体可以参考Istio关于VirtualService相关介绍
• 关于A/B testing, Blue/Green, Canary下文会详细介绍

部署策略

A/B testing

analysis:
    # schedule interval (default 60s)
    interval: 1m
    # total number of iterations
    iterations: 10
    # max number of failed iterations before rollback
    threshold: 2
    # canary match condition
    match:
      - headers:
          x-canary:
            regex: ".*insider.*"
      - headers:
          cookie:
            regex: "^(.*?;)?(canary=always)(;.*)?$"

以上面代码示例为例:
• 会在创建VirtualService过(istio)程中, 设置多个HTTPRoute.
• 默认流量, 访问primary service
• 通过http header或者cookie 正则匹配方式, 将流量路由到canary service.
• 整个流程会执行10次,每次间隔1分钟, 最多允许2次metrics验证失败. 如果超过2次, 则进行回滚.
• 正常结束后, 会执行"confirm-promotion" webhook, 确认是否将primary替换成cannay

• 如果是, 会将primary替换成cananry的spec(deployemnt spec, configmap)相关信息
• 如果否, 继续等待

Blue/Green

 analysis:
    # schedule interval (default 60s)
    interval: 1m
    # total number of iterations
    iterations: 10
    # max number of failed iterations before rollback
    threshold: 2
    webhooks:
     - name: "load test"
       type: rollout
       url: http://flagger-loadtester.test/
       metadata:
         cmd: "hey -z 1m -q 10 -c 2 http://podinfo.test:9898/"

以上面代码示例为例:
• 整个流程会执行10次,每次间隔1分钟, 最多允许2次metrics验证失败.如果超过2次, 则进行回滚.
• 在这段时间会对canary service进行压力测试
• 正常结束后, 会执行"confirm-promotion" webhook, 确认是否将primary替换成cannay

• 如果是, 会将primary替换成cananry的spec(deployemnt spec, configmap)相关信息
• 如果否, 继续等待

如果配置了mirror=true(只有provider=istio时才支持该特性), 则会使用istio的mirror特性, 将流量分别copy 到primary和canary, 使用primary的reponse作为返回值. 这个时候要特别注意业务是否幂等.

Canary

analysis:
    # schedule interval (default 60s)
    interval: 1m
    # max number of failed metric checks before rollback
    threshold: 2
    # max traffic percentage routed to canary
    # percentage (0-100)
    maxWeight: 50
    # canary increment step
    # percentage (0-100)
    stepWeight: 2
  # deploy straight to production without
  # the metrics and webhook checks
  skipAnalysis: false

以上面代码示例为例:
• 整个流程会执行25(maxWeight/maxWeight)次,每次间隔1分钟, 最多允许2次metrics验证失败.如果超过2次, 则进行回滚.
• 每次primary减少stepWeight%流量, canary增加stepWeight%流量, 直到canary到达maxWeight
• 执行"confirm-promotion" webhook, 确认是否将primary替换成cannay

• 如果是, 会将primary替换成cananry的spec(deployemnt spec, configmap)相关信息
• 如果否, 继续等待

其它

Webhooks

webhooks: 在整个发布过程中, 定义了相应的扩展点:
• confirm-rollout: 在canary接收流量之前执行. 可以用于人工审核发布, 自动化测试通过等场景.
如果该webhook没有返回成功(例如:请求返回状态码200), 则发布一直等待.
• pre-rollout: 在第一次切流到canary前执行的webhook. 如果执行失败次数超过阀值, 则进行回滚
• rollout: 在发布的每个周期(例如每个stepWeight)中的metrics分析之前执行.如果执行失败次数超过阀值, 则进行回滚
• confirm-promotion: 在primary变更到canary配置相关信息之前执行.
如果不成功, 会一直等待.在等待的过程中, Flagger会继续执行metrics验证直到最终回滚.
• post-rollout: 在rollback或者finish后执行. 如果执行失败只会记录Event日志。
• rollback: 当Canary处于Progressing或者Waiting状态时. 提供人工执行回滚的能力.
• event: 在每个生命周期,都会产生一些相关k8s event. 如果配置event webhook, 则在产生k8s event的同时,发送相关event事件信息.

Metrics

Metrics: 用于决策(A/B, Blue/Green, Canary)流量是否验证失败, 超过制定阀值(threshold)就会回滚发布
• 缺省自带的metrics

analysis:
    metrics:
    - name: request-success-rate
      interval: 1m
      # minimum req success rate (non 5xx responses)
      # percentage (0-100)
      thresholdRange:
        min: 99
    - name: request-duration
      interval: 1m
      # maximum req duration P99
      # milliseconds
      thresholdRange:
        max: 500
  • request-success-rate(请求成功率). 上例说明成功率不能低于99%
  • request-duration(avg RT): RT均值不能超过500ms
    request-success-rate和request-duration是Flagger缺省自带的metrics.

不同的provider有不通实现. 例如:应用可以提供prometheus metrics

• 自定义metrics

  1. 创建MetricTemplate. 比如业务自定义的业务metrics, 如订单支付失败率
apiVersion: flagger.app/v1beta1
kind: MetricTemplate
metadata:
  name: not-found-percentage
  namespace: istio-system
spec:
  provider:
    type: prometheus
    address: http://promethues.istio-system:9090
  query: |
    100 - sum(
        rate(
            istio_requests_total{
              reporter="destination",
              destination_workload_namespace="{{ namespace }}",
              destination_workload="{{ target }}",
              response_code!="404"
            }[{{ interval }}]
        )
    )
    /
    sum(
        rate(
            istio_requests_total{
              reporter="destination",
              destination_workload_namespace="{{ namespace }}",
              destination_workload="{{ target }}"
            }[{{ interval }}]
        )
    ) * 100
  1. 引用MetricTemplate

    analysis:
       metrics:
    - name: "404s percentage"
     templateRef:
       name: not-found-percentage
       namespace: istio-system
     thresholdRange:
       max: 5
     interval: 1m

    上例表示canary的关于404错误/s的metrics不能超过5%

Alter

Alter: 用于发布过程中信息通知.
1.定义AlterProvider(可以是slack, 也可以是dingding)

apiVersion: flagger.app/v1beta1
kind: AlertProvider
metadata:
  name: on-call
  namespace: flagger
spec:
  type: slack
  channel: on-call-alerts
  username: flagger
  # webhook address (ignored if secretRef is specified)
  address: https://hooks.slack.com/services/YOUR/SLACK/WEBHOOK
  # secret containing the webhook address (optional)
  secretRef:
    name: on-call-url
---
apiVersion: v1
kind: Secret
metadata:
  name: on-call-url
  namespace: flagger
data:
  address: <encoded-url>

2.使用Alter

analysis:
    alerts:
      - name: "on-call Slack"
        severity: error
        providerRef:
          name: on-call
          namespace: flagger

• serverity: 通知信息的等级, 类似日志级别. 包含info, warn, error
在整个部署过程中,不同阶段都会使用alter来发送通知信息, 例如发布成功, webhook执行失败等场景。

总结

• Flagger对应用自动化发布流程进行了很好的抽象, 提供了丰富的扩展机制(webhook, alter, metrics等).
这些特性比较吸引人,那是否能能直接就能在集团内使用呢?
答案是不行。Flagger要求应用构建在k8s基础上, 例如服务发现机制, 另外要求部署Ingress/service mesh(这两者都具备调整流量策略的能力). 以HSF为例,它的服务发现机制是根据configserver, 服务是面向接口, 而不是应用。
如果不经过一定改造,估计还是无法使用.

• 另外Flagger也有一些改进的地方(我个人人为):
canary实例在切流过程中的扩缩容是根据HPA(如果配置了)来进行的, HPA扩缩容不及时就会对业务有影响.
改进方案: 可以根据stepWeight的变化动态调整canary的实例数, 这个只针对Canary release.
对于Blue/Green, A/B tesing可以通过webhook提前准备容量.

• Flagger正在规划primary和canary流量比较特性,这个似乎和集团Doom干的是同一件事情。未来可以期待一下.

相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
目录
相关文章
|
Kubernetes 网络协议 前端开发
k8s更新策略-系列文章第一篇:蓝绿发布
k8s更新策略-系列文章第一篇:蓝绿发布
|
域名解析 Kubernetes Java
图文详述Nacos配置中心使用:应用间配置共享、扩展配置文件加载优先级、新老版本差异
图文详述Nacos配置中心使用:应用间配置共享、扩展配置文件加载优先级、新老版本差异
4170 1
图文详述Nacos配置中心使用:应用间配置共享、扩展配置文件加载优先级、新老版本差异
|
14天前
|
运维 监控 安全
自动恢复机制在哪些情况下可能无法正常工作,有哪些替代方案?
自动恢复机制在哪些情况下可能无法正常工作,有哪些替代方案?
|
3月前
|
Kubernetes 监控 测试技术
在K8S中,如何实现上线发布流程(灰度发布)?
在K8S中,如何实现上线发布流程(灰度发布)?
|
4月前
|
负载均衡 算法 测试技术
通用快照方案问题之灰度发布中实现用户请求到新旧版本服务的分流如何解决
通用快照方案问题之灰度发布中实现用户请求到新旧版本服务的分流如何解决
43 0
|
6月前
|
Kubernetes Shell Docker
ChaosBlade设置问题之无法设置加压时间如何解决
ChaosBlade 是一个开源的混沌工程实验工具,旨在通过模拟各种常见的硬件、软件、网络、应用等故障,帮助开发者在测试环境中验证系统的容错和自动恢复能力。以下是关于ChaosBlade的一些常见问题合集:
|
6月前
|
编解码
亚丁号自动阅读第一次更新
亚丁号自动阅读第一次更新
44 1
|
Java 数据库 开发者
自动配置要点解读
自动配置要点解读
|
NoSQL Java 开发者
自动配置原理|学习笔记
快速学习自动配置原理
136 0
|
运维 Kubernetes Cloud Native
Rainbond 5.6 版本发布,增加多种安装方式,优化拓扑图操作体验
Rainbond 5.6 版本,主要致力于提升拓扑图操作效率以及快速安装体验,降低用户使用门槛。
Rainbond 5.6 版本发布,增加多种安装方式,优化拓扑图操作体验