美团端侧CDN容灾解决方案

news2025/1/6 20:45:06

1. 前言

作为业务研发,你是否遇到过因为 CDN 问题导致的业务图片加载失败,页面打开缓慢,页面布局错乱或者页面白屏?你是否又遇到过某些区域 CDN 域名异常导致业务停摆,客诉不断,此时的你一脸茫然,不知所措?作为 CDN 运维,你是否常常被业务方反馈的各种 CDN 问题搞得焦头烂额,一边顶着各种催促和压力寻求解决方案,一边抱怨着服务商的不靠谱?今天,我们主要介绍一下美团外卖技术团队端侧 CDN 的容灾方案,经过实践,我们发现该产品能有效减少运维及业务开发同学的焦虑,希望我们的这些经验也能够帮助到更多的技术团队。

2. 背景

CDN 因能够有效解决因分布、带宽、服务器性能带来的网络访问延迟等问题,已经成为互联网不可或缺的一部分,也是前端业务严重依赖的服务之一。在实际业务生产中,我们通常会将大量的静态资源如 JS 脚本、CSS 资源、图片、视频、音频等托管至 CDN 服务,以享受其边缘节点缓存对静态资源的加速。但是在享用 CDN 服务带来更好体验的同时,也经常会被 CDN 故障所影响。比如因 CDN 边缘节点异常,CDN 域名封禁等导致页面白屏、排版错乱、图片加载失败。

每一次的 CDN 故障,业务方往往束手无策,只能寄希望于 CDN 团队。而 CDN 的监控与问题排查,对 SRE 也是巨大的难题和挑战。一方面,由于 CDN 节点的分布广泛,边缘节点的监控就异常困难。另一方面,各业务汇聚得到的 CDN 监控大盘,极大程度上隐匿了细节。小流量业务、定点区域的 CDN 异常往往会被淹没。SRE 团队也做了很多努力,设计了多种方案来降低 CDN 异常对业务的影响,也取得了一定的效果,但始终有几个问题无法很好解决:

  • 时效性:当 CDN 出现问题时,SRE 会手动进行 CDN 切换,因为需要人为操作,响应时长就很难保证。另外,切换后故障恢复时间也无法准确保障。
  • 有效性:切换至备份 CDN 后,备份 CDN 的可用性无法验证,另外因为 Local DNS 缓存,无法解决域名劫持和跨网访问等问题。
  • 精准性:CDN 的切换都是大范围的变更,无法针对某一区域或者某一项目单独进行。
  • 风险性:切换至备份 CDN 之后可能会导致回源,流量剧增拖垮源站,从而引发更大的风险。

当前,美团外卖业务每天服务上亿人次,即使再小的问题在巨大的流量面前,也会被放大成大问题。外卖的动态化架构,70%的业务资源都依赖于 CDN,所以 CDN 的可用性严重影响着外卖业务。如何更有效的进行 CDN 容灾,降低 CDN 异常对业务的影响,是我们不断思考的问题。

既然以上问题 SRE 侧无法完美地解决,端侧是不是可以进行一些尝试呢?比如将 CDN 容灾前置到终端侧。不死鸟(Phoenix) 就是在这样的设想下,通过前端能力建设,不断实践和完善的一套端侧 CDN 容灾方案。该方案不仅能够有效降低 CDN 异常对业务的影响,还能提高 CDN 资源加载成功率,现已服务整个美团多个业务和 App。

3. 目标与场景

3.1 核心目标

为降低 CDN 异常对业务的影响,提高业务可用性,同时降低 SRE 同学在 CDN 运维方面的压力,在方案设计之初,我们确定了以下目标:

  • 端侧 CDN 域名自动切换:在 CDN 异常时,端侧第一时间感知并自动切换 CDN 域名进行加载重试,减少对人为操作的依赖。
  • CDN 域名隔离:CDN 域名与服务厂商在区域维度实现服务隔离且服务等效,保证 CDN 切换重试的有效性。
  • 更精准有效的 CDN 监控:建设更细粒度的 CDN 监控,能够按照项目维度实时监控 CDN 可用性,解决 SRE CDN 监控粒度不足,告警滞后等问题。并根据容灾监控对 CDN 容灾策略实施动态调整,减少 SRE 切换 CDN 的频率。
  • 域名持续热备:保证每个 CDN 域名的持续预热,避免流量切换时导致回源。

