5分钟了解系统架构设计(3)

最近梳理了之前学习的架构设计相关的一些课程学习总结,将其整理成了一个大纲脑图,以每篇5分钟系列展现出来,希望对你有所帮助。本篇,我们聚焦如何在面试中回答架构设

最近梳理了之前学习的架构设计相关的一些课程学习总结,将其整理成了一个大纲脑图,以每篇5分钟系列展现出来,希望对你有所帮助。

本篇,我们聚焦如何在面试中回答架构设计。

其实,关于架构设计的问题,我们只需要做到立足于点、连接成线 和 扩散成面

下面,我们以一个典型案例来看看,如何基于这个套路来回答。

典型案例

在电商中,当用户发表一条商品评论,后台的逻辑是点评系统会调用一系列的远程 API 接口,如调用风控系统、广告系统、消息系统……几个甚至十几个系统的接口。

在业务建设之初,考虑到快速开发与上线,商品评论发布是通过同步 RPC(Remote Procedure Call,远程过程调用)远程调用各系统接口完成的。这种方式在系统少、逻辑简单的阶段很符合实际情况的设计。

但随着业务快速发展,通过 RPC 同步调用的问题逐渐暴露出来。由于过多地依赖其他系统,导致评论发布的接口性能很低,可用性也容易受到其他系统影响。而且每当点评系统需求上线时,其他系统都需要跟着进行联调测试,导致需求迭代速度缓慢。

问题来了

你会如何做架构设计改造?为什么?

回答示例

回答套路:

四个层面,缺一不可。

一谈复杂来源,二谈解决方案,三谈评估标准,四说技术实现。

示例回答:

(1)复杂来源

互联网软件通常分为功能性的复杂度和非功能性的复杂度两种。从功能性复杂度来看产品业务发展快速、系统越来越多、协作效率越来越低,其问题根源就在于各业务子系统强耦合。于是我们引入了MQ来解耦各个子系统,这是系统业务领域带来的本质复杂度,解决的是业务系统效率的问题。从非功能性复杂度来看基于现有的TPS/QPS需求(假设目前峰值TPS=44,QPS=460)结合考虑业务规模发展的前提(假设未来业务预估峰值为目前峰值的4倍),点评消息队列系统的TPS为176,QPS为1840,这个量级的数据意味着并不需要设计高性能架构方案。基于现有可用性问题的考量,假设点评系统的MQ挂掉,将导致用户评论失败,在用户体验层面虽然可以提示用户重新操作,但是如果问题影响到了点评消息的读取导致评论没有走风控策略,就会造成严重的的影响。所以高可用性是点评消息系统的复杂度之一,点评的写入、存储和读取,都需要保证高可用性。综合来看点评系统改造的复杂度在于 功能性复杂度(即要解决业务发展带来的系统耦合 和 开发效率缓慢 的问题)以及 非功能性复杂度(即要保证系统的高可用性)。

(2)解决方案

一般会设计两个到三个备选方案,通过考虑不同的技术方式解决问题,从而确定技术的可行性和优缺点。

方案一:采用开源的MQ消息管道

  • RocketMQ、RabbitMQ、Kafka 等等,结合实际场景和开源MQ优缺点选用

  • 优点是开源MQ解决方案比较成熟引入方便

  • 缺点是引入了一个消息中间件带来了额外的运维成本

方案二:采用开源的Redis实现消息队列

  • 基于轻量级的Redis实现

  • 优点是降低了系统的维护成本(方案一的缺点)和实现复杂度

  • 缺点是仍然引入了一个缓存系统同样存在额外的运维成本

方案三:采用内存队列+MySQL来实现

  • 基于内存队列的方式,异步持久化到MySQL数据库

  • 优点是没有引入额外的中间件,从而不存在维护成本

  • 缺点是不容易实现降级 和 水平扩展

(3)评估标准

通常来说,方案没有优劣之分,而是要看哪个更适合当下的问题,只要架构满足一定时期内的业务发展就可以。

从点评系统的功能复杂度(系统耦合 + 协作/研发效率低)来看

本质上是解决随着业务发展所带来的系统开发效率问题,需要架构师以部门负责人的视角,考虑现有研发团队的能力素质、IT成本、资源投入周期等因素是否匹配设计的三种方案。

从点评系统的非功能性复杂度(高可用性)来看

为了解决系统高可用性,通常需要参考三个原则:

  • 一是系统无单点原则:三种方案都满足;

  • 二是可水平扩展原则:方案三需要做分库分表的开发改造,还需要根据业务提前考虑未来的容量预估;

  • 三是可降级原则:方案三在一般情况下是不可降级的;

常见的解决手段主要有三种:

  • 限流:抛弃超出预期流量外的用户请求;

  • 降级:抛弃部分不重要的功能,让系统提供有损服务,确保系统核心功能不受影响,比如商品详情页不展示宝贝收藏的数量;

  • 熔断:抛弃对故障系统的调用,一般情况下熔断会伴随着降级处理,比如展示兜底数据;

(4)技术实现

在确定了具体的架构解决方案之后,需要进一步说明技术上的落地实现方式和深层原理。

假设最终采用基于Redis来实现消息队列,实现方式有哪些,各自的优缺点又有哪些?

比如:基于Redis List的LPUSH和RPOP的实现方式

又比如:基于Redis的发布订阅模式

又比如:基于Redis的有序集合(Sorted Set)的实现方式

有关Redis相关的内容可以参考我的这一篇:Redis核心技术与实战学习总结

参考资料

李运华,《从0开始学架构》

刘海丰,《架构设计面试精讲》

潘新宇,《23讲搞定后台架构实战》