web项目上云_披荆斩棘向云端 — 职能业务上云踩坑实战

web项目上云_披荆斩棘向云端 — 职能业务上云踩坑实战披荆斩棘向云端—职能业务上云踩坑实战从2018年初开始,企业IT部职能中心的小伙伴就开始对业务上云这事跃跃欲试了

披荆斩棘向云端 — 职能业务 上云踩坑实战

从2018年初开始,企业IT部职能中心的小伙伴就开始对业务上云这事跃跃欲试了。但实际上我们的绝大多数应用都是基于 Windows 平台的,因此为了长远打算,我们启动了技术栈和跨平台升级的工程。经过同学们一年半的历练,我们积累了大量基于容器开发、运营的经验,具备了上云的条件。因此,在此次轰轰烈烈的上云行动中,我们团队也有幸作为部门的先行先试团队,率先实施业务上云。

     但是上云这事,很显然不是一件容易的事。特别是作为“摸着石头过河”的开荒者,没有前人的经验,只好大胆尝试小心验证,一步一个脚印,稳步推进了。下面,我将分享一下我们团队在上云过程中遇到的一些实战的“坑”,作为一家之言,以飨后来者。

上云难度

      对于上云,我们是没有经验的“拓荒者”,我们只能摸着石头过河。

4c0461178dbd542dad70fcfc406e846c.png

      职能中心的业务主要有三个领域:集团采购、行政、公共策略,三个领域的业务体量不同,特色也各有不同。

      采购业务,作为中心历史最悠久的业务,可以追述到十年前。业务在成长,团队在成长,所用到的技术栈也在变化,在这部分业务中,我们几乎可以看到半个软件开发技术发展史。

      行政业务,打开 Tencent Home 您就能看到,大到班车、会议室,小到理个发、贴个膜,只要是提升员工幸福感的事,我们什么都做,为员工提供了数百项服务,为员工营造家一般的氛围,其形态各异的项目数量也很庞大。

      公共策略业务,作为新兴领域,团队引进了若干新鲜血液,启动或接手了大量的项目,新同学接触新系统,一切都是从陌生到熟悉的过程。

      从复杂度上讲,我们不同业务、不同类型、不同时期的项目混合堆积在同一台服务器上部署;涉及 7 个不同的网络区域及相互之间的复杂交互。

      从体量上讲,我们的项目形态各异,组织各异,上云的可复制性极低,难以做到批量性,必须一个项目一个项目地推进。

      同时,作为一个业务团队,我们的业务需求和业务迭代是不会给机会等待我们上云的,往往迭代开发和业务上云都在同时进行,这也导致测试验证难度和上云回滚的风险大大增加。每一次流量上云切换都可能对业务带来阵痛,每次迁移切换都需要与业务沟通协调人力和时间,业务侧能够给予的时间窗口也弥足珍贵。如果不巧,系统还涉及到外部公司,其协调难度将直线上升,一旦业务受影响,损失了公司的口碑和信誉,也是我们难以接受的。

      除此之外,我们还有需要偿还的历史旧账,“迁移不是目的,目的还是要在迁移过程中解决一些现有问题,能够体现出工作的价值,总结一套最佳实践的方法(短期),同时,未来我们过度到云环境下的运营和开发打下基础(中长期)。所以过程中大家不仅仅是说按要求完成规定动作,还是要想想借助这次迁移,思考下以上问题,并及时反馈。”——这是领导对业务上云提出的进一步要求。

应对策略

      通过以上的分析,很显然,整个中心所有业务上云这事是不容易的。现实的问题摆在面前,我们要怎么做呢?那就是要根据产品和团队的形态,采取不同的上云策略。具体从方法论上,我们提炼了两个方面。

“关注点分离”—— 设计原则

      我们可以通过多种维度,将上云这一件复杂的事情,简化拆分为多件简单的事情。确保一件事情,那就是每一次上云,只有一个变更点。其带来的好处就是,上云前的准备工作会被分解,上云过程中出现问题时,能更快速定位和解决问题,保证风险的最大控制能力,尽可能地保证业务稳定运行。