3.2 适用场景

适用所有依赖 CDN ,希望降低 CDN 异常对业务影响的端侧场景,包括 Web、SSR Web、Native 等技术场景。

4. Phoenix 方案

一直以来,CDN 的稳定性是由 SRE 来保障,容灾措施也一直在 SRE 侧进行,但仅仅依靠链路层面上的保障,很难处理局部问题和实现快速止损。用户终端作为业务的最终投放载体,对资源加载有着天然的独立性和敏感性。如果将 CDN 容灾前置到终端侧,无论从时效性,精准性,都是 SRE 侧无法比拟的。在端侧进行容灾,就需要感知 CDN 的可用性,然后实现端侧自动切换的能力。我们调研整个前端领域,并未发现业内在端侧 CDN 容灾方面有所实践和输出,所以整个方案的实现是从无到有的一个过程。

4.1 总体设计

Phoenix 端侧 CDN 容灾方案主要由五部分组成:

  • 端侧容灾 SDK:负责端侧资源加载感知,CDN 切换重试,监控上报。
  • 动态计算服务:根据端侧 SDK 上报数据,对多组等效域名按照城市、项目、时段等维度定时轮询计算域名可用性,动态调整流量至最优 CDN。同时也是对 CDN 可用性的日常巡检。
  • 容灾监控平台:从项目维度和大盘维度提供 CDN 可用性监控和告警,为问题排查提供详细信息。
  • CDN 服务:提供完善的 CDN 链路服务,在架构上实现域名隔离,并为业务方提供等效域名服务,保证端侧容灾的有效性。等效域名,就是能够通过相同路径访问到同一资源的域名,比如:cdn1.meituan.net/src/js/test.js 和 cdn2.meituan.net/src/js/test.js 能够返回相同内容,则 cdn1.meituan.net 和 cdn2.meituan.net 互为等效域名。
  • 容灾配置平台:对项目容灾域名进行配置管理,监控上报策略管理,并提供 CDN 流量人工干预等措施。

4.2 容灾流程设计

为保证各个端侧容灾效果和监控指标的一致性,我们设计了统一的容灾流程,整体流程如下:

4.3 实现原理

4.3.1 端侧容灾 SDK

Web 端实现

Web 端的 CDN 资源主要是 JS、CSS 和图片,所以我们的容灾目标也聚焦于这些。在 Web 侧的容灾,我们主要实现了对静态资源,异步资源和图片资源的容灾。

实现思路

要实现资源的容灾,最主要的问题是感知资源加载结果。通常我们是在资源标签上面添加错误回调来捕获,图片容灾可以这样实现,但这并不适合 JS,因为它有严格的执行顺序。为了解决这一问题,我们将传统的标签加载资源的方式,换成XHR来实现。通过Webpack在工程构建阶段把同步资源进行抽离,然后通过PhoenixLoader来加载资源。这样就能通过网络请求返回的状态码,来感知资源加载结果。

在方案的实现上,我们将 SDK 设计成了 Webpack Plugin,主要基于以下四点考虑:

  1. 通用性:美团前端技术栈相对较多,要保证容灾 SDK 能够覆盖大部分的技术框架。
  2. 易用性:过高的接入成本会增加开发人员的工作量,不能做到对业务的有效覆盖,方案价值也就无从谈起。
  3. 稳定性:方案要保持稳定可靠,不受 CDN 可用性干扰。
  4. 侵入性:不能侵入到正常业务,要做到即插即用,保证业务的稳定性。

通过调研发现,前端有 70%的工程构建都离不开 Webpack,而 Webpack Plugin 独立配置,即插即用的特性,是实现方案的最好选择。整体方案设计如下:

当然,很多团队在做性能优化时,会采取代码分割,按需引入的方式。这部分资源在同步资源生成的过程中无法感知,但这部分资源的加载结果,也关系到业务的可用性。在对异步资源的容灾方面,我们主要是通过对 Webpack 的异步资源处理方式进行重写,使用Phoenix Loader接管资源加载,从而实现异步资源的容灾。整体分析过程如下图所示:

CSS 资源的处理与 JS 有所差别,但原理相似,只需要重写 mini-css-extract-plugin 的异步加载实现即可。

Web 端方案资源加载示意:

容灾效果

Native 端容灾

客户端的 CDN 资源主要是图片,音视频以及各种动态化方案的 bundle 资源。Native 端的容灾建设也主要围绕上述资源展开。

实现思路

重新请求是 Native 端 CDN 容灾方案的基本原理,根据互备 CDN 域名,由 Native 容灾基建容灾域名重新进行请求资源,整个过程发生在原始请求失败后。Native 容灾基建不会在原始请求过程中进行任何操作,避免对原始请求产生影响。原始请求失败后,Native 容灾基建代理处理失败返回,业务方仍处于等待结果状态,重请新求结束后向业务方返回最终结果。整个过程中从业务方角度来看仍只发出一次请求,收到一次结果,从而达到业务方不感知的目的。为将重新请求效率提升至最佳,必须尽可能的保证重新请求次数趋向于最小。

调研业务的关注点和技术层面使用的网络框架,结合 Phoenix 容灾方案的基本流程,在方案设计方面,我们主要考虑以下几点:

  • 便捷性:接入的便捷性是 SDK 设计时首先考虑的内容,即业务方可以用最简单的方式接入,实现资源容灾,同时也可以简单无残留拆除 SDK。
  • 兼容性:Android 侧的特殊性在于多样的网络框架,集团内包括 Retrofit 框架,okHttp 框架,okHttp3 框架及已经很少使用的 URLConnection 框架。提供的 SDK 应当与各种网络框架兼容,同时业务方在即使变更网络框架也能够以最小的成本实现容灾功能。而 iOS 侧则考虑复用一个 NSURLProtocol 去实现对请求的拦截,降低代码的冗余度,同时实现对初始化项进行统一适配。
  • 扩展性:需要在基础功能之上提供可选的高级配置来满足特殊需求,包括监控方面也要提供特殊的监控数据上报能力。

基于以上设计要点,我们将 Phoenix 划分为以下结构图,图中将整体的容灾 SDK 拆分为两部分 Phoenix-Adaptor 部分与 Phoenix-Base 部分。

Phoenix-Base

Phoenix-Base 是整个 Phoenix 容灾的核心部分,其包括容灾数据缓存,域名更换组件,容灾请求执行器(区别于原始请求执行器),监控器四个对外不可见的内部功能模块,并包含外部接入模块,提供外部接入功能。

  1. 容灾数据缓存:定期获取及更新容灾数据,其产生的数据只会被域名更换组件使用。
  2. 域名更换组件:连接容灾数据缓存,容灾请求执行器,监控器的中心节点,负责匹配原始失败 Host,过滤错误码,并向容灾请求执行器提供容灾域名,向监控器提供整个容灾过程的详细数据副本。
  3. 容灾执行器:容灾请求的真正请求者,目前采用内部 OkHttp3Client,业务方也可以自主切换至自身的执行器。
  4. 监控器:分发容灾过程的详细数据,内置数据大盘的上报,若有外部自定义的监控器,也会向自定义监控器分发数据。

Phoenix-Adaptor

Phoenix-Adaptor 是 Phoenix 容灾的扩展适配部分,用于兼容各种网络框架。

  • 绑定器:生成适合各个网络框架的拦截器并绑定至原始请求执行者。
  • 解析器:将网络框架的 Request 转换为 Phoenix 内部执行器的 Request,并将 Phoenix 内部执行器的 Response 解析为外部网络框架 Response,以此达到适配目的。

容灾效果

① 业务成功率

以外卖图片业务为例,Android 业务成功率对比(同版本 7512,2021.01.17 未开启 Phoenix 容灾,2021.01.19 晚开启 Phoenix 容灾)。

