本文主要介绍了如何使用Istio和云效AppStack实现灰度发布。
场景描述
为了实现线上发布的灰度控制,可以通过控制不同版本实例的数量来调整流量比例。例如,将发布过程暂停在新、旧实例比为1:4的状态,此时20%的流量进入新版本,从而进行灰度验证。
然而,通过流量比例实现灰度发布存在两个不足:
无法精准控制灰度范围,如无法满足“指定用户请求新版本”的场景;
无法灵活控制流量比例,如最小灰度比例为20%,这对大部分应用来说不现实。
通过控制不同请求参数进入不同版本服务,并覆盖全链路场景,可以实现全链路的灰度发布。例如,基于阿里云MSE,可支持基于http/https、RocketMq流量的灰度发布,可参考实践:MSE+云效AppStack实现应用服务全链路灰度 。
本篇将介绍基于开源工具Istio实现全链路灰度发布的原理及在云效应用交付平台AppStack上的配置方法,满足基于http、gRPC、WebSocket的流量灰度发布场景。
原理介绍
前置条件
在Istio中,为了实现基于特定header的流量路由,需要完成如下操作:
安装Istio,参考:https://istio.io/latest/zh/docs/setup/getting-started/;
给命名空间添加标签,在部署应用的时候自动注入Envoy sidecar代理
kubectl label namespace default istio-injection=enabled
根据规则配置DestinationRule和VirtualService,例如:
apiVersion: networking.istio.io/v1alpha3 kind: DestinationRule metadata: name: service-a spec: host: service-a subsets: - name: v1 labels: version: v1 - name: v2 labels: version: v2 --- apiVersion: networking.istio.io/v1alpha3 kind: VirtualService metadata: name: service-a spec: hosts: - service-a http: - match: - headers: end-user: exact: jason route: - destination: host: service-a subset: v2 - route: - destination: host: service-a subset: v1
配置完上述规则后,header 中包含 end-user=jason 的请求将全部路由到service-a的v2版本,其余请求将继续访问service-a的v1版本。
操作步骤
在云效AppStack中,我们提倡将发布规范固化在研发流程中,业务研发团队可自助式地完成发布。我们以官方的Bookinfo微服务为例,演示在云效AppStack中的配置过程:
步骤一:应用配置
依次创建 details、ratings、reviews、productpage 4个应用(一个微服务对应一个应用)。
配置应用编排(应用编排定义了应用的部署架构,在k8s中,即 k8s manifest),完整的示例编排已上传至 https://atomgit.com/aliyun_appstack/bookinfo_k8s_manifest。配置编排示例(部署顺序上,我们推荐将非工作负载放在一个阶段,工作负载独立放在一个阶段)。
在4个应用下创建生产环境(prod),reviews应用额外创建灰度环境(gray),并关联k8s资源。
分别进入4个应用的生产环境中完成首次部署,部署后可在环境详情页看到部署后的资源清单。
在reviews应用的研发流程流水线中添加灰度环境部署任务,人工验证后发布生产环境。
步骤二:运行验证
参考官方示例创建网关,确保从集群外部访问应用。
运行研发流程并部署灰度环境后,访问BookInfo服务:
以 jason 用户登录,访问灰度环境。
匿名或以其他用户身份登录,访问生产环境。
步骤三:灰度环境资源清理
在研发流程最后,添加 AppStack清理环境组件,选择‘仅清理资源保留环境元数据。
重新运行研发流程,执行完成 AppStack清理环境步骤后,前往k8s集群查看资源,灰度环境资源已被删除;访问 BookInfo 服务,所有用户都访问生产环境新版本。