c35c8c09cf100e7345659ffd63d48fcd.png

“组织架构决定技术架构”— 康威定律

      第二个方面,我们通过分析不同团队的组织形式和项目特点,采取了不同的上云策略。

3fda2d83af8e85db6833411aa1bc4a8b.png

      对于采购领域的业务,我们由多人同时负责同一个历史悠久、极其复杂的项目。其开发测试人员也几经易手,项目的内外部依赖、耦合都极其复杂,甚至很多模块有哪些配置,有哪些上下游依赖也无人知晓,文档不可考。对于这样大而复杂的系统,我们则以机器维度进行整体上云。团队的同学们协调时间进行统一验证,统一上云。

57adc306e23c02e5342087bd2655855e.png

      对于行政领域的业务,我们团队的每个成员各自都负责了大大小小多个不同的系统,虽然数量庞大,但这些系统之间的耦合度相对较低。因此我们决定采取各个系统分别排期、分别上云,各个击破的方式。每个人对自己负责的系统较为熟悉,迁移自己负责的系统,其效率较高,风险较低,能够保证在上云的过程中业务稳定。

e3403b07552294bb1f0cb2c990c8836c.png

      而在公共策略领域,由于团队的建立相对较晚,要么是新成员负责老系统,要么是老成员负责新系统。为了批量化进行,提升与运营侧的沟通协调效率,我们安排专职人员进行所有系统的上云工作,这样由专人负责,可以有效地减少沟通成本,上云的操作步骤上,也可以统一进行,提高了上云的效率。

采坑实录

    即使有应对策略的方法论指导,但在实际的上云迁移过程中,我们不免还是跌跌撞撞地踩到了大量的坑,暴露了上云过程中从运营到开发的若干问题。

8cfe3b12d4dbbd7e730fd55f398e5df4.png

       经过统计,仅登记在案的问题就有 76 个之多。这其中的问题规模有大有小。小的问题可能几个小时就能搞定,大的问题甚至排期到一个季度才能搞定。

      从类型分布上讲,问题最多的是网络策略方面。这也是意料之中的,毕竟通过上云,应用所运行的整个IaaS层环境都与云下不同了,再何况云上的网络策略要求更规范、更严格;其次是平台使用和运营工具两个方面,运营和开发同学在这个过程中都是在熟悉新的环境、新的工具,在使用上还不够得心应手,TKEX 平台目前自身也都还在进化完善,这对我们使用上也造成了一定的障碍。只是上述三个类型的问题,其占比就接近 3/4 了。

      为了提供前车之鉴,下面分享几个典型的案例。主菜之前,咱们先来一碟开胃菜,看一看最简单的问题是如何解决。

01

踩坑典型案例

解决多阶段请求 IP 校验失败的问题

86f557198343e866bdaa64fe3be3da7f.png

      在我们的应用中,有上传附件到 GAS 服务的场景。GAS 服务为确保上传附件的合理鉴权,其中有对上传来源的 IP 进行校验的逻辑。这会分为两步,首先由业务侧获取自身的 IP 并以此为参数请求 GAS,得到一个 uploadid,然后再根据这个 uploadid 来上传实际的文件数据。GAS 服务在接收文件数据之前,会获取客户端 IP 进行校验,判断本次上传的来源是否合法。

      原本这个逻辑在云下环境已经跑了很多年,但我们的系统上云之后却无法正常工作了。问题就发生在这两段交互的前一段,由于业务在容器中运行,因此从容器中获取到了容器实例的 IP,而非计算节点的 IP,而 GAS 服务端获取到的是计算节点的 IP,这就导致第二段请求时校验失败了。作为基础服务,GAS 服务端提供给了大量的业务共同使用,因此对于这段校验逻辑是很难去驱动修改的。于是只能通过调整业务侧逻辑来解决这个问题。

      我们通过分析,现在只需要将节点 IP 通过某种形式传入容器,那么业务即可获取到这个 IP 进而带着它去请求 GAS了。于是 TKEX 的环境变量 NODE_IP 就登场了,我们配置好这个环境变量,并且在容器中获取它,成功地得到了容器的节点 IP,最终解决了这个问题。

