去哪儿网Service Mesh落地实践:100%容器化打底,业务友好是接入关键
自2011年引入Dubbo框架至今,去哪儿网的微服务架构已经有了十多年的历史。时至今日,去哪儿网架构已经形成了Dubbo、HTTP协议为主,多语言共存的格局。
根据去哪儿网基础架构部高级技术总监朱仕智分享的数据,现在去哪儿网Dubbo服务接口有18,000多个、HTTP域名超过3500个,内部大约有Java、Golang、Node和Python等5种语言的技术栈,其中以Java和Node为主。此外,去哪儿网在线运行的应用大约3000多个、MQ应用主题超13,000个。
随着业务的不断发展,多语言、多协议给基础架构团队带来了不小的治理问题。
首先,多语言的复杂性主要在于SDK的重复实现,每个治理逻辑需要开发不同的语言版本,此后还要一直对其进行维护,这是一份冗余且负担很重的工作。
在多协议治理上,一方面,去哪儿网内部有Cactus平台对Dubbo进行治理,治理功能相对完善。另一方面,去哪儿网对HTTP的治理主要通过OpenRestry,治理能力相对薄弱,一些必需的治理需求零散分布在多个平台,对开发同学很不友好。
Dubbo和HTTP治理能力不统一导致了重复造轮子情况,增加了业务的开发和维护成本。
此外,业务和中间件强耦合,但业务部门与基础架构部门对升级更新的意愿并不同步。基础架构部门不断升级更新来完善中间件,但业务研发在不影响使用情况下并不希望频繁更新。所以每次发布新版本后,基础架构团队要花很长的时间进行推广,致使整个迭代周期变长。
而Service Mesh将服务治理能力下沉到了sidecar,SDK只需要负责编解码、与sidecar通信,通用逻辑基本不用修改,只要对sidecar修改就可以应用到所有语言和框架,于是在去年,去哪儿网开始组织团队引入Service Mesh来解决自身多语言、多框架的治理难题。
容器化基础
在去哪儿网资深开发工程师李佳龙看来,容器化下比较适合引入Service Mesh。
大概从2014年起,去哪儿网便开始使用Docker、Mesos、Kubernetes(以下简称K8s)等来解决测试环境构建困难的问题,也逐渐尝试基于容器部署ES、MySQL等中间件服务。到了2021年底,去哪儿网全面实现容器化,业务服务基本完成上云。从效果数据来看,容器化虚拟比例从1:17提升到1:30,资源利用率提升76%,宿主运维时间由天变成了分钟级,环境稳定性差、交付慢、可扩展性差和服务器成本高等问题都得到了有效解决。
经过多年积累,去哪儿网已经为引入Service Mesh打下了坚实的基础。引入Service Mesh,本质上也是去哪儿网步入云原生实践新阶段——多方向探索的体现之一。
在去年加入去哪儿网后,李佳龙主要负责Service Mesh的落地工作。团队基于去哪儿网的现状,明确了对新服务治理体系的期望:多语言、多协议统一治理、治理能力增强,同时可以将治理能力下沉,实现基础组件开发周期和业务开发周期解耦。
如何做技术选型
整个实践过程主要分为三个阶段:调研、开发和推广。调研阶段的主要任务是技术选型。去哪儿网团队用了两周左右的时间,调研了其他企业的落地情况。
自2011年引入Dubbo框架至今,去哪儿网的微服务架构已经有了十多年的历史。
如何找到适合自己的产品呢?首先,由于业界已经有成熟的产品,因此去哪儿网没有选择重复造轮子,而是基于业内已有开源软件进行选型。其次,去哪儿网团队还从产品是否成熟、社区活跃度、性能是否满足公司需求,以及开发和维护难度等方面进行了考察。
最终,去哪儿网选择了蚂蚁开源的MOSN作为数据面。MOSN经过了阿里双十一几十万容器生产级别验证,产品自身已经成熟。另外,MOSN社区比较活跃,迭代也较快,更新周期基本维持在了两个月左右。
语言也是重要的考虑因素。由于在C++技术栈方面人才储备有限,团队放弃了流行的Envoy。MOSN的开发语言是Go,在性能、开发、维护难度和灵活性上有优势,虽然不是去哪儿网使用的主要语言,但开发人员入门和上手都比较快。MOSN既可以替代Envoy,也可以集成Envoy在网络层高性能的优势,并将其作为自己的网络插件使用。
控制面上,去哪儿网选择了Istio,并根据自身需要对其进行了二次开发。Istio使用XDS协议与数据面进行交互,是很多企业的首选,去哪儿网选择紧跟社区的脚步。但原生的Istio有个问题,就是和K8s耦合非常严重:主要体现在K8s既是注册中心又是配置中心,以及sidecar注入、启动配置和网络模型等。这导致去哪儿网团队面临着以下问题:
• K8s存储是以应用为维度,但Dubbo是以Service为维度,维度不统一问题怎么解决?
• 去哪儿网内部容器要和KVM共存,如何解决兼容问题?
• 公司内部已有比较成熟的注册中心和配置中心,一刀切必然会引入很多适配和运维成本问题。如果遇到定制化需求,是否会影响K8s集群的稳定?
去哪儿网希望K8s更多的用于服务编排,因此在最初商定方案时,选择解耦K8s,采用内部使用多年的注册中心和配置中心。于一些启动配置,则依赖去哪儿网内部的配置中心(QConfig),同时团队自研了McpServer模块替代K8s来对接Istio。
整体架构
具体实践如何?
接入Mesh后,业务主要关心的就是性能、治理能力和问题排查。因此在做好技术选型后,去哪儿网团队便开始设计实践方案,并花了数月的时间进行研发。
流量管理
目前,业界将流量从SDK拦截到sidecar的方式主要有两种:iptables拦截和流量转发。但由于iptables的可运维性和可观察性较差,配置较多时还会出现性能下降的问题,因此很多公司选择了流量转发的方式,去哪儿网也是如此。
去哪儿网主要使用了两种流量转发方式:一是升级SDK,在SDK中直接将请求转发到本机sidecar;二是域名拦截,例如使用dnsMasa将xx.qunar.com的请求转发到本机sidecar。
李佳龙提醒道,引入Service Mesh后,流量安全值得特别关注,因为之前两个服务的调用变成了四个服务间的调用,大大增加了不稳定性。对此,去哪儿网主要采取了四方面的措施来保证流量的安全:
• SDK自动调用降级。当业务进程与sidecar连接断开(基于健康检查)时,调用降级为直连调用。
• sidecar节点故障剔除。sidecar会对upstream的节点列表进行健康检查,一旦发现连接异常就快速剔除。
• 用户可以在新的统一治理平台Captain上一键切入/切出Mesh模式。
• 柔性可用。为保证可用性,当控制面出现问题时,sidecar会使用缓存数据;当注册中心或配置中心出现异常,MCPServer以及Istio也可以使用缓存数据。
Sidecar管理
对于sidecar的配置、部署、升级、回滚和灰度等,去哪儿网团队将其整合到了运维面上。
以sidecar的升级为例,Sidecar的升级可以分为两个场景:原地升级和服务部署时升级。前者不需要重新部署服务,但需要确保升级对用户透明、流量无损。
Sidecar的注入和升级
对于原地升级,由于sidecar容器和业务容器是同属一个pod的两个独立容器,基础架构团队将MosnAgent作为sidecar容器的1号进程,用于管理sidecar的生命周期,例如启停、健康状态检查和升级等。新版本发布时,会将sidecar镜像推送到镜像仓库,同时将二进制包推送到对象存储。
基础架构团队通过sidecar管理平台,可以对sidecar容器发送升级指令,MosnAgent会拉取对应版本的mosn包,之后启动新版本mosn,并通过fd迁移机制,完成无损升级流程。
而部署时升级,发布平台会请求sidecar管理平台来获取sidecar配置,包括是否注入、sidecar版本、环境变量、配额信息等,然后生成服务的yaml配置。注意在部署时,有可能遇到sidecar容器、业务容器的启用顺序问题。如果sidecar容器未启动成功或者配置未拉取成功、但业务容器已经ready,那么请求就会失败。基础架构团队设置成sidecar先于业务容器启动,并通过配置K8s的postStart钩子函数,来保证正确的启动顺序。
需要注意的是,Istio下发配置时,也可能发生顺序异常问题。去哪儿网团队通过Istio merkeltree来跟踪资源下发进度,通过暴露接口来查询每个资源是否全量下发到side car。
另外,运维面还负责对接内部系统,如内部配置中心、全链路监控系统、报警系统、镜像仓库及对象存储等。
性能优化
在性能优化方面,首先由于业务容器与sidecar容器同属一个pod,基础架构团队选择了使用unix domain socket进行通信,以此规避网络栈、优化性能。
其次,团队对Dubbo协议进行了优化。sidecar接收到请求后的第一步是获取路由信息,用以服务寻址。按照Dubbo原来的设计,路由信息(service/method/group等)存放在body中,但为了避免不必要的body反序列化,团队扩展了内部Dubbo协议,将路由信息放置到了扩展header中。
再者,团队选择按需加载xDS数据方式。Sidecar启动时会请求控制面拉取xds数据,但是原生的Istio会拉取当前集群中所有服务数据,导致sidecar资源占用过多以及推送风暴,大大制约了Service Mesh的集群规模,这也是很多公司落地Service Mesh要解决的问题。去哪儿网的解决方式是配合内部Spring Cloud Qunar框架,在编译器采集订阅关系,并扩展xds协议,来实现按需加载。
除了按需加载配置,基础架构团队也在优化推送性能,统一服务注册模型等。
治理能力
针对之前治理功能分散、能力不统一的问题,基础架构团队将Dubbo和HTTP统一到了新的Captain平台。
“在设计时,Captain要尽量做到服务治理与协议无关。”李佳龙说道。比如,之前Dubbo服务需要在项目中配置参数支持调权预热、HTTP在发布平台配置支持引流预热或者自定义接口预热,引入Service Mesh后就可以很方便地支持Dubbo/HTTP调权、引流两种预热模式。
此外,Captain增强了很多服务治理能力,例如多维度的限流策略,包括基于应用粒度限流和基于优先级限流。业务团队既可以根据应用的不同来设置不同的限流阈值,也可以根据不同的流量来源设置不同的优先级,优先处理有价值的请求。
如下图所示,当流量达到设定的阈值时会触发限流,这时流量会进入到多个优先级队列,可以按照优先级处理。
此外很多情况下,业务会将超时时间、限流阈值设置得比较大或比较小,这未能起到应尽的作用,基础架构团队根据监控数据和合理算法,会智能推荐超时、限流等参数。
如何进行推广
目前,去哪儿网已经在基础平台、机票等部门开始推广和试行Service Mesh。
“推广是最为关键、也是比较容易出现阻塞的地方。因为对于用户来说,让系统最稳定的做法就是不轻易做变动。”李佳龙说道。
那么,如何让业务更容易接受Service Mesh呢?去哪儿网团队先是在内部做了关于Service Mesh基本认识的分享,让业务了解接入Mesh后都能得到哪些收益。
然后对于新服务治理平台,基础架构团队也注意保留了很多业务的使用习惯。比如在实际使用中,超时时间等治理参数与路由的相关度较低,业务更习惯作为服务提供方配置某个接口的超时时间,或者作为服务调用方配置要调用服务的超时时间。但在xDS协议中,超时时间等治理参数配置在服务提供方,并且与路由绑定。因此,基础架构团队做了部分扩展,业务可以从服务提供方、调用方两个角度来进行配置,并以接口为维度,这些配置包括超时、重试、备份请求、负载均衡策略等。
便捷性对业务来说也是非常重要的,业务希望切到Mesh后能够方便地查询问题,日志、trace、监控报警等内部系统的打通也是推广的前提。
基础架构团队现在提供了两种Mesh接入方式:第一种是接入新的开发框架Spring Cloud Qunar,业务需要做部分改动;第二种是无侵入地一键接入,业务不需要修改代码,这也是接受度较高的一种方式。
另外,去哪儿网提供了按照接口级别的接入方式,业务可以按照百分比来切入Mesh,而不是一刀切地接入。基础架构团队的策略是让业务先从一个小的接口、小的流量来接入,业务接受了之后再扩大接入范围。
在李佳龙看来,便捷易用性问题一定程度上确实阻碍了Service Mesh的落地。
一方面,从业务角度看,使用者更加在意Mesh接入后是不是好用、操作是不是简单、切换起来是不是安全和方便、需求是不是能够满足、能不能保留之前的研发习惯等等。另一方面,从开发角度看,企业开发Service Mesh时通常有很多工作,比如进行二次开发并与内部系统打通,还有诸如xDS按需下发,sidecar管理等目前没有统一标准的工作,这些都需要维护成本。公司基础设施之间有差异,这些都需要决策者考虑清楚。
结束语
Service Mesh不是一个很新的概念,它的本质就是解耦,具体实现起来就是语言SDK负责编码以及与sidecar的通信,这部分比较固定,不包含治理功能。虽然还是多个实现,但是复杂度降低了一个量级,从而将更多的功能实现,抽离到独立的sidecar进程,只需要实现一次。“所以本质上,解决多语言多协议的复杂问题,是分离了变与不变,这也是去哪儿网进行软件架构时的常用方式。”李佳龙说道。
那么对于企业来说,是不是要容器化后才能够接入Service Mesh呢?李佳龙表示这不一定。
“只能说,Service Mesh天然比较适合容器化的场景,比如Istio方案默认使用者已经具备K8s的基础设施了,但是我们仍然可以有多种方式支持虚机接入服务网格,只要解决掉sidecar注入、升级,流量拦截,服务注册发现等。而且我们设计之初去除了K8s的耦合,接入虚机也变得更方便。按照去哪儿的云原生的发展来看,容器化作为云原生架构的底座,在容器之上能更好的支持Service Mesh、Serverless等。”
就中小企业而言,李佳龙表示,中小企业首先考虑的更多是业务。业务越来越多、越来越复杂后,才可能会出现多语言、多框架的问题。只有确实出现这个问题时,才应该开始考虑是否引入Service Mesh。此外还需要考虑自身的基础设施、团队技术储备等是否支持落地。Service Mesh是利用低复杂的技术去解决高复杂度的问题,如果本身复杂度不高,引入Service Mesh这样的技术只会增加复杂度,得不偿失。
还有一个值得关注的方面就是性价比。引入Service Mesh的新增成本包括sidecar所占有的资源,比如每个sidecar占用的CPU、内存、磁盘以及其他如trace存储、日志存储等存储资源。另外,像请求耗时增加、系统开发维护等会产生相应成本,因此去哪儿网目前对于各类日志是按需开启,只打印耗时高的trace信息。
”不过目前看,Service Mesh确实带来了很多好处。”李佳龙说道,“首先便是统一了多语言、多框架的治理能力,提供丰富的治理功能。另外对业务开发透明,减少了业务的使用成本。与业务解耦后,我们的推广周期也大大缩短。”
“Service Mesh应该会是未来的一个发展趋势。”李佳龙表示,“之后去哪儿网会在可观察性、性能优化、多语言支持上持续发力。”
嘉宾介绍
李佳龙,2021年加入去哪儿网基础架构部,担任资深开发工程师,近五年专注于云原生、基础架构等领域,负责去哪儿内部Service Mesh和新服务治理平台Captain的研发落地等工作。