NVIDIA 初创加速计划,免费加速您的创业启动 了解详情
写点什么

生产环境的 Service Mesh 流量劫持怎么搞?

  • 2021-04-13
  • 本文字数:2908 字

    阅读完需:约 10 分钟

生产环境的 Service Mesh 流量劫持怎么搞?

背景

 

ServiceMesh 社区使用 iptables 实现流量劫持,这个机制在百度生产环境使用会遇到一些问题,因此,我们探索了其他的流量劫持方式,如基于服务发现的流量劫持机制、基于 SDK 的流量劫持机制、基于固定 Virutal IP 的流量劫持机制等。

 

本文主要介绍基于服务发现的流量劫持机制,这个机制是在服务发现步骤 "伪造" 地址来完成流量劫持。

基于 iptables 流量劫持机制

 

我们先简单的看看社区的流量劫持方案,首先看下 Inbound 流量劫持,如图 1 所示:

 

  1. 所有入站流量都会经过 iptables;

  2. iptables 忽略非 TCP 以及访问 istio 管理端口的流量,将其他入站流量转发给 Envoy;

  3. Envoy 处理完后再将流量转发给 App;

  4. 上述流量又一次经过 iptables 规则匹配,iptables 将具备以下特点的流量当做 Envoy 发出的流量直接转发给目的地:

    Envoy 发出的;

    输出设备时 lo;

    目的地时 127.0.0.1。

 

至此 iptables 完成了 Envoy 对 Inbound 流量的劫持和转发。

 


图 1 iptables 流量劫持

 

接下来咱们再来看看 Outbound 流量劫持,如图 2 所示:

 

  1. App 给 Server 发送流量;

  2. iptables 将满足以下条件的流量转发给 Envoy:

    不是 Envoy 发出的;

    输出设备不是 lo;

    目的地址不是 localhost。

  3. Envoy 处理完后,选定 Server 的一个 endpoint 转发流量;

  4. iptables 将满足以下条件的流量直接发给目的地,也就是 Server:

    Envoy 发出的;

    输出设备不是 lo。



图 2 iptables 劫持 outbound 流量

 

至此,iptables 完成了 inbound 和 outbound 的流量劫持,该机制的好处在于可以透明的劫持业务流量,但是在百度生产环境使用时存在一些问题:

 

  • 可管控性差,内网各容器网络没有隔离,iptables 是全局工具,可被其它用户修改,导致流量劫持异常;它作为单机流量管理工具,没有成熟的平台/产品进行统一的管理。

  • 大并发场景下存在一定的转发性能问题;规则数过多时变更时延大。

 

因此我们探索了其他的劫持机制,接下来我来介绍下百度生产环境正在使用的流量劫持机制——基于服务发现的流量劫持机制。

基于服务发现的流量劫持机制

 

先来看下该机制的设计思路,服务流量根据方向的不同,可以分为 Outbound 和 Inbound。如图 3 所示,有两个服务:Client 和 Server,Client 的 Envoy 记为 EnvoyC,Server 的 Envoy 记为 EnvoyS(本质是一样的,只不过为了表述方便取了不同的名字)。EnvoyC 要劫持的流量是来自在相同机器上的 Client 发出的 Outbound 流量,而 EnvoyS 要劫持的流量大部分是来自不同机器上的服务发给 Server 的流量。

 

这两种流量的劫持机制可以分开设计,考虑到 ServiceMesh 常用的策略都在 EnvoyC 上生效,因此我们先设计了 EnvoyC 劫持 Outbound 流量的方案。

 


图 3 ServiceMesh 流量劫持

Outbound 流量劫持

 

一个完整的请求大概要经历域名解析(或者是服务发现)、建立连接、发送请求这几个步骤,现在 iptables 用不了,其他依赖 Kernel 的劫持方案暂时也用不了,我们将目光转向第一步——服务发现。百度生产环境的服务基本都依赖 Naming 系统来解析服务真实的 ip 列表,我们只需要让 Naming 系统返回 Envoy 的 ip 地址,就能将服务的 Outbound 流量劫持到 Envoy。

 

