关于架构设计:工作十年在腾讯沉淀的高可用系统架构设计经验

113次阅读

共计 6376 个字符,预计需要花费 16 分钟才能阅读完成。

👉腾小云导读

在零碎的开发过程中,很多开发者都为了实现零碎的高可用性而发愁。本文从研发标准层面、应用服务层面、存储层面、产品层面、运维部署层面、异样应急层面这六大层面去分析一个高可用零碎的架构设计须要有哪些要害的设计和思考。心愿腾讯的教训办法,可能给宽广开发者提供参考。内容较长,您能够珍藏后继续浏览。

👉看目录点珍藏,随时涨技术

1 高可用零碎的架构设计思维

1.1 可用性和高可用概念

1.2 高可用零碎设计思维

2 研发标准层面

2.1 方案设计和编码标准

2.2 容量布局和评估

2.3 QPS 预估(漏斗型)

3 应用服务层面

3.1 无状态和负载平衡设计

3.2 弹性扩缩容设计

3.3 异步解耦和削峰设计(音讯队列)

3.4 故障和容错设计

3.5 过载爱护设计(限流、熔断、降级)

4 存储层面

4.1 集群存储(集中式存储)

4.2 分布式存储

5 产品层面

6 运维部署层面

6.1 开发阶段 - 灰度公布、接口测试设计

6.2 开发阶段 - 监控告警设计

6.3 开发阶段 - 安全性、防攻打设计

6.4 部署阶段 - 多机房部署(容灾设计)

6.5 线上运行阶段 - 故障演练(混沌试验)

6.6 线上运行阶段 - 接口拨测系列设计

7 异样应急层面

01、高可用零碎的架构设计思维

1.1 可用性和高可用概念

可用性是一个能够量化的指标,是指在某个考查工夫,零碎可能失常运行的概率或工夫占有率期望值。行业内个别用几个 9 示意可用性指标,对利用的可用性水平个别衡量标准有三个 9 到五个 9。个别咱们的零碎至多要到 4 个 9(99.99%)的可用性能力谈得上高可用。

高可用 High Availability 的定义(From 维基百科):

高可用是 IT 术语,指零碎无中断地执行其性能的能力,代表零碎的可用性水平,是进行零碎设计时的准则之一。服务不可能 100% 可用,因而要进步咱们的高可用,就要尽最大可能的去减少咱们服务的可用性,进步可用性指标。

一句话来表述就是:高可用就是让咱们的服务在任何状况下,都尽最大可能地可能对外提供服务。

2.2 高可用零碎设计思维

高可用零碎的架构设计,须要有一套比拟迷信的工程治理套路。要从产品、开发、运维、基建等全方位去考量和设计。高可用零碎的架构设计思维包含但不限于

  • 做好研发标准。零碎都是研发人员设计和编码写进去的,因而首先要对研发层面有一个标准和规范。
  • 做好容量布局和评估。次要是让开发人员对系统要抗住的量级有一个根本认知,不便进行正当的架构设计和演进。
  • 做好服务层面的高可用。次要是负载平衡、弹性扩缩容、异步解耦、故障容错、过载爱护等。
  • 做好存储层面的高可用。次要是冗余备份(热备,冷备)、生效转移(确认,转移,复原)等。
  • 做好运维层面的高可用。次要是公布测试、监控告警、容灾、故障演练等。
  • 做好产品层面的高可用。次要是兜底策略等。
  • 做好应急预案。次要是要思考在呈现问题后怎么疾速复原,不至于让咱们的异样事态扩充。

02、研发标准层面

2.1 方案设计和编码标准

研发标准层面是大家容易漠视的一个点。然而咱们所有的设计,都是研发人员来实现的,包含从设计文档到编码再到公布上线。因而,研发层面也要有一个标准流程和套路,以让咱们更好地去研发和保护一个高可用的零碎:

2.2 容量布局和评估

  • 容量评估:

是指须要评估好在做的这个零碎是为了应答一个什么体量的业务、这个业务申请量的平均值、顶峰的峰值大略都在一个什么级别。

如果是新零碎,那么就须要先收集产品和经营共事对业务的大体预估,开发者依据他们给的数据再进行具体评估。如果是老零碎,那么就能够依据历史数据来评估。评估的时候,要从一个整体角度来看全局的量级,而后再细化到每个子业务模块要承载的量级。

  • 容量布局:

是指零碎在设计的时候,就要可能初步布局好零碎大抵可能维持的量级,比方是十万级还是百万级别的申请量,或者更多。不同量级对应的零碎架构设计齐全不一样。尤其到了千万、亿级别的量级的时候,架构设计会有更多的考量。

这里值得注意的是,不须要在一开始就设计出远超以后业务实在流量的零碎,要依据业务理论状况来设计。同时,容量布局还波及到:零碎上下游的各个模块、依赖的存储、依赖的三方服务别离须要多少资源,须要有一个绝对可量化的数据。容量布局阶段更多是要依附本身和团队的教训,比方要理解零碎的 log 的性能、redis 的性能、rpc 接口的性能、服务化框架的性能等等,而后依据各种组件的性能来综合评估曾经设计的零碎的整体性能状况。

容量评估和容量布局之后,还须要做就是性能压测。最好是可能做到全链路压测。

性能压测的目标是确保零碎的容量布局是否精确。假如设计的这个零碎,布局的是可能抗千万级别的申请。那么实际上,真的可能抗住吗?在上线之前首先要依据教训来判断,其次是肯定要通过性能压测得出精确论断。性能压测要关注的指标很多,然而重点要关注的是两个指标:一个是 QPS,一个是响应耗时要确保压测的后果合乎预期

压测的步骤:能够先分模块独自压测。最初如果状况容许,那么最好执行全链路压测。

2.3 QPS 预估(漏斗型)

QPS 预估(漏斗型)指的是:一个实在的申请过去后,从接入层开始别离通过了整个零碎的哪些层级、哪些模块,每一个层级的 QPS 的量级别离有多少。

从申请链路上来看,层级越往下,上游层级的量级就会越少。因为每通过一个层级,都有可能会被各种条件过滤掉一部分申请。例如进入流动页后查看商品详情而后下单这个例子,首先进入流动页,所有的申请都会进入拜访。而后只会有局部用户查问商品详情。最初查看商品详情的这些用户又只会有局部用户会下单。这里就会有一个漏斗,所以从下层模块到上层模块的量级肯定是逐渐缩小的。

QPS 预估(漏斗型)须要开发者依照申请的层面和模块,来构建预估漏斗模型,而后预估好每一个层级的量级。包含但不限于从服务、接口、分布式缓存等各个层面来预估,最初形成残缺的 QPS 漏斗模型。

03、应用服务层面

3.1 无状态和负载平衡设计

要做到零碎的高可用,个别应用服务的惯例设计都是无状态的。这也就意味着,开发者能够部署多个实例来进步零碎的可用性。而这多个实例之间的流量调配,就须要依赖零碎的负载平衡能力。「无状态 + 负载平衡」既能够让零碎进步并发能力,也能够进步零碎的可用性。

如果开发者的业务服务应用的是各种微服务框架,那么大概率在这个微服务框架外面就蕴含了服务发现和负载平衡的能力。这一整套流程包含:服务注册和发现、负载平衡、衰弱状态检查和主动剔除。当零碎的任何一个服务实例呈现故障后,它会被主动剔除掉。当零碎有新增一个服务实例后,它会被会主动增加进来提供服务。

如果大家不是应用的微服务框架来开发的,那么就须要依赖负载平衡的代理服务,例如 LVS、Nginx 来帮零碎实现负载平衡。当然,腾讯云的 CLB 负载平衡也反对亿级连贯和千万级并发,各位感兴趣的话可自行搜寻理解。

3.2 弹性扩缩容设计

弹性扩缩容设计是应答突峰流量的十分无效的伎俩之一,同时也是保障系统服务可用性的必要伎俩。弹性扩缩容针对的是零碎无状态的应用服务而言的。服务是无状态的,因而能够随时依据申请量的大小来进行扩缩容,流量大就扩容来应答大量申请,流量小的时候就缩容缩小资源占用。

怎么实现弹性扩缩容呢? 现阶段都是云原生时代,大部分的公司都是采纳容器化(K8s)部署,那么基于这个状况的话,弹性扩缩容就非常容易了,只须要配置好 K8s 的弹性条件就能主动依据 CPU 的使用率来实现。

如果不是容器化部署,是物理机部署的形式,那么要做到弹性扩缩容,必须要有一个公司外部的根底建设能力、可能在经营平台上针对服务的 CPU 或者 QPS 进行监控。如果超过肯定的比例就主动扩缩容,就和 K8s 的弹性原理是一样的,只是须要自行实现。

3.3 异步解耦和削峰设计(音讯队列)