02

踩坑典型案例

容器 IP 段与应用网关/TOF之间的访问

       关于 IP 校验,发散起来远远不止上述的 GAS 服务了。只算公司内和部门内的基础服务,就有 TOF、应用网关、ASF 等若干服务,其校验请求者都是以 IP 白名单的形式,甚至如 TOF 服务是不支持 IP 段,支持配置一个一个 IP 的。即使应用网关支持 token 方式鉴权,但由于 token 鉴权和 IP 白名单鉴权不可以同时开启,而上云过程是一个过程,同一个系统存在云上云下混布的中间态,因此难以一刀切地把所有系统都改为 token 鉴权,不得不采用 IP 白名单的方式。遑论我们还有大量的老旧系统,几年未有过迭代,维护的人也已几经易手,更难以去推动更改鉴权方式了。

      类似的情况给我们的业务上云造成了极大的影响。一方面,我们需要梳理所有对这些基础服务的依赖,另一方面,我们必须配置所有计算节点的 IP 到相关的服务。这将容器集群后续的扩容和这些服务的IP白名单耦合了起来。试想,在半年、一年后,TKEX 容器集群的计算节点扩容,那么到时候我们又要再一次地梳理所有使用到这些服务的应用,配置对应系统接入这些服务时的 IP 白名单。不得不说,这是一件非常容易遗漏、遗忘的事情。

03

踩坑典型案例

通过“有限回滚”避免整体迁移失败

aded71d290d757ff3799cf4fca970cd0.png

       我们的 EPO 系统要从云下迁移到云上,遵循“关注点分离”的原则,本次只迁移 web 层上云。但是上云后我们发现,局部两个路径下的请求会偶发失败。现在我们面临两个选择,一个是作为已知问题,公告用户某些功能有问题暂时不能提供服务,预期日后修复;另一个是回退变更,还原流量请求到云下,定位并解决问题之后重新再申请变更窗口期。让用户感知到业务出现故障,这是我们无法接受的,而此次变更窗口期也是很艰难才从业务方申请到的,那怎么办呢?

      经过分析,我们确认故障点很小,于是使用 PAAS 网关的智能路由的能力,使得有故障的局部请求,还是被路由到云下系统。那么对于用户来讲,整个系统仍然是可用的,对于我们来讲,后续只需要有针对性地修复这两个局部问题即可。整个上云变更无需回退,也无需再重新向业务方申请变更窗口期了。

    前面的几个案例都相对简单,都可以短平快地立即解决,看官们可能并不过瘾,接下来,我们分享两则相对复杂的案例。

04

踩坑典型案例

网络链路故障场景

201974f18531da81492bcef1831af4a3.png

      仍然是上述的 EPO 系统上云,前文将 Web 层已经迁移上云了,但是中间层的情况就相对复杂一些。

EPO系统基于 ASF 平台做服务治理,从上图请求链路①可知,请求都通过 ASF 进行路由进行流量控制。那么上云就是要将云下的流量①切换到云上的流量②,这个过程要怎么做呢?

      首先,我们从生产复制一份 Web 层,单独搭建部署。其次,我们从 ASF 系统中离线一整套出来,为刚刚复制的 Web 层做流量控制,使得这些流量都能被路由到云上的 EPO 中间层。整个这套,我们定义为验证环境,而云上 EPO 中间层即为待验证的目标环境。一旦验证成功,则可以重新将 ASF 上线,将所有流量切到云上 EPO 中间层,然后删除验证环境中那份单独搭建的 Web 层即可。

    但事情,往往是有意外的。我们在验证过程中发现,通过云上中间层去访问数据库的时候,会偶发报错:ORA-25408: 无法安全重放调用,这是什么原因呢?

240bb24487c3d1a060c83e82617de113.gif

可能原因一:数据库维护

根据经验,这个错误在如下两个情况会大概率发生:

a.数据库维护时

