简介:本文分享了阿里云内部所沉淀的全链路流量打标与路由的能力,做出服务网格技术新体验的同时,很好地兑现了服务网格的新价值。

作者:至简

软件是以持续迭代的方式去不断演进的。某种程度上,我们并不担心软件不完善,但担心软件的迭代速度太慢而影响了完善的速度。在分布式软件领域,如何快速、安全地验证新的软件版本一直是大家所关心并探索的。服务网格(Service Mesh)的出现将这个领域的探索推向了新的高度。“泳道”这一概念在分布式软件领域并非新词,只不过,这次我们是以服务网格为基础技术去构建,充分发挥云原生技术天然具备灵活治理流量的优势。

本文分享了阿里云内部所沉淀的全链路流量打标与路由的能力,做出服务网格技术新体验的同时,很好地兑现了服务网格的新价值。

概念与场景

图 1 以 Istio 官方所提供的 Bookinfo 示例程序为例示例说明了使用场景中的关键概念。其中紫色的圆边方框代表了 Envoy。图中所有泳道的性质是一样的,不同的命名只是为了区分细分场景或用户。

  • 基线(baseline):指业务所有服务都部署到了这一环境中。基线可以来自真实的生产环境,也可以专为开发工作而构建的与生产环境完全独立的环境。
  • 流量泳道(traffic lane):代表了一个与基线环境相隔离的软环境,通过给机器(即 Kubernetes 中的 Pod)打标签的方法,将机器加入到该泳道中。显然,加入泳道的机器在网络层面与基线中的机器是互通的。
  • 流量回退(traffic fallback):泳道中所部署的服务数量并非要求与基线环境完全一致,当泳道中并不存在调用链中所依赖的其他服务时,流量需要回退至基线环境,进一步在必要的时候返流泳道。比如,图 1 中 dev1 泳道中并不存在 productpage 服务所依赖的 reviews 服务,因此需要让流量回退到基线中的 reviews 服务(图中深蓝色线所示),紧接着基线中的 reviews 服务需要将流量打回 dev1 泳道中的 ratings 服务。
  • 流量标识透传(traffic label passthrough):所有服务边上的 Sidecar 都需要有能力将调入请求中所携带的流量标签自动放到由这一请求所分叉出的每一个调出请求中去,以便实现全链路流量标识透传和按流量标识路由,否则泳道与基线间的流量无法来回穿梭。
  • 入口服务(entrance service):指流量进入泳道时所触达的第一个服务。图 1 中代表服务的图形在左边框边上打上三角形标识的就代表它是一个入口服务。

图1

泳道技术可以运用于如下场景:

  • 单个服务的日常开发或多个服务间的日常开发联调。开发者建立泳道,将增加了新功能的服务部署到泳道中,基于流量的特征通过定义规则将测试流量引入泳道中进行验证。由于泳道只需部署被测试服务的新版本,省去了搭建全链路测试环境的麻烦。在这一场景中,需要注意测试流量所存在的数据落盘问题,处理好开发与联调过程中所留下的脏数据。
  • 全链路灰度。对于涉及重大功能上线中的多个服务,可以通过泳道以全链路灰度的方式做更为全面的功能验证。全链路功能验收通过后,再将服务的新版本发布至基线。
  • 关键业务重保。类似零售场景的业务(比如 POS 机收银),我们不希望因为软件的故障而引发巨大的舆情,这时可以通过泳道对业务流量进行隔离实现重保。

技术实现

流量打标方案与实现

在运用泳道技术时,根据流量打标的位置不同而存在三种不同的方案。值得指出,虽然方案有所不同,但就服务网格而言的技术实现是完全一致的,将方案罗列出来是为了帮助读者更好地理解。

图 2 示例说明了方案一。在这个方案中,流量进入服务网格的 Ingress 网关之前还有一级网关,我们姑且称之为 API 网关(比如,Nginx)。通常 API 网关可以根据流量的特征,在转发收到的请求前先加上额外的头,从而完成对流量的打标动作。图中对于特定的流量将增加名为 x-asm-traffic-lane: dev1 的 HTTP 头,代表需要将流量打到 dev1 泳道中。在这个方案,服务网格中的 Envoy 无需有任何流量打标动作。

图 2

图 3 示例说明了方案二。本方案中,客户端的流量直接打到服务网格的 Ingress 网关上。由 Ingress 网关根据流量的特征通过 Istio 原生的 VirtualService 匹配规则识别出后,在转发请求前加上名为 x-asm-traffic-lane 的 HTTP 头,随后将流量路由到相应的泳道。

图 3

图 4 示例说明了方案三。本质上,这一方案与方案二是完全一样的,同样通过 Istio 原生的 VirtualService 匹配规则识别出相应的流量后加上名为 x-asm-traffic-lane 的 HTTP 头。唯一的不同在于,方案二中的 Envoy 的角色是 Ingress,而方案三中 Envoy 的角色是 Sidecar。

