架构基础:从需求到架构
上QQ阅读APP看书,第一时间看更新

2.1.6 异地多活架构设计

两地三中心容灾设计带来极大的浪费,并且没有解决访问效率问题。两个可用的数据中心都部署在同一个城市或相邻的城市,例如,服务器部署在北京,则只有华北、华中等周边地区访问速度较快,而华南地区、海外地区访问速度较慢。

因此,最好的架构应该是异地多活架构,就是全国乃至全球部署数据中心,这些数据中心同时对外提供服务,让不同地区的用户访问距离他们最近的数据中心。但是,部署成本极高,并且技术复杂,资金和人员投入巨大。

例如,分别设立北京、上海、香港数据中心,通过域名解析将不同地区的用户请求分发到不同的数据中心,如图2-17所示。

图2-17 异地多活架构

异地双活是异地多活的特例,是指在两个距离较远的城市建立IDC(Internet Data Center,互联网数据中心),同时对外提供服务。

异地多活架构主要存在以下两个问题。

(1)跨数据中心访问,导致处理速度慢。用户的一次请求,对于分布式系统,可能在服务器发生数十次的调用,如果这些调用不能发生在同一个IDC内,延迟就会较高。

例如,某北京用户的一次购买行为,服务器需要200个服务调用完成,如果这200次调用全部在北京IDC内完成,每次调用耗时2毫秒,则全部串行化总计需要200×2=400(毫秒)给用户应答。如果这200次调用中有100次发生在北京IDC内,每次调用耗时2毫秒,另外有100次发生在上海IDC内(发生跨IDC调用),每次调用耗时20毫秒,则全部串行化总计需要(100×2+100×20)/1000=2.2(秒)给用户应答,会造成极差的用户体验,甚至有些页面直接超时,如图2-18所示。

所以,异地多活的第一个要求就是尽量让所有的交易发生在同一个IDC内,避免出现跨区访问。

图2-18 一个IDC内完成与跨IDC调用的对比

(2)数据无法实时同步。由于各个IDC的距离较远,网络延迟是无法避免的,因此数据无法达到实时复制。如果不进行特殊的控制,则会产生很严重的不一致性问题。

例如,某用户购买商品时,交易是在北京机房完成,订单数据也存储在北京机房内。紧接着用户去查看订单信息,这时请求到了上海机房,而此时数据还未同步过来,就会导致用户无法看到订单,这是用户无法容忍的错误。

为了解决数据同步延迟问题,最简单的方式就是数据库不拆分也不同步,都集中在一个IDC中,多个IDC中的服务共享一套数据源,即伪异地多活架构,如图2-19所示。

图2-19 伪异地多活架构

每个IDC中除数据库外均正常部署,所有服务都对一个数据源(并非一个数据库)进行读写。这样就保证了数据的一致性。这种方式部署实现相对简单,但是数据库压力过大,并且跨区访问时由于数据库远程访问,依然会造成交易效率很低。这种方案依然只适合多个IDC同城或邻城部署,因此通常作为异地多活的一种过渡方案。

真正的异地多活架构则是数据库都是完全独立拆分部署的,通过同步的方式进行数据同步,但是复制延迟是无法避免的,因此这个问题无须纠结(因为现代的通信技术还无法彻底解决长距离数据传输的延迟问题)。所以,异地多活架构并不是将所有业务都进行异地部署,对于一些账户余额、转账等一致性、实时性要求极高的业务并不适合,而且对于一些非常用的交易也没有必要进行异地多活设计。例如,登录操作是使用极其频繁的,用户可能一天要登录10次,而用户信息修改可能一个月才修改1次,并且用户登录十分重要,是一切业务的起点,而用户信息修改并不重要。

用户的位置几乎是固定的,不会出现现在在北京登录,而10分钟之后在上海登录。所以,对于登录业务、用户注册、产品订单等数据只需要异步复制到其他IDC即可,达到最终的数据一致性。

所以,将同一个地区的用户交易控制在一个IDC内,数据存储在一个IDC内,再将数据异步复制到其他IDC是一种较好的方案。