b.维护后程序第一次连接时

      其原理是,Oracle 客户端会在保证数据安全的情况下,重放刚刚被断开的查询请求,如果无法重新建立连接(或者无法确保安全),则会抛出上述异常的错误。

      那么故障当时是否是有数据库维护呢?答案是否定的。我们继续对现场进行排查,在访问验证系统时虽然报了很多次上述错误,但待验证的目标服务多达 44 个,即使是每一个服务只在“第一次访问数据库”的时候报一次错误,都可能报 44 个错误。为了检测是不是每个服务都只报了一次错,我们逐一排查 44 个服务的日志,发现并不是想象的那样,而是同一个服务有多次报错。这样看来,也不是“维护后程序第一次连接时”产生的错误。就这样,我们排查了 44 个服务的日志,自问自答了若干问题,最后把怀疑的重点放到了 TPC 连接上。

240bb24487c3d1a060c83e82617de113.gif

可能原因二:TCP 长连接被重置或被关闭

疑点一:RAC 配置(Real Application Clusters)导致 TCP 连接不稳定

      由于我们的 Oracle 云数据库采用了 RAC 配置,具有连接断开时的 FailOver 机制,因此我们首先来排查是否是我们的服务器与某个 RAC 计算节点之间的网络有了问题,是不是由于配置了多个 RAC 节点而其中某些节点不稳定呢?检查当前 TNS 的配置,我们配置了 4 个数据库节点。在去掉 RAC 配置,仅连接一台节点后发现,没有了 FailOver,Oracle 直接报了失去连接的错误。而且这个错误不随 RAC 节点的改变而消失或出现。据此,我们可以确认两个方面:

a.TCP 连接确实有重置或关闭发生

b.故障并非由 RAC 配置导致,RAC 指向的多个计算节点均有连接断开的情况发生

疑点二:数据库长连接被防火墙断开

      好了,既然质疑 TCP 连接有被重试,那么我们来验证一下。在验证之前我需要补充一个背景,那就是出于性能考虑,我们的应用于数据库之间的连接采用了长连接模式,也就是说,一旦打开数据库连接,就不会从应用侧主动去关闭断开数据库连接了,连接断开,要么是服务端主动断开,要么是网络层断开。而如果是服务端主动断开,数据访问层的驱动及SDK是可以感知到的,并且在框架层面我们也做了相应的容错处理,这块应该不会导致问题的出现,那就只能是网络层断开了我们的TCP连接。

与网络侧沟通,我们得到了两个信息:

a.我们的应用与数据库之间,存在硬件防火墙

b.根据现有配置,硬件防火墙会关闭30分钟内没有数据传输的TCP连接

      我们再回头看现场。由于是验证环境,因此访问的请求很少,数据库连接池最大连接数设置为 20。同时,数据访问层采用的是长连接模式,打开了数据库连接就不再关闭。很敏感地,我们发现了这里有个“30分钟”的数字,并且硬件防火墙的这个特性,和我们故障场景十分吻合。为了确认上述的猜想,我们进行了两次验证。

验证一:使用 SQLPlus 连接数据库并观察防火墙上的会话

      首先,我们在待验证的服务器上安装 SQLPlus 客户端,并且打开客户端连接数据库。此时为 2020年7月14日16点11分。

b796fc57f7b3228847de85547d868861.png

      同时,我们在硬件防火墙对该链接进行信息查询输出,可以看到连接情况。在17点13分左右,连接剩余有效时间为 136 秒。

      在大约 70 分钟之后,通过 life 1 可知,“若干空闲时间之后”,硬件防火墙即将关闭该链接:

3c2796637e95c5cee83f548d2a4a2996.png

      果然,在硬件防火墙关闭连接之后,我们再次通过 SQLPlus 进行数据库操作时便失败了:

b796fc57f7b3228847de85547d868861.png

      以上,根据防火墙上的会话来看,可以说明连接会话已经断开了。