图 4

流量一旦完成打标后,由服务网格中的每一个 Envoy 基于流量标和控制面下发的配置做全链路的标透传和按标路由。

流量标识透传

图 5 示例说明了服务网格中一个服务与边上的 Envoy (Sidecar)间的流量细节。

图 5

从 Envoy 的视角来看,包含对流入和流出两种流量的转发。I1 是流入的流量,收到后将转发给本地的 Svc A;O1 是流出的流量(因为处理 l1 的需要而去调用别的服务所引发),收到后将转发给外部的被调用的服务。流入与流出只与请求(request)相关,与请求对应的响应(response)没有关系。显然,一个流入的请求可能导致有多个流出的请求发生(即“分叉”),这完全取决于 Svc A 的具体业务逻辑。

泳道技术所需解决的核心点在于,当流入的流量打上了相应的标签后,如何让由其所分叉出的每一个流出的流量都带上同样的标签,我们采用的方案是结合链路追踪技术(比如,OpenTelemetry)去解决。链路追踪技术是通过 traceId 去唯一标识一条调用链树,为根请求分配并带上全网唯一的 traceId 后,之后由其所分叉出的所有新调用都得带上值完全一样的 HTTP 头,换句话说服务开发者需要在编程的过程中确保这一头被传播到后续的服务调用中(比如,调用 OpenTelemetry 的 SDK 完成头传播)。换句话说,运用泳道技术的前提是需要每个服务都采用了链路追踪技术,作为微服务构架的最佳实践之一这一先决条件很容易满足。回到图 5,Svc A 收到 I2 请求并对之处理时需要发起 O1 调用,此时需要确保 I2 中的 traceId 头传播到 O1 请求中,这是 Svc A 的开发者需要特别注意的一个细节。

一旦服务网格中所有服务的请求都带上了 traceId,那么通过 Envoy 实现全链路的流量标透传就是非常简单的事了。大体分这几大步骤:

  • Envoy 内部构建一张映射表,记录 traceId 与流量标的映射。比如,图 5 所示的流量标是放在 x-asm-traffic-lane 这一 HTTP 头中的。x-asm-traffic-lane: dev1 代表的流量标是 dev1,x-asm-traffic-lane: canary 代表的流量标是 canary。
  • 当请求 I1 进到 Envoy 时,Envoy 基于请求中所带的 traceId 和流量标,在映射表中增加一条映射记录。
  • Envoy 对于收到的每一个 O1 请求,基于请求中的 traceId 从映射表中找到对应的流量标并将之增加到 O2 请求中再转发出去。

通过服务网格基于 traceId 打标的技术方案的好处在于,将流量打标的动作和流量标传递做到完全与服务解耦,将这一能力下沉到本来擅长流量治理的服务网格中,让流量调度的灵动性得以进一步解锁。

流量标识与 traceld 的定义

我们在 Istio 已有 CR 的基础上,新增了 TrafficLabel 这个全新的 CRD。选择新增而非直接对 VirtualService 做扩展的原因是,VirtualService 的设计之初是应用维度的,当一个业务复杂到全链路有很多应用需要放到泳道中时,就得对每个应用的 VirtualService 进行变更,背后所导致的时效性和可操作性会是一个问题。扩展 VirtualService 去实现的另一种思路是,让 VirtualService 具备配置全局规则的能力,而这就要用到规则的合并机制,这一点从实操层面也有问题。Istio 社区对于多个 VirtualService 进行合并的需求有不少讨论,目前只在网关上支持合并,对于 Sidecar 则不提供这一能力,原因在于担心合并的顺序不同而导致故障。

图 6 示例说明了如何使用 TrafficLabel 这一 CR 在 istio-system 根命名空间定义全局有效的流量打标方法。其中定义了名为 x-asm-traffic-lane 的标签,作为 HTTP 请求的头用于存放流量标识(比如,dev1、dev2、canary 等),以及 traceId 基于 x-request-id 获得。用户可以根据自己所选型的链路追踪系统的具体实现加以设置。图中设置为从 x-request-id 头中获得,是因为 Envoy 实现了通过 x-request-id 做全网链路唯一性标识的功能。采用 x-request-id 作为映射表键意味着,我们可以直接用 Istio 开源社区所提供的 Bookinfo 示例程序去演示泳道的效果,因为 Bookinfo 中的所有服务都做了 x-request-id 头从调入请求到调出请求的传播。

图6

按流量标路由