iOS 业务成功率对比(同版本 7511,2021.01.17 未开启 Phoenix 容灾,2021.01.19 晚开启 Phoenix 容灾)。

② 风险应对

以外卖与美团图片做为对比 ,在 CDN 服务出现异常时,接入 Phoenix 的外卖 App 和未接入的美团 App 在图片成功率方面的对比。

4.3.2 动态计算服务

端侧的域名重试,会在某一域名加载资源失败后,根据容灾列表依次进行重试,直至成功或者失败。如下图所示:

如果域名 A 大范围异常,端侧依然会首先进行域名 A 的重试加载,这样就导致不必要的重试成本。如何让资源的首次加载更加稳定有效,如何为不同业务和地区动态提供最优的 CDN 域名列表,这就是动态计算服务的要解决的问题。

计算原理

动态计算服务通过域名池和项目的 Appkey 进行关联,按照不同省份、不同地级市、不同项目、不同资源等维度进行策略管理。通过获取 5 分钟内对应项目上报的资源加载结果进行定时轮询计算,对域名池中的域名按照地区(城市&&省份)的可用性监控。计算服务会根据域名可用性动态调整域名顺序并对结果进行输出。下图是一次完整的计算过程:

假设有 A、B、C 三个域名,成功率分别是 99%、98%、97.8%,流量占比分别是 90%、6%、4%。基于转移基准,进行流量转移,比如,A 和 B 成功率差值是 1,B 需要把自己 1⁄2 的流量转移给 A,同时 A 和 C 的成功率差值大于 1,C 也需要把自己 1⁄2 的流量转移给 A,同时 B 和 C 的差值是 0.2,所以 C 还需要把自己 1⁄4 的流量转移给 B。最终,经过计算,A 的流量占比是 95%,B 是 3.5%,C 是 1.5%。最后,经过排序和随机计算后将最终结果输出。

因为 A 的占比最大,所以 A 优先被选择;通过随机,B 和 C 也会有一定的流量;基于转移基准,可以实现流量的平稳切换。

异常唤起

当某个 CDN 无法正常访问的时候,该 CDN 访问流量会由计算过程切换至等效的 CDN B。如果 SRE 发现切换过慢可以进行手动干预分配流量。当少量的 A 域名成功率上升后,会重复计算过程将 A 的流量加大。直至恢复初始态。

服务效果

动态计算服务使得资源的首次加载成功率由原来的99.7%提升至99.9%。下图为接入动态计算后资源加载成功率与未接入加载成功率对比。

4.3.3 容灾监控

在监控层面,SRE 团队往往只关注域名、大区域、运营商等复合维度的监控指标,监控流量巨大,对于小流量业务或者小范围区域的 CDN 波动,可能就无法被监控分析识别,进而也就无法感知 CDN 边缘节点异常。容灾监控建设,主要是为了解决 SRE 团队的 CDN 监控告警滞后和监控粒度问题。监控整体设计如下:

流程设计

端侧容灾数据的上报,分别按照项目、App、资源、域名等维度建立监控指标,将 CDN 可用性变成项目可用性的一部分。通过计算平台对数据进行分析聚合,形成 CDN 可用性大盘,按照域名、区域、项目、时间等维度进行输出,与天网监控互通,建立分钟级别的监控告警机制,大大提升了 CDN 异常感知的灵敏性。同时,SRE 侧的天网监控,也会对动态计算服务结果产生干预。监控整体流程如下:

监控效果

CDN 监控不仅从项目维度更加细粒度的监测 CDN 可用性,还为 CDN 异常排查提供了区域、运营商、网络状况、返回码等更丰富的信息。在监控告警方面,实现了分钟级异常告警,灵敏度也高于美团内部的监控系统。

4.3.4 CDN 服务

端侧域名切换的有效性,离不开 CDN 服务的支持。在 CDN 服务方面,在原有 SRE 侧容灾的基础上,对 CDN 服务整体做了升级,实现域名隔离,解决了单域名对应多 CDN 和多域名对应单 CDN 重试无效的弊端。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/567913.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