要想零碎可能高可用? 从架构层面来说,要做到分层、分模块来设计。而分层分模块之后各个模块之间,还能够进行异步解决、解耦解决。目标是为了不相互影响,通过异步和解耦能够使零碎的架构大大的晋升可用性。

架构层面的异步解耦形式就是采纳音讯队列(比方常见的 Kafka),并且同时音讯队列还有削峰的作用,这两者都能够进步零碎的架构可用性:

采纳音讯队列之后,能够把同步的流程转换为异步的流程,音讯生成者和消费者都只须要和音讯队列进行交互。这样不仅做了异步解决,还将音讯生成者和消费者进行了隔离。

3.4 故障和容错设计

任何服务,肯定会存在失败的状况,不可能有 100% 的可用性。服务在线上运行过程中,总会遇到各种各样意想不到的问题会让服务呈现情况,因而业界来评估可用性 SLA 都是说多少个 9,例如 4 个 9(99.99%)的可用性。

为此,个别设计倡议遵循「design for failure」的设计准则,设计出一套可容错的零碎。须要做到尽早返回、主动修复,细节如下:

3.5 过载爱护设计(限流、熔断、降级)

零碎无奈高可用的一个重要起因就在于:零碎常常会有突发的流量到来,导致服务超载运行。这个时候首先要做的是疾速扩容,并且开发者当时就要预留好肯定的冗余。另外一个状况下,就算扩容了,然而还是会超载。例如超过了上游依赖的存储的最大容量、或者超过了上游依赖的三方服务的最大容量。

那么这个时候,零碎就须要执行过载爱护策略了,次要包含限流、熔断、降级,过载爱护是为了保障服务局部可用,不至于导致整个服务齐全不可用。

熔断和降级这两个策略虽有些类似,字面的意思都是要疾速拒绝请求。然而却是两个维度的设计:降级的目标是应答零碎本身的故障,而熔断的目标是应答零碎依赖的内部服务故障。

04、存储层面

以后的互联网时代,应用服务根本都是无状态的。因而应用服务的高可用相对来说会比较简单。然而数据存储的高可用相对来说,会简单很多。因为数据是有状态的,那具体开发者要怎么保障数据存储的高可用。下文一起来剖析下。

存储层面的高可用计划实质是通过数据的冗余来实现,将数据复制到多个存储介质外面,能够无效的防止数据失落,同时还能够进步并发能力。因为数据是有状态的,这里会比服务的高可用要简单很多。

常见的解决存储高可用的计划有两种:集群存储和分布式存储。业界大多是围绕这些来构建,或者是做相干衍生和扩大。上面开展解说。

4.1 集群存储(集中式存储)

集群存储是指由若干个「通用存储设备」组成的用于存储的集群。组成集群存储的每个存储系统的性能和容量均可通过「集群」的形式得以叠加和扩大。

集群存储适宜业务存储量规模个别的场景,惯例的业务数据存储个别都是集群存储形式就足够了。当初个别业务数据存储的应用默认都是集群形式。比方 Redis、MySQL 等存储类型。个别中大型互联网公司默认是集群存储的形式。

集群存储就是常说的「1 主多备」或者「1 主多从」的架构。写数据通过主机,读数据个别通过从机。集群存储次要须要思考如下几个问题:

4.2 分布式存储

分布式是指将不同的业务散布在不同的节点。分布式中的每一个节点,都能够做集群。

「分布式存储系统」是将数据扩散存储在多台独立的设施上。传统的网络存储系统采纳集中的存储服务器寄存所有数据,存储服务器成为零碎性能的瓶颈,也是可靠性和安全性的焦点,不能满足大规模存储利用的须要。

分布式网络存储系统采纳可扩大的系统结构,利用多台存储服务器分担存储负荷,利用地位服务器定位存储信息。它岂但进步了零碎的可靠性、可用性和存取效率,还易于扩大。

分布式存储适宜十分大规模的数据存储,业务数据量微小的场景能够采纳这种形式。常见的分布式存储比方 COS、GooseFS、Hadoop(HDFS)、HBase、Elasticsearch 等。

05、产品层面

产品层面的高可用架构解决方案,基本上就是指兜底产品策略。降级 / 限流的策略,更多的是从后端的业务服务和架构上的设计来思考相干解决方案。这里说的兜底策略也可叫做「柔性降级策略」,更多的则是通过产品层面上来思考。上面举几个例子:

06、运维部署层面

6.1 开发阶段 - 灰度公布、接口测试设计

灰度公布、接口测试、接口拨测系列设计包含但不限于:

  • 灰度公布:

服务公布上线的时候,要有一个灰度的过程。先灰度 1-2 个服务实例,而后逐渐放量察看。如果所有 ok,再逐渐灰度,直到所有实例公布结束。

  • 接口测试:

每次服务公布上线的时候,服务提供的各种接口,都要有接口测试用例。接口测试用例测试通过后,服务能力公布上线。这样目标是为了查看零碎对外提供的接口是否可能失常运行,防止服务公布后才发现有问题。

灰度公布和接口测试,个别在大公司外面会有相干的 DevOps 流程来保障。

6.2 开发阶段 - 监控告警设计

监控告警的设计,对局部大公司来说不是问题。因为肯定会有一些比拟专门的人去做这种根底能力的建设,会有对应的配套零碎,业务开发者只须要配置或应用即可。

那如果公司外部没有相干根底建设,就须要开发者别离来接入对应的零碎,或者间接接入一些指标、链路、日志、事件等多数据反对、更加一体化的监控平台,比方腾讯云可观测平台。

6.3 开发阶段 - 安全性、防攻打设计

安全性、防攻打设计的目标是为了防刷、防黑产、防黑客,防止被内部歹意攻打。个别有两个策略:

  • 在公司级别的流量入口做好对立的防刷和鉴权的能力,例如在对立接入层做好封装。

  • 在业务服务外部,做好相干的业务鉴权,比方登录态信息、例如减少业务鉴权的逻辑。

6.4 部署阶段 - 多机房部署(容灾设计)

个别的高可用策略,都是针对一个机房内的服务层面来设计的,然而如果整个机房都不可用了,例如地震、火灾、光纤挖断等状况怎么办?这就须要零碎的服务和存储可能进行容灾了。容灾的常见计划就是多机房部署。

条件不容许的状况下,保障多机房部署业务服务就能够了。

6.5 线上运行阶段 - 故障演练(混沌试验)

故障演练在大公司是一个常见的伎俩。在业界,Netflix 早在 2010 年就构建了混沌试验工具 Chaos Monkey。混沌试验工程对于晋升简单分布式系统的健壮性和可靠性施展了重要作用。

简略的故障演练就是模仿机房断电、断网、服务挂掉等场景,而后看整个零碎运行是否失常。零碎就要参考混沌试验工程来进行具体的布局和设计,这个是一个绝对较大的工程、成果较好,然而须要有大量人力去开发这种根底建设。

6.6 线上运行阶段 - 接口拨测系列设计

接口拨测和巡检相似,就是服务上线后,每隔一个固定工夫(比方 5s)调用后端的各种接口,如果接口异样则进行告警。

针对接口拨测,个别也会有相干配套设施来提供相干的能力去实现。如果没有提供,那么开发者能够写一个接口拨测(巡检)的服务,定期去调用重要的接口。

07、异样应急层面

即便后面做了很多保障,也不肯定招架住线上的各种异常情况。如果真出问题让零碎的服务异样、无奈提供服务,开发者还有最初一根救命稻草——那就是应急预案,将服务异样的损失升高到最小。

应急预案是须要开发者当时布局好,业务零碎在各个层级呈现问题后第一工夫怎么复原,并制订好相干规定和流程。当出现异常情况后能够依照既有的流程去执行。这样避免出现问题后慌手慌脚导致事态扩充。

最初,咱们整顿出本文的思维导图如上,供各位参考。总体来说,咱们从研发标准层面、应用服务层面、存储层面、产品层面、运维部署层面、异样应急层面这六大层面,分析了一个高可用零碎的架构设计须要有哪些要害的设计和思考。

以上便是本次分享的全部内容,如果您感觉内容有用,欢送点赞、珍藏,把内容分享给更多开发者。

-End-

原创作者|吴德宝

技术责编|吴德宝

腾小云福利来也💐

扫码一键支付 「腾讯云开发者 - 秋季限定红包封面」

最近微信改版啦,有粉丝反馈收不到小云的文章🥹。

请关注「腾讯云开发者」并 点亮星标

周一三晚 8 点 和小云一起 涨(领)技 (福) 术(利)

你可能感兴趣的腾讯工程师作品

| 编程语言 70 年:谁是世界上最好的编程语言?

| 腾讯工程师聊 ChatGPT 技术「文集」

| 一文揭秘微信游戏举荐零碎

| 微信全文搜寻耗时降 94%?咱们用了这种计划

技术盲盒:前端|后端|AI 与算法|运维|工程师文化

正文完
 0