验证二:对TCP连接进行抓包

      为了进一步详细确认,我们进行了第二次验证。这一次我们采用了更专业的 Wireshark,对应用服务器与数据库之间的 1523 端口的 TCP 通信进行抓包。

de963816c2855a84f15790093a9f4693.png

      如上图所示,在发起数据库查询并建立了 TCP 长连接之后,长达 3个小时20分钟 时间范围内(行号14936~6326619)并未发生任何数据通信。

      而在 6326619 行所示,直到 19:23 左右,我们通过访问应用发起请求,应用服务器预期当前TCP连接为长连接,期待可以直接通信,因此并未重新发起 SYN 包进行重连接,而是直接发起 PSH 数据包。但接下来在 6326621 行,远程返回了 RST 数据包,明确表明 TCP 连接被重置了。

      以上,我们真实地确认了当前 TCP 连接是由于网络链路的原因而断开了。接下来,我们便来尝试解决这个问题。

尝试一:设置类似 KeepAlive 的心跳,保证连接不长期空闲

      Oracle 服务端有 SQLNET.EXPIRE_TIME 配置,该配置的目的是周期性地向客户端发送探测数据包,从而检查客户端是否异常断开(如网络异常中断,客户端异常掉电,异常重启等),在发现断开之后,则服务端会主动清理连接及相关资源。

      那么是不是我们的服务端该参数的配置为零,没有启用呢?从服务端的配置来看,不是。当前配置值为 10,即10分钟。

bf665658bc2a34f6d8f4997fc6f770a8.png

      该数值小于防火墙断开空闲长连接的阈值,按理来说,有数据包的通信,连接不会被防火墙断开才对,那为什么连接还是会被断开呢?

     网络侧给出了答案:有的防火墙会忽略服务端向客户端发的“探测”包,继续杀空闲的连接。

      自此,确认了即使服务端已经配置 SQLNET.EXPIRE_TIME,TCP 连接仍然会被防火墙关闭。此路不通,无法解决问题。

尝试二:尽可能减小从连接池中获取到无效连接的概率

     既然服务端配置了 SQLNET.EXPIRE_TIME 仍然无法解决问题,那么从客户端能做些什么事情呢?是不是可以通过连接池的配置,尽可能减小从连接池中获取到无效连接的概率呢?

      我们当前的连接字符串是这样的:User ID=***;Password=***;Data Source=***;Connection Lifetime=120; Max Pool Size=20;Min Pool Size=5;

      可以看出,Min Pool Size 的配置为 5。即连接池回收数据库连接时会最少保持 5 个连接。试想,我们如果把该值减小为 1,则可以合理期待连接池会尽可能地回收数据库连接。

      但是,由于连接池固定每 3 分钟回收一次没有使用的连接,也无法确保剩余未被回收的连接是可用的,因此最后我们直接放弃了这个方案。

尝试三:配置连接字符串参数 Validate Connection = true

      不能从服务端解决问题,又无法调整防火墙参数,那只好从客户端解决问题了。

经过查阅 Oracle 官方文档,我们发现了 Validate Connection 这个参数。其目的是使得 Oracle 客户端从连接池里获取连接使用之前,先验证连接的可用性,但是默认值为false。

      这看起来正符合我们现在的问题场景,于是赶紧在连接字符串上加上这段配置。

107a1862e1a162e9fb1e540440f08b6c.png

谁知道,加上之后居然报错了。

0e2f475280b3c5e2b7ef984bcb4e41dd.png

      堆栈信息表明,我们使用了微软的数据库驱动,而不是 Oracle 的 ODP.NET。而这个属性是 ODP.NET 专属的,微软的驱动不支持。这样的话,我们只需要将底层数据库驱动改为 ODP.NET 即可。

      好了,有了解决问题的思路,那按照步骤一步步解决即可。在这里要更换底层数据库的驱动,我们却又遇到系列的插曲:数据库访问层由框架决定,框架又引入了外部闭源组件,那我们如何更换底层驱动呢?

插曲一:添加配置节

      我们先来看看框架的 dll。由于年久失修,框架的 dll 也无法确保源码和生产环境的版本一致了。因此我们只好通过反编译来查看框架的代码。