javaWebssh服装租赁店信息管理系统台myeclipse开发mysql数据库MVC模式java编程计算机网页设计

一、源码特点 java ssh服装租赁店信息管理系统是一套完善的web设计系统(系统采用ssh框架进行设计开发),对理解JSP java编程开发语言有帮助,系统具有完整的源代码和数据库,系统主要 采用B/S模式开发。开发环境为TO…

C++第一章:开始

开始目录 引言一、开发环境和参考书籍二、一个简单的C程序三、初识输入和输出标准输入输出对象 四、注释五、控制流while循环for循环 六、数量不定数据的输入七、C 缩进和格式八、类简介使用一个类书店处理书籍信息程序 九、术语表 引言 C在人们的眼中通常是“复杂”一词的代表…

软考高级架构师笔记-4中间件、嵌入式技术

目录 1. 前言 & 考情分析2. 中间件3. 微处理器4. 嵌入式软件5. 嵌入式系统6. 嵌入式软件设计6. 结语1. 前言 & 考情分析 前文回顾: 软考高级架构师笔记-1计算机硬件软考高级架构师笔记-2计算机软件(操作系统)软考高级架构师笔记-3数据库本章考情: 本章节偶尔会考到…

多电商平台订单整合,库存同步ERP系统,为何不用电商API对接?

还有不到1个月就是618购物狂欢节了,这个节日对很多电商来说是重头戏,一年中销售额暴涨的机会。现在电商们会在多平台开直播,挂小黄车,如抖音、拼多多、小红书等。数据资源大户电商们通常会把这些不同类型的海量数据分散存储在各个…

如何快速使用 WeUI 组件库?

1、如何快速应用 WeUI 组件库 快速应用 WeUI 组件库的步骤如下: 1、进入即时设计社区资源广场:访问即时设计社区资源广场,该资源广场提供免费使用的 WeUI 组件库,包括深色版和浅色版。设计师可以根据产品风格选择合适的组件库。…

[C++]octomap安装后测试

测试环境&#xff1a; vs2019 octomap1.9.6 release x64 代码&#xff1a; #include <octomap/octomap.h> #include <octomap/OcTree.h> using namespace std; using namespace octomap; void print_query_info(point3d query, OcTreeNode* node) { if (…

使用JS来实现轮播图的效果

最好今天分享一个使用JS制作的轮播图效果 个人名片&#xff1a; &#x1f60a;作者简介&#xff1a;一名大一在校生&#xff0c;web前端开发专业 &#x1f921; 个人主页&#xff1a;几何小超 &#x1f43c;座右铭&#xff1a;懒惰受到的惩罚不仅仅是自己的失败&#xff0c;…

mjpg-streamer实现细节分析

mjpg-streamer实现细节分析 文章目录 mjpg-streamer实现细节分析输入初始化input_initinit_videoIninit_v4l2 启动摄像头输入线程cam_threaduvcGrabcompress_yuyv_to_jpegmemcpy_picture 输出初始化output_init启动摄像头输出线程server_thread设置 SO_REUSEADDR 选项。设置 IP…

数据库 查询执行(1) 多路归并

用户输入一个sql语句 sql解析器 将sql语句转换成一个 关系代数 但是同时也会附加一些 操作 (下方未体现)。 外存排序 原理 外部数据元素太多无法一次性的读入内存 通常设计者 会让磁盘块的大小和缓冲区的大小相等 。 首先构造初始的归并段 分别从横向和纵向 体会这…

单片机GD32F303RCT6 (Macos环境)开发 (二十七)—— 蓝牙透传模块HC-08的调试

蓝牙透传模块HC-08的调试 1、模块为汇承HC-08&#xff0c;GD32我们之前已经把usart1 配置成了dmaidle的方式接收数据&#xff0c;我们的hc-08模块连接的就是这一路usart。 所以&#xff0c;与GD32的连接比较简单&#xff0c;如下图&#xff1a; GD32 HC-08 TX(PA2 ) RX RX(PA3…

弘基笔记本电脑怎么使用U盘重装系统?