如图 4 所示,Naming Agent 是单机上负责服务发现的 Agent。Client 在发送请求前,会先去 Naming Agent 问:我想给 Server 发个请求,请给我他的地址。这时候 Naming Agent 就会把 Envoy 的地址当成 Server 的地址告诉 Client。接下来 Client 就会乖乖的把请求发给 Envoy,Envoy 再根据一系列的策略把请求转发给 Server。

 


图 4 Outbound 流量劫持

 

这种劫持机制的好处在于改造事项集中在 Naming 系统,使用该 Naming 系统的服务都能通过该方案透明的完成 Outbound 流量劫持。

 

另外,基于 Naming 系统的流量劫持机制可以动态回传流量治理参数给业务服务,如超时、重试等。这种能力的其中一个用途是可以避免 Mesh 劫持后的多级重试导致服务雪崩,具体做法如图 5 所示,当业务流量被 Envoy 劫持后,Envoy 会通过 Naming Agent 将业务服务的重试次数置为 0。

 


图 5 动态回传流量治理配置

 

此外,为了降低数据面(Envoy)故障时对业务服务的影响,我们还增加了数据面自动容灾、主动关闭 Mesh 等能力:

 

  • 数据面故障自动容灾能力:当 Envoy 异常时,Naming Agent 会自动返回 Server 实际的实例列表,此时,Client 会自动回退为非 Mesh 劫持模式。

  • 主动关闭 Mesh 劫持:用户也可以主动关闭 Mesh 劫持,此时,Client 也会自动回退为非 Mesh 劫持模式。

 

至此,Envoy 能够劫持 Outbound 流量,但是,只有 Outbound 流量劫持能力的 Envoy 是不完整的,对于入口限流等功能,还需要具备 Inbound 流量劫持的能力。

Inbound 流量劫持

 

Inbound 流量主要来自其他机器,我们无法再依赖单机的 Naming Agent 伪造地址,得另寻出路。还是基于 Naming 系统的思路,EnvoyS 和 Server 是同机部署的,他们对外提供的地址,唯一的区别在于端口,因此,只要我们能更换 EnvoyC 访问 Server 时的端口,就能将 Inbound 流量劫持到 EnvoyS。

 

如图 4 所示,EgressPort 接收 Outbound 流量,IngressPort 接收 Inbound 流量。

 

  1. 控制面(Istio)将 EnvoyS 的 IngressPort 作为 Server 的端口下发给 EnvoyC;

  2. EnvoyC 将访问 Server 的流量转发到 IngressPort,被 EnvoyS 收到。

  3. EnvoyS 再将流量转发到 Server 服务端口 NamedPort。

 


至此,Envoy 具备了部分 Inbound 流量劫持能力,为什么说是部分呢,因为这种机制无法劫持入口服务的流量。入口服务的上游(Client)是外部服务,它的配置不受 Istio 控制,也就无法采用该机制完成流量劫持,后续需进一步完善该能力。

Inbound 流量劫持中的坑

 

除了上面提到的问题,Inbound 流量劫持还存在一些坑。我们发现当 EnvoyS 劫持了 Inbound 流量后,L3/L4 层通信协议的部分健康检查机制失效。

 

L3/L4 层通信协议的主动健康检查部分功能失效

 

原因:L3/L4 层通信协议的主动健康检查默认是检查端口存活,当流量被劫持到 EnvoyS 后,该功能实际检查的是 EnvoyS 的 IngressPort 端口存活,也就无法反馈 Server NamedPort 端口存活情况。

 

我们目前采用的解决方案是采用两段式主动健康检查机制,两段分别是:

 

  1. Envoy 间健康检查:EnvoyC 对 EnvoyS 的健康检查,该健康检查能够反馈 EnvoyS 和 Server 的状态。

  2. Envoy 和本地 Service 间健康检查:EnvoyS 检查 Server 端口存活情况,检查结果由 EnvoyS 反馈给 EnvoyC。 

L3/L4 层通信 协议的异常点驱逐(被动健康检查)功能失效

 

