TSE 云原生 API 网关支持基于 Method 、特定位置(Header,Query、Body、Cookie)参数、系统参数(domain,clientIP,httpScheme,clientUa)的灰度发布能力。
通过灰度条件和目标服务进行配置。路由规则的多个条件为逻辑与(AND)关系,即一个路由规则内的条件都满足了,才会转发到对应的后端服务。
后端服务通过 Kong Upstream 来定义,绑定容器集群后,Kong Ingress Controller 从 K8S Service 中同步过来自动生成资源。
参数支持表达式运算:
支持<,<=, >, >=, ==, != 运算符。
支持存在与正则表达式
支持包含和不包含
实现原理
tse-route 插件为 TSE 提供的用于进行参数路由的插件。通过将 tse-route 插件绑定在原始服务上,通过参数条件路由到目标服务(灰度服务)以进行灰度发布。
操作步骤
步骤1:创建Ingress
前提:已在 k8s 创建好正式服务(nginx)和灰度服务(demo1,demo2)。
创建 Ingress 定义转发规则:
apiVersion: networking.k8s.io/v1kind: Ingressmetadata:annotations:konghq.com/strip-path: 'true'name: demonamespace: defaultspec:ingressClassName: kongrules:- http:paths:- backend:service:name: nginxport:number: 80path: /nginxpathType: Prefix- backend:service:name: demo1port:number: 80path: /demo1pathType: Prefix- backend:service:name: demo2port:number: 80path: /demo2pathType: Prefix
步骤2:定义 TSE Route 插件的 KongPlugin 注解
1. 插件配置字段:
配置字段 | 配置说明 | 备注 |
rules-weight | 规则优先级,支持 0-100,数值越大优先级越高。 | / |
rules-upstream-name | 目标服务名称。 | / |
rules-upstream-weight | 目标服务流量百分比,默认 100。 | 所有 upstream 的 weight 加起来等于100 |
rules-condition | 灰度规则的条件说明,支持 header 参数,query 参数,system 参数,cookie 参数,path 和 method。 | / |
description | 插件说明。 | / |
2. 表达式写法
大于>
- value: '1'operator: gtkey: 'version'global_config_id:delimiter:
小于<
- value: '1'operator: ltkey: 'version'global_config_id:delimiter:
等于==
- value: '1'operator: eqkey: 'version'global_config_id:delimiter:
不等于!=
- value: '1'operator: nekey: 'version'global_config_id:delimiter:
大于等于>=
- value: '1'operator: gekey: 'version'global_config_id:delimiter:
小于等于<=
- value: '1'operator: lekey: 'version'global_config_id:delimiter:
存在
- operator: existskey: 'version'global_config_id:delimiter:
正则表达式
- value: '1'operator: regexkey: 'version'global_config_id:delimiter:
场景一:基于 Header 的灰度发布
使用 KongPlugin 注解,定义插件配置,condition 配置 header 参数的转发条件。
例如:请求 Header 为 version=v1 时,转发到目标灰度服务(demo1),其他情况访问正式服务(nginx)。
apiVersion: configuration.konghq.com/v1kind: KongPluginmetadata:name: my-test-routeconfig:description: testrules:- enabled: truecondition:cookie:system:path:body:method:header:- global_config_id:key: versionvalue: '1'delimiter:operator: eqquery:weight: 22upstream:- weight: 100name: demo1.default.80.svcplugin: tse-route
场景二:基于Query的灰度发布
使用 KongPlugin 注解,定义插件配置,condition 配置 query 参数的转发条件。
例如:请求 Query 参数 age <3 0 时,转发到目标灰度服务(demo1),其他情况访问正式服务(nginx)。
apiVersion: configuration.konghq.com/v1kind: KongPluginmetadata:name: my-test-routeconfig:description: testrules:- enabled: truecondition:cookie:system:path:body:method:header:query:- global_config_id:key: agevalue: '30'delimiter:operator: ltweight: 22upstream:- weight: 100name: demo1.default.80.svcplugin: tse-route
场景三:基于权重的灰度发布
使用 KongPlugin 注解,定义插件配置,配置不同后端服务百分比的转发条件。
例如:配置灰度服务 demo1的百分比为 20%,灰度服务 demo2的百分比为 30%,剩余流量(50%)访问正式服务 nginx。
apiVersion: configuration.konghq.com/v1kind: KongPluginmetadata:name: my-test-routeconfig:description: testrules:- enabled: truecondition:cookie:system:path:body:method:header:query:weight: 10upstream:- weight: 20name: demo1.default.80.svc- weight: 30name: demo2.default.80.svc- weight: 50name: nginx.default.80.svcplugin: tse-route
步骤3:将插件绑定在服务上
为正式服务 Nginx 添加注解,将插件绑定到该正式服务上。
kubectl apply -f tseroute.yamlkubectl annotate service nginx konghq.com/plugins=my-test-route
步骤4:访问正式服务
访问正式服务,将根据条件依次匹配,满足匹配条件则按照条件转发到对应的灰度服务。
claire@CLAREZZHANG-MB0 ~ % curl -i 'http://1.15.161.241/hello?uid=/custokjhjhjkkj&whiteList=qatest'HTTP/1.1 200 OKAccept-Ranges: bytesConnection: keep-aliveContent-Length: 615Content-Type: text/html; charset=UTF-8Date: Wed, 01 Mar 2023 13:47:53 GMTEtag: "6398a011-267"Last-Modified: Tue, 13 Dec 2022 15:53:53 GMTServer: nginx/1.23.3Via: kong/2.5.1X-Kong-Proxy-Latency: 7X-Kong-Route-Rule: 100X-Kong-Route-Upstream: nginx.default.80.svcX-Kong-Upstream-Latency: 2