弘基笔记本电脑怎么使用U盘重装系统&#xff1f;有的用户的弘基笔记本电脑使用过程中出现了蓝屏的情况&#xff0c;系统频繁的出现蓝屏问题导致自己的使用受到了影响&#xff0c;那么这个情况怎么去进行问题的解决呢&#xff1f;一起来看看以下的解决方法吧。 准备工作&#xf…

挂耳式蓝牙耳机排行,四款挂耳式耳机盘点

现在耳机的更新换代也是相当快的&#xff0c;普通的入耳式耳机在长期佩戴的舒适度方面饱受诟病&#xff0c;所以新近流行的开放式耳机很好的避免这个问题&#xff0c;它拥有不入耳不伤耳佩戴设计&#xff0c;解放双耳的同时也更不易丢失。面对市面上款式多样的开放式耳机&#…

Qt基础 自定义消息框

ps&#xff1a;忘记copy那位大佬tip代码了&#xff0c;后面新增可以点选的控件 #pragma once#include <QWidget> #include <QHBoxLayout>#define SHADOW_WIDTH 15 // 窗口阴影宽度; #define TRIANGLE_WIDTH 15 // 小三角的宽度; #de…

优化 docker 容器性能慢问题

问题&#xff1a; 部署环境下tomcat容器启动缓慢&#xff0c;耗时10多分钟&#xff0c;性能较差&#xff0c;同时后端服务响应较慢。 排查&#xff1a; 宿主环境&#xff1a; docker使用情况&#xff1a; 对比结果CPU、内存使用率都不高。 针对docker环境进行检查&#xff…

浅析变电站无人值守管理的模式与特点

安科瑞虞佳豪 近年来&#xff0c;随着电网的发展&#xff0c;变电站实行无人值班管理模式已成为电网的发展方向。自1998年始&#xff0c;辉县市就开始了变电站综合自动化改造&#xff0c;截止目前全局所属24座变电站&#xff08;其中35kV19座、110kV5座&#xff09;已全部实现…

对话 ONES 联合创始人兼 CTO 冯斌:技术管理者如何打造一支自驱型团队?

熟悉冯斌的人&#xff0c;大都直接称呼其网名 Kid&#xff0c;包括他在 ONES 的同事。人如其名&#xff0c;Kid 的寓意就是「用孩子的眼光看世界」&#xff0c;返璞归真的思维方式才能发现新大陆。正如毕加索说的&#xff1a;「我一生都在向孩子学习。」 在 ONES 联合创始人兼…

基因注释R包——annotatr介绍

目录 简介安装annotatr包使用annotatr进行注释CpG注释基因注释自定义注释读取基因组区域注释区域 简介 下一代测序实验和生物信息学管道产生的基因组区域在注释基因组特征时更有意义。出现在外显子或增强子中的SNP可能比出现在基因间区域的SNP更令人感兴趣。有趣的是&#xff…

Tomcat安装与启动和配置

目录 Tomcat 简介 Tomcat 安装 Tomcat 启动和配置 文件夹作用 启动&#xff0c;关闭Tomcat&#xff1b; 常见问题 配置 环境变量 IDEA中配置Tomcat Tomcat 简介 Tomcat 服务器是一个免费的开放源代码的Web 应用服务器&#xff0c;属于轻量级应用服务器&#xff0c;在…

CSDN铁粉攻略

欢迎关注博主 Mindtechnist 或加入【Linux C/C/Python社区】一起学习和分享Linux、C、C、Python、Matlab&#xff0c;机器人运动控制、多机器人协作&#xff0c;智能优化算法&#xff0c;滤波估计、多传感器信息融合&#xff0c;机器学习&#xff0c;人工智能等相关领域的知识和…

DataX-一款稳定高效的数据同步工具-从安装、启动、配置、使用总结,看这篇让你一步到位

前言 大数据部门现阶段ETL按同步方式分为两种&#xff1a; 实时同步&#xff1a;DTS、CloudCanal离线同步&#xff1a;dataworks-DI节点 但CloudCanal在使用中出现了部分问题&#xff0c;归纳总结后主要为以下几点&#xff1a; 部分使用场景获取不到binlog点位停止任务&…