原因:L3/L4 层通信协议的异常点驱逐条件是连接异常,当流量被劫持到 EnvoyS 后,该功能实际上检查的是 EnvoyC 能否正常的跟 EnvoyS 建立连接,而不是 Server。

 

我们目前采用的解决方案是完善 L3/L4 层通信协议的驱逐条件,增加访问超时作为驱逐条件。因此,当 Server 异常时,EnvoyC 会因为一直无法得到应答,而将该下游标记为异常。

总结

 

最后简单的对比下上述两种方案:



基于服务发现的流量劫持机制目前已应用在百度 App、信息流、百度地图等业务线的数百个服务、数万个实例上。这种流量劫持机制能够减少转发性能的损耗,具备数据面故障自动容灾能力,能够动态回传流量治理参数。但是该机制也缺失一些能力:无法劫持入口服务的流量,后续我们将进一步补齐该能力。

2021-04-13 16:024844

评论

发布
暂无评论
发现更多内容

文心一言 VS 讯飞星火 VS chatgpt (109)-- 算法导论10.1 7题

福大大架构师每日一题

福大大架构师每日一题

TX云服务器续费肉痛?试试华为云耀云服务器吧!

轶天下事

手敲,Ascend算子开发入门笔记分享

华为云开发者联盟

人工智能 华为云 算子开发 华为云开发者联盟 自定义算子

租赁系统开发定制源码:实现高效、智能的资产管理和租赁流程

V\TG【ch3nguang】

使用 Databend Kafka Connect 构建实时数据同步

Databend

OpenHarmony父子组件双项同步使用:@Link装饰器

OpenHarmony开发者

给力!一个基于SpringBoot+Vue前后端分离低代码项目

互联网工科生

Vue 低代码 springboot

开发搭建体育行业的赛事直播平台指南

软件开发-梦幻运营部

打造次世代分析型数据库(五):复杂查询分析工具

腾讯云大数据

数据库

JD云云主机太捞?这款轻量云服务器存在感满满

轶天下事

八股乱背,力扣不会!下辈子远离计算机

王磊

Java java面试

聊聊技术之外的面试问题-上

老张

面试 职业规划 职业发展

深耕业财一体化,激活企业全面预算管理新动能

智达方通

业财融合 智达方通 全面预算管理 企业财务管理

Hello, Vector DB|认识一下,这才是真正的向量数据库

Zilliz

Milvus Zilliz ann 向量数据库

API网关是什么?

RestCloud

ipaas

C++移动和获取文件读写指针

智趣匠

云小课|MRS基础操作之集群健康检查

华为云开发者联盟

大数据 后端 华为云 华为云开发者联盟 华为云云小课

Parallels Desktop 19 for Mac虚拟机 19.0.0一键激活版+完整安装教程

mac

苹果mac Windows软件 Parallels Desktop 19 pd19虚拟机

低代码平台技术分享官丨inBuilder与DevOps平台的集成故事

inBuilder低代码平台

DevOps 低代码

全域Serverless+AI,华为云加速大模型应用开发

华为云开发者联盟

人工智能 华为云 华为云开发者联盟 大模型应用开发

节能减排 | AIRIOT智慧工厂节能管理解决方案

AIRIOT

物联网 智能工厂

技术为王丨华为云打破中小企业开发小程序低效怪圈

轶天下事

测试小白必掌握软件测试十大原则

优测云服务平台

软件测试 测试技术 软件测试工具 软件测试技能 测试能力

时间序列分析在股票量化策略中的探讨

Geek_d872c2

时间序列 量化投资

关系数据库SQL

Frank

sql

可拓展的低代码全栈框架

树上有只程序猿

软件开发 低代码

遥遥领先!华为云耀云服务器L实例打造企业数字化转型新标杆

YG科技

跨境电商难做?轻量云服务器助你快速“出海”

YG科技

Spring扩展-自定义属性编辑器

2023年被问了100遍的1000道java面试题,终于总结成了485页PDF

程序员万金游

编程 Java 面试 程序员、 java Java 面试题

HarmonyOS网络管理开发—Socket连接

HarmonyOS开发者

生产环境的 Service Mesh 流量劫持怎么搞?_架构_百度云原生团队_InfoQ精选文章