大型网站的演化之路——读《大型网站技术架构》
author:姚毛毛的博客 & 妖生
01 大型网站or软件有什么特点?
高并发、大流量,微信都日活10亿了
7×24的高可用,俗称的4个9(99.99%)
海量数据的存储与管理
全国甚至全球的用户分布,复杂网络
安全环境很差
需求变更频繁,需要快速迭代
最后,是渐进式的发展。
所有大型网站都是从一个小网站发展起来的。
好的网站与复杂的架构都是演化来的,而不是一开始就设计好的。
当年才出发的时候,谁也想不到微信可以日活十亿,最初的时候肯定也没有成千上万的服务器集群对不对。
02 最初与第一次的演化之路:应用与数据的分离
我们最初的小型网站是什么样的?
从逻辑上看,一个应用服务、一个数据库;从物理上看,一台服务器就搞定了。
在用户量增多后,我们开始需要将应用跟数据库分离。
那应用跟数据库所需要的服务器配置是一样的吗?
当然是NO。
应用需要处理更多的业务逻辑,所以需要好一点多一点的CPU。
数据库则要快速检索磁盘跟放置数据缓存,因此需要快一点的磁盘和大一点的内存。
当然,所有演进的目的都是想更高、更快、更强。只是有时候没法做到面面俱到,需要取舍。
03 第二次演进:缓存优化
恭喜你,网站优化了一次,体验变好了,用户也开始增多了,可是烦恼的又来了。
用户的增多,带来的数据库压力也大了,怎么办?
在IT行业甚至所有现实模型中都存在一个颠扑不破的真理,即二八原则。
在网站访问上也是如此,80%的业务访问总是集中在20%的数据上。
淘宝买东西就翻前面那么一点,淘宝已经为我们找好了信用好、成交量高的卖家;百度一下也就是翻前面那两三页,甚至一页里的前几条(如果没有广告的话);微博热搜吃瓜也就看前十吧,后面的你会一个个点过去吗?
那么,把这20%的数据缓存起来,是不是就可以减少数据库的访问压力,提高网站访问性能了?
YES。
那么,怎么缓存呢?
我们通常使用的缓存方案有两种,即应用服务器上的本地缓存,和独立的分布式缓存。
有什么优缺点?
本地缓存速度快些,但是受限于应用服务器的内存,且会导致与应用争用的情况。
独立的分布式缓存可以使用集群,速度稍慢,但也很快,基本只有网络IO的消耗;但是缺点就一个字:贵。因为需要购买独立的缓存服务器。
所以在现实中,有时候,我们有时并不会购买独立的缓存服务器,而是放在大内存的应用或数据库服务器上,设置好阈值,共用内存。
04 第三次演进:应用集群与数据库的集群和读写分离
哇,用了缓存后,访问数据好快啊。
可是用户又增多了,应用支撑不过来了怎么办?真是幸福的烦恼啊。
单台数据库是不是有宕机的危险啊?
唉,集群呗。花钱就完事了。
应用集群、数据库集群。
这也是我们当今的软件架构中最常用的部署方案。
通过负责均衡调度器(nginx、F5等),可以将用户请求通过轮询或者IP指定的方式,分发到应用服务器集群中的任意一台服务器上,缓解应用压力。
而数据库以Oracle为例,则是可以在生产服务器上安装RAC版本,而应用可以通过访问数据库的VIP(Virtual IP),或者JDBC集群访问的方式访问数据库。
但是在网站的应用开发中,则一般选择mysql的较多。虽然淘宝早期也是使用了Oracle,但是后期也转mysql了。
至于为什么?
呵呵,一个字,贵。两个字,很贵。三个字,太贵了。
集群的好处有两个:1、缓解服务压力;2、高可用,其中一台坏了,另一台还可以继续使用,给你恢复服务的机会。
一般软件演化到这里就完事了。
但是网站有个不一样的地方,很多时候,都是读多写少。
点赞的、吃瓜的比上场评论的少很多对吧?
而读多的情况虽然通过缓存配置消化了一部分,但还是有一部分读操作(缓存未命中、缓存过期)和全部的写操作会访问数据库。
所以在你的用户量又迅猛增加到一定规模时,又是数据库成为了我们的瓶颈。
目前大部分数据库都是支持主从热备功能的,主数据库通过主从复制机制将数据更新同步到从数据库。
此时我们的应用就可以建设专门的读、写数据库的访问模块,使数据库读写分离对应用透明。
有时我们甚至会将专门的查询模块剥离出来,成为另一个子系统。
05 不算演进的第四次演进:CDN与反向代理
为什么要做CDN?
移动、电信、联通……,华东、华南、西南、西北……,网络环境复杂,每个地区访问网站的速度都不太一样。
CDN跟反向代理是加速访问的一种手段,它们的基本原理都是缓存。
区别是CDN部署在网络厂商的机房,反向代理是部署在网站机房。
CDN跟反向的目的都是尽早返回数据给用户。
06 三国演义式的第五次演进:分布式演进、业务的拆分与合并
分布式数据库是一种最后手段,只有在单表数据非常庞大的时候才使用。
很多网站和软件根本用不到这一步,分布式数据库会带来更麻烦的复杂性。
网站更常用的手段是拆分业务,拆分不同的业务应用,拆分不同的业务库,部署在不同的物理服务器上。
这一招,在围棋上,叫分治。在三国里,叫合久必分。
以商城网站为例,可以将首页、店铺、订单、卖家、买家拆分不同的产品线,这其中不同的产品线又可以拆分多个应用,分归不同的业务团队管理。
应用之间可以通过首页超链接建立关系,也可以通过消息队列进行数据分发,当然,最多的还是访问同一个数据存储系统,来构成一个完整的系统。
这叫微服务。
随着业务拆分越来越小,应用越来越复杂,其中又出现了一些可以共用的服务。如用户管理、商品管理,那么就可以将这些共用的业务提取出来,独立部署。
用现在流行的话来说,叫业务中台。
在技术上,大家又造了各种各样的轮子,解决的问题其实有很多共性。例如文件、图片的处理、数据的存储与搜索系统。
技术中台也有了。
在数据上,大家的系统因为拆分的愈来愈零碎,存储到了不同的数据库中,又形成了一个个数据孤岛。把这些打通,做成数据仓库,分析用户画像岂不美哉?优惠券推送、大数据杀熟了解一下。
而在技术上,随着数据越来越多,数据存储和检索的技术需求也越来越高。所以我们又会引用一些非关系型的技术如NoSQL、搜索引擎等等。
最后,数据中台也有了。
所谓分久必合,新三国成型了。
欢迎关注我的公众号:姚毛毛的博客
这里有我的编程生涯感悟与总结,有Java、Linux、Oracle、mysql的相关技术,有工作中进行的架构设计实践和读书理论,有JVM、Linux、数据库的性能调优,有……
有技术,有情怀,有温度
欢迎关注我:姚毛毛& 妖生