862d82222b884a8e890b6d394d35e2aa.png

      可以看到,当我们使用 Oracle 时,有一个名为 UserOracleDataAccess 的配置项,如果配置为 true,则会加载 Oracle 的相关库。那这个问题就很简单了,在配置文件中添加配置节即可。

      正当我们准备见证奇迹的时刻,奇迹却并没有发生。我们发现,即使配置了 UserOracleDataAccess = true,报错日志仍然显示加载了 System.Data.OracleClient.dll,继续报 Keyword not supported: ‘validate connection’. 的错误!这是怎么回事呢?

插曲二:去除对微软驱动的强制依赖

看上面反编译出来的代码,无论 UserOracleDataAccess 的配置如何,都会初始化创建 Data.CachedOracleContext 类的实例。继续分析,我们发现了这样的依赖关系:

Data.CachedDataAccess

  └ Data.CachedOracleContext

        └ Data.CachedOracleProvider

            └ LinqToOracle.OracleProvider

 └ System.Data.OracleClient.OracleConnectionStringBuilder

经过按图索骥,我们终于发现了无论如何都会加载微软驱动的地方,见下图。

150a3c3cc7d9b07c12cc3f85e3e69a46.png

      好了,定位到问题所在,那么祭出大杀器,使用 ildasm、ilasm 修改 dll 吧!删掉蓝色方框部分逻辑,不创建System.Data.OracleClient.OracleConnectionStringBuilder 实例!编辑好之后,上线,验证。

插曲三:安装 Oracle 驱动

要做成一件事总是会有意外发生的。正当以为一切都搞定了的时候,才发现我们的环境根本没有安装 Oracle 的驱动。

e1aa797768df68825c8d4834ad68f6f9.png

      很简单,马上去 Oracle 官网,下载 ODP.NET 驱动。下载地址:https://www.oracle.com/database/technologies/dotnet-odacdeploy-downloads.html,根据服务器上安装的客户端版本(11gR2),我们选择下载 ODAC XCopy 的 64-bit ODAC 11.2.0.4.0。安装部署,启动程序,请求验证,没有再报驱动不兼容的问题了。

      最后,经过上述多处变更,我们最后再进行验证,系统未再发生 “ORA-25408: 无法安全重放调用” 报错了。

05

踩坑典型案例

行政班车系统故障

      接下来,我们再来复盘一个更加复杂,涉及面更广的案例。

8月25日傍晚,七夕节,故障爆发

• 18:16,正值下班高峰期,有用户反馈班车应用无法打开,行政其他应用频繁报错,我们立即进行故障定位。

• 18:40,我们定位到班车系统所连接的数据库实例 CPU 占用达到 250%,数据库活动会话 2000+,并且发生了主备切换。

d9a49a5206f7ba156a4aaaf1236bc726.png

      于是我们进行紧急维护,kill 掉了所有数据库会话,重启班车应用,减少容器个数,阻止高频SQL,但实际上故障未能恢复。

• 19:25,不得已,我们停掉了班车服务,此时行政其他系统恢复了正常。

• 19:40,经过一系列的故障分析定位,我们查询班车公告的 SQL 异常,调用耗时超出正常预期 (正常应当为毫秒级,但实际故障现场时该查询的平均耗时居然高达 144 秒)。而该接口已提供给 MOA 和 CSIG 地图团队调用,因此决定回收外部 BG 的调用权限,以期快速恢复系统。

• 19:54,我们拒绝了来自外部的访问,班车系统恢复正常。

自此,看起来问题已经解决了,拒绝了外部访问和系统恢复正常具有因果关系。但事实上真的是这样吗?

8月25日深夜,故障追查

• 20:25,我们继续追查,既然是外部调用拖垮了我们的服务,那到底是谁呢?

8f498470254ac866e0a7fb6b3d8b0b09.png

      通过请网关侧协助,我们拿到了如上图所示的信息,得到一个结论:我们的接口有被外部严重超出预期地高频调用,半小时内峰值高达45万余次。那么到底这个 IP 是哪个业务呢?

