前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Knative通过header访问指定版本

Knative通过header访问指定版本

作者头像
李鹤
发布2023-03-06 11:19:17
4380
发布2023-03-06 11:19:17
举报
文章被收录于专栏:k-cloud-labs

背景

knative 0.14.0 实际修改可能与贴出来的代码不符,贴出来的代码只是为了方便快速实现功能

最近在搭建公司级的serverless平台,需要用到域名来访问内部服务,采取的是通过PATH来区分不同的服务,域名采用同一个。上一篇已经解决了通过Path访问不同服务的问题,但是在灰度过程中可能会想测试下新版本时候正常,如何将流量打到指定版本上呢?原生的knative是通过url的不同实现的,可以配置一个根据版本生成url的模板,设置后不同版本的服务url不同。但是我们的场景是所有服务url相同,于是我们约定通过在设置特殊的header的来实现此功能

方案

原生通过url来区分不同版本,实现方式是通过在生成vs时,设置其Match的条件Authroty为对应的url prefix即可。显然无法满足我们当前统一使用一个url的场景。但是我们可以参考其实现方式,换一个维度,靠header实现即可,但是又不能影响正常访问,即不添加header的时候,流量按照设置的比例打到不同的revision上,添加了header后,需要将流量打到指定版本,所以不能简单的在Match中添加Header,需要分别设置正常访问的情况和访问指定版本的情况,且访问指定版本的配置应该顺序靠前

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73

// MakeIngressSpec creates a new IngressSpec func MakeIngressSpec( ctx context.Context, r *servingv1.Route, tls []v1alpha1.IngressTLS, targets map[string]traffic.RevisionTargets, visibility map[string]netv1alpha1.IngressVisibility, acmeChallenges ...v1alpha1.HTTP01Challenge, ) (v1alpha1.IngressSpec, error) { ... // add custom external domains customHostStr := r.Annotations["serverless.kakuchuxing.com/domains"] // 倒序,否则不生效,因为访问指定版本时name不为空,不区分版本时name默认为空 sort.Sort(sort.Reverse(sort.StringSlice(names))) if len(customHostStr) > 0 { customHosts := strings.Split(customHostStr, ";") for _, name := range names { if name != "default" { visibility := netv1alpha1.IngressVisibilityExternalIP rule := *makeIngressRule(customHosts, r.Namespace, visibility, name, targets[name]) // If this is a public rule, we need to configure ACME challenge paths. rule.HTTP.Paths = append( makeACMEIngressPaths(challengeHosts, customHosts), rule.HTTP.Paths...) rules = append(rules, rule) } } } ... } func makeIngressRule(domains []string, ns string, visibility netv1alpha1.IngressVisibility, name string, targets traffic.RevisionTargets) *v1alpha1.IngressRule { ... return &v1alpha1.IngressRule{ Hosts: domains, Visibility: visibility, HTTP: &v1alpha1.HTTPIngressRuleValue{ Paths: []v1alpha1.HTTPIngressPath{ { Splits: splits, // TODO(lichuqiang): #2201, plumbing to config timeout and retries. // 把tag name保存下来,传递给vs,用来区分是否需要设置header AppendHeaders: map[string]string{ "RevisionName": name, }, }, }, }, } } func makeVirtualServiceRoute(hosts sets.String, usn string, http *v1alpha1.HTTPIngressPath, gateways map[v1alpha1.IngressVisibility]sets.String, visibility v1alpha1.IngressVisibility) *istiov1alpha3.HTTPRoute { ... // add revision tag header to custom domain // 获取传递过来的tag,设置match header if tag := http.AppendHeaders["RevisionName"]; tag != "" { for i := 0; i < len(matches); i++ { if matches[i].Headers == nil { matches[i].Headers = make(map[string]*istiov1alpha3.StringMatch) } matches[i].Headers["RevisionName"] = &istiov1alpha3.StringMatch{ MatchType: &istiov1alpha3.StringMatch_Exact{ Exact: http.Splits[0].ServiceName, }, } } } ... }

总结

至此,已经实现了通过统一域名访问集群内服务,且根据Path转发请求,并且可以通过在访问时添加指定的header来把流量打到指定版本上,这在灰度或者测试时是一个非常实用的功能。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020-08-19,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 背景
  • 方案
  • 总结
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档