为了支持按流量标路由,需要对 Istio 的 VirtualService 做扩展,让 destination 字段支持用 $x-asm-traffic-lane 这样的变量指定流量的目的地,如下图 7 所示。换句话说,包含 x-asm-traffic-lane: dev2 头的流量会打到 dev2 这个泳道中,背后其实是使用 DestinationRule 定义的名为 dev2 的 subset,如图 8 所示。请注意,图 7 中 VirtualService 中的 $x-asm-traffic-lane 这一名称要与图 6 中 TrafficLabel 内所定义的名保持一致。

图7

图8

从图 8 中 DestinationRule 的定义不难看出,除了 baseline 外只定义了 dev2 这个泳道,图 7 则是对应情形下的 VirtualService 定义。两者对应的使用场景正是图 1 中的基线和 dev2 泳道。

产品实现

在云原生的大技术背景之下,易用性被放到了聚光灯之下,我们深刻理解背后意味着什么。为此,在设计产品的交互时,努力清空自己所知、站在用户所面临的场景下去思考和优化,在功能性和易用性之间努力做好平衡。

在用户使用泳道前,我们认为他已构建了一个包含所有服务在内的基线环境。在 K8s 中,基线环境通常被部署于特定的命名空间中以便更好地运维和管理其中的服务。用户创建泳道时,只需提供泳道名称。本节接下来的内容以创建名为 dev2 的泳道展开。

泳道创建好后,需要将服务发布到泳道之中。由于所发布的服务已存于基线环境中并创建了 K8s Service 资源,所以泳道中发布服务其实是创建对应服务下的一个 Deployment,直观的理解就是创建已有服务的另一个软件版本。不难想到,这一发布动作包含确认基线版本,实例数和容器镜像地址。

当服务发布到泳道中后,需要通过泳道的服务列表确保所有服务都正常启动。此时泳道中并没有流量进入,需要通过配置引流规则才能将基线中的流量引入泳道中。

引流规则可以基于 HTTP 头、URI、Cookie 的特征去配置,方便我们精确地选择被测流量进入泳道。下图的规则是指将 HTTP 头 end-user 的值为 dev2 的流量引导致 dev2 泳道中。配置规则的同时,需要正确指定入口服务。

引流规则应用后,即可在网页上以 dev2 用户名登录,从而看到 dev2 泳道中服务所呈现的效果。下面两图分别示例了全基线和 dev2 泳道所看到的页面效果。由于 dev2 泳道中并没有部署 productpage 和 details 两个服务,所以这两个服务会回退为使用基线中的,而最终呈现的效果就是两图中 The Comedy of Errors 和 Book Details 两块的内容是完全一致的。

当服务发布到泳道中上线后,可以在泳道的服务列表中方便地查看各服务与基线版本的流量比对情况。帮助开发者更好地了解泳道中服务的运行情况。

此外,通过服务拓扑图也可以清晰地看到,dev2 泳道中服务的调用情况(图中的 lane-dev2)。

总结与展望

我们所探索的基于服务网格的泳道技术,让开发者能秒级创建隔离环境用于开发测试或业务重保,通过精确的引流规则将“爆炸半径”控制到最小。很好地兑现了云原生服务网格技术的新体验和新价值。

接下来,我们将进一步以场景化的方式打通泳道和版本灰度的功能,让用户能基于直觉使用好这些功能。功能层面,我们将进一步完善泳道中支持的协议,比如 RocketMQ、Dubbo 3.0 等,通过丰富泳道技术的应用场景去最大程度地发挥其价值。

最后,我们将持续以 Service Mesh as Infra 的理念去构建微服务架构的现代化服务治理平台,和业界伙伴一同加速这一新技术的发展和推广。

作者介绍:李云(花名:至简),阿里云服务网格混合云产品技术负责人。2018 年开始在阿里集团带领团队从事服务网格技术的发展与建设工作,在 QCon 做过多次云原生与服务网格的技术分享。

原文链接

本文为阿里云原创内容,未经允许不得转载。