8月26日凌晨,回到原点

• 00:09,我们作为直接定位问题的业务团队,由于已经深夜了,我们又没有足够的权限和工具,于是定位外部 BG 的 IP 十分困难。几经周折,我们终于得到了答案,那就是:这个 IP 居然是测试环境的某网关地址!实际上,在追查这个 IP 所属方的过程中,我们发现疑点越来越多了。

      环境匹配:测试环境为什么会调到我们生产环境的接口?

      接口授权:我们接口只公开给了 MOA 和另外一个合作部门,但这个 IP 不是这两个团队的,他们是怎么知道我们接口的地址和 token 的?怎么会来调我们的接口?

      请求统计:网关统计(45W/30m)-> 数据库工具平台统计的慢查询约 1W/h,平均耗时 143s,在数据量级上无法匹配。

      时间分布:网关统计峰值时间在 16:00,与数据库 CPU 取消、慢查询曲线、SQL 总量曲线在时间上均无法匹配。

      经验判断:被调用最多的慢查询,其业务逻辑极简单,数据查询量全表数据量也很少,没有理由成为瓶颈。

• 02:41,我们意识到肯定是哪里出现重大错误了。终于,我们很遗憾地发现,用于分析问题的第一手材料,我们十分信赖的原始依据,由于一个小小的人为原因,失真了。原本以为我们的接口被外部高频调用,但实际上网关侧查询的结果却是“整个网关”的调用情况,而不是我们的接口情况。得知这一情况时,所有人都意识到,一整晚的猜想、分析、诊断,都是无根之水,无缘之木,我们回到了问题的原点。

8月26日,寻找第一片雪花

      通过观察和对比 CPU利用率、活跃连接数、SQL 总数的曲线,我们定位为这是一次典型的雪崩效应,上文提到的班车公告查询并不是主因,它也是受害者,是雪球外部的表现。于是接下来,我们需要降低 CPU 的峰值,找到引起雪崩的第一片雪花。

• 03:00,不得已,我们开始请求腾讯云的协助。

• 10:00,与此同时,我们也进行了紧急的维护,包括SQL性能优化,配置应用的数据库连接池最大连接数,申请 TDSQL 实例扩容等等。

• 14:13,午休之后,大量的人员查询和预订会议室,会议室系统发出性能预警,出现慢查询。

• 18:11,下班之后,班车系统再次出现慢查询预警。同时,我们可以观察到周期性的CPU峰值毛刺发生在整点十几分,由于行政领域的不同应用共用了同一个数据库实例,于是我们对整个政领域的所有应用进行全面排查,却并未找到周期为一小时的定时任务。在这里我们进一步看出,由于 TDSQL 实例扩容还没有真实实施,CPU 的周期性峰值每一次都超过了 100%,如果不解决这个问题,那系统一直都处于走钢丝的悬崖上,随时都可能不可用。

• 21:30,腾讯云上的 TDSQL 实例扩容终于完成,CPU 周期性峰值从 100% 降低到了 18%。

经验总结

      以上,我们分享了这次上云过程中遇到的问题踩过的坑。回过头来看,我们认为是一次有难度、有策略、有爬坑也有成果的体验。

bb8d05cf1a194b04987b0dc400a9f1c8.png

综合来看,有如下几个方面的总结:

bd86917801a871c430a9f548161b23f6.png

      以上,便是这次上云踩坑之旅的总结,经过披荆斩棘,我们终于抵达云端乘风而行。作为踩坑实战,这里并未描述上云应有的最佳实践,仅作为一家之言,以飨后来者,希望对后续的上云工作,提供借鉴意义。

3e92b522771a885410336a88ca5a1e97.gif

你们点点“分享”,给我充点儿电吧~

今天的文章web项目上云_披荆斩棘向云端 — 职能业务上云踩坑实战分享到此就结束了,感谢您的阅读。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
如需转载请保留出处:https://bianchenghao.cn/67720.html

(0)
编程小号编程小号

相关推荐

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注