搞定系统设计:面试敲开大厂的门
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

1.8 无状态网络层

现在是时候考虑横向扩展网络层了。为此,我们需要将状态(例如,用户会话数据)从网络层中移出。一个好的做法是将会话数据存储在持久性存储(如关系型数据库或NoSQL)中。集群中的每个Web服务器都可以经由数据库访问状态数据。这就是所谓的无状态网络层。

1.8.1 有状态架构

有状态的和无状态的服务器是有一些关键差异的。有状态的服务器处理客户端发来的一个个请求,并记下客户端的数据(状态)。无状态的服务器则不保存状态信息。

图1-12展示了一个有状态架构。

图1-12

在图1-12所示的架构中,用户A的会话数据和个人资料图片会被存储到服务器1上。为了对用户A进行身份验证,必须将HTTP请求发给服务器1。如果将请求发给其他服务器,比如服务器2,由于服务器2上没有用户A的会话数据,因此身份验证就会失败。同理,用户B的所有HTTP请求必须发给服务器2;用户C的所有请求必须发给服务器3。

现在的问题是,如何将来自同一客户端的所有请求都发给同一个服务器。大部分负载均衡器都提供的黏性会话[7]可以解决这个问题,但是会增加成本。这种方法使得添加或者移除服务器变得更加困难,同时也使得应对服务器故障变得更具挑战性。

1.8.2 无状态架构

图1-13展示了一个无状态架构。

在这个无状态架构中,用户的HTTP请求可以发给任意Web服务器,然后Web服务器从共享的数据存储中拉取数据。状态数据存储在共享数据存储而非Web服务器中。无状态的系统更加简单,更健壮,也更容易扩展。

图1-14展示了加入了无状态网络层后的系统设计。

图1-13

图1-14

如图1-14所示,我们把会话数据从网络层中移出,放到持久化存储中保存。共享数据存储可以是关系型数据库或者NoSQL(比如,Memcached、Redis)。选择NoSQL的原因是它容易扩展。自动扩展的意思是,基于网络流量自动地增加或者减少Web服务器。将状态数据从Web服务器中移除后,就很容易实现网络层的自动扩展了。

如果你的网站发展迅速,而且吸引了非常多的国际用户,要提高可用性以及在更广的地理区域提供更好的用户体验,让网站支持多数据中心就非常关键。