兑现 Service Mesh 的新价值:精确控制“爆炸半径”的更多相关文章

  1. Service Mesh 是新瓶装旧酒吗?

    点击下载<不一样的 双11 技术:阿里巴巴经济体云原生实践> 本文节选自<不一样的 双11 技术:阿里巴巴经济体云原生实践>一书,点击上方图片即可下载! 作者 | 李云(花名: ...

  2. 阿里巴巴 Service Mesh 落地的架构与挑战

    点击下载<不一样的 双11 技术:阿里巴巴经济体云原生实践> 本文节选自<不一样的 双11 技术:阿里巴巴经济体云原生实践>一书,点击上方图片即可下载! 作者 | 方克明(溪翁 ...

  3. 微服务应用新趋势:Service Mesh、AIOps和中台化

    微服务技术由于天生支持快速迭代.弹性扩展的特点,使企业能够在不确定性下提升发展速度及抗风险能力,受到了越来越多的关注.当前,云服务商纷纷试水微服务产品,最为典型的,当属推出轻舟微服务平台.剑指整个微服 ...

  4. 新锤子驾到,通通闪开—Service Mesh

    微服务方兴未艾如火如荼之际,除 Spring cloud 等经典框架之外,新一代的微服务开发技术正在悄然兴起,那就是Service Mesh(服务网格).2018 年是Service Mesh 元年, ...

  5. 蚂蚁金服 Service Mesh 实践探索

    SOFAMesh是蚂蚁金服在ServiceMesh方向上的探索,下面是它高级技术专家敖小剑在QCon上海2018上的演讲. Service Mesh 是一个 基础设施层,用于处理服务间通讯.现代云原生 ...

  6. Qcon2017实录|Service Mesh:下一代微服务

    https://zhuanlan.zhihu.com/p/30292372 数人云11月Meetup报名开启,看中西方大神如何论道云原生与微服务!本文作者敖小剑老师将在本次Meetup上继续分享Ser ...

  7. Service Mesh服务网格:是什么和为什么

    Service Mesh服务网格:是什么和为什么 - 好雨云帮 CSDN 博客 - CSDN博客 https://blog.csdn.net/zyqduron/article/details/8043 ...

  8. 干货 | 蚂蚁金服是如何实现经典服务化架构往 Service Mesh 方向的演进的?

    干货 | 蚂蚁金服是如何实现经典服务化架构往 Service Mesh 方向的演进的? https://www.sohu.com/a/235575064_99940985 干货 | 蚂蚁金服是如何实现 ...

  9. 转载:Service Mesh:重塑微服务市场--敖小剑

    转载地址:https://skyao.io/talk/201805-service-mesh-rebuild-microservice-market/ 重点: 不要太过关注  Service Mesh ...

  10. Service Mesh服务网格新生代--Istio(转)

    万字解读:Service Mesh服务网格新生代--Istio  官网地址:https://preliminary.istio.io/zh/docs/concepts/security/ Servic ...

随机推荐

  1. day01-项目介绍+SSM环境搭建

    项目介绍+SSM环境搭建 1.项目功能/界面 SSM整合项目界面:使用Vue完成 技术栈:前后端分离开发,前端框架Vue3+后端框架SSM 前端框架-Vue3 后端框架-SSM(SpringMVC+S ...

  2. 【Leetcode】768. 最多能完成排序的块 II

    题目(链接) arr是一个可能包含重复元素的整数数组,我们将这个数组分割成几个"块",并将这些块分别进行排序.之后再连接起来,使得连接的结果和按升序排序后的原数组相同. 我们最多能 ...

  3. AXI4自定义FPGA外设理论基础

    AXI4自定义FPGA外设理论基础 1.理论目的 在前面的基于AXI4的自定义GPIO的实验中,大概地了解了AXI4的工作模式,即以寄存器为缓冲,实现操作和传输.那个实验只是将自定义的FPGA连接到现 ...

  4. Python爬虫爬取ECVA论文标题作者摘要关键字等信息并存储到mysql数据库

    网站截图: 源代码: 1 import re 2 import requests 3 import pymysql 4 from bs4 import BeautifulSoup 5 import l ...

  5. 现代DevOps如何改变软件开发格局

    在软件开发的早期,该过程通常是开发人员编写代码,再将其交给质量保证(QA)进行测试.这种瀑布开发方法可能会导致质量问题和延迟,因为问题是在周期后期发现的. 一.了解DevOps和测试左移 DevOps ...

  6. #最大流#WOJ 124 Football Coach

    题目 有\(n\)支球队,互相之间已经进行了一些比赛.现在还有\(m\)场比赛未进行, 每场比赛胜者得2分,平局各得1分,负者不得分. 问是否存在一种方法使得球队\(n\)的得分比其他\(n-1\)支 ...

  7. #单调队列#JZOJ 1753 锻炼身体

    题目 一个\(n*m\)的矩阵,有些格子不能经过,有\(k\)个时段, 要么停留某个格子,要么沿时段规定的方向移动,问最多能够移动多少次 \(n,m,k\leq 200\) 分析 题目已经提示了\(O ...

  8. el-table边框颜色修改—骨灰级

    一.前言说明 1. 网上很多都是通过上下左右边框方式,如: .el-table { border-bottom: 1px solid black; border-right: 1px solid bl ...

  9. Docker学习路线12:开发者体验

    到目前为止,我们只讨论了使用Docker来部署应用程序.然而,Docker也是一个极好的用于开发应用程序的工具.可以采用一些不同的建议来改善开发体验. 在应用程序中使用docker-compose以方 ...

  10. Seaborn分布数据可视化---统计分布图

    统计分布图 barplot() sns.barplot( x=None, y=None, hue=None, data=None, order=None, hue_order=None, estima ...