本文是《大型网站技术架构:核心原理与案例分析》的学习笔记
网站架构模式
什么是网站架构模式
模式,这个来自建筑学的词汇的定义是:“每个模式描述了我们周边不断重复发生的问题及问题的解决方案的核心。” 模式的关键在于模式的可重复性(问题与场景的可重复性带来解决方案的可重复性)。
为了解决大型网站面临的高并发访问、海量数据处理、高可靠运行等一系列问题和挑战,大型互联网公司在实践中提出了许多解决方案,以实现高性能、高可用、易伸缩、可扩展等各种架构目标。这些解决方案被更多的网站重复使用,逐步形成了网站架构模式。
网站架构的几种模式
分层
什么是分层? 将系统在横向维度上切分成几个部分,每个部分相互独立职责单一,通过上层对下层的依赖和调用组成一个完整的系统。
计算机中的分层结构:网络的七层通信协议、计算机分层(硬件、操作系统、软件)、网站系统的分层(应用层、服务层、数据层)
优点:将庞大的系统切分,方便合作分工开发和维护;只要维持接口不变,各层可根据需要独立演化发展而不影响其他层。
缺点:必须合理规划层次边界和接口;必须严格遵循分层架构的约束,禁止跨层次调用及逆向调用。
分层的注意点
- 大的分层结构内部还可以继续分层。如服务层可分为数据接口层和逻辑处理层
- 分层是逻辑上的,应用切分的三层结构可以部署在同一台物理机上,但随着业务的发展,需要通过分离部署来获取更多的资源。分层的初衷是规划软件清晰的逻辑结构以便开发维护,但是分层结构对网站支持高并发并向分布式方向发展至关重要。
分割
如果说分层是将软件在横向方面切分,那分割就是在纵向方面的切分。
网站越大,功能越复杂,服务和数据处理的种类越多,将这些不同的功能和服务分割开来,包装成高内聚低耦合的模块单元,有助于软件的开发和维护,便于分布式部署,提高网站的并发处理和功能扩展能力。
大型网站的分割粒度可以很小。在应用层,将不同业务分割,如将购物、搜索、广告分割成不同的应用,由独立团队负责,部署在不同服务器上。在同一个应用内部,如果规模庞大业务负责,会继续进行分割,如购物业务可以分割成机票酒店业务、3C业务等等,而在这个业务上还可以继续分割成首页,搜索列表等模块。
分布式
对于大型网站,分层和分割的主要目的就是分布式部署。
什么是分布式? 将不同的模块部署在不同的服务器上,通过远程调用来协同工作。分布式通过利用更多的计算机资源来提高并发和数据处理能力,为更多用户提供服务。
分布式带来的问题
- 通过网络调用服务,影响性能
- 服务器多,宕机概率大,降低可用性
- 难以维持数据一致性,保证事务,影响网站业务正确性和业务流程
- 网站依赖错综复杂,开发管理维护困难
分布式方案
- 分布式应用和服务:将分层和分割后的应用和服务模块分布式部署。可以加快开发和发布速度;改善网站性能和并发性;复用共同服务,减少数据库连接资源消耗,便于功能扩展。
- 分布式静态资源:网站的静态资源如js、css、图片等独立分布式部署,并采用独立的域名,即动静分离。可以减轻应用服务器的负载压力;使用独立域名能加快浏览器并发加载速度;有利于网站分工。
- 分布式数据和存储对传统数据库进行分布式部署;Nosql产品
- 分布式计算 网站中一些业务的计算(如搜索引擎的索引构建、数据仓库的数据分析统计等)规模非常庞大,目前普遍使用Hadoop及其MapReduce分布式计算框架进行批处理计算。特点是移动计算而不是移动数据,将计算程序分发到数据所在位置以加速计算。
- 分布式配置:支持网站线上服务器配置实时更新
- 分布式锁:实现并发和协同
- 分布式文件系统:支持云存储
集群
多台服务器部署相同的应用构成集群,通过负载均衡设备共同对外提供服务。
作用:提供更好的并发特性;提高可用性,当某台机器发生故障时,负载均衡或失效转移机制会将请求转移到其他服务器上。
缓存
缓存就是将数据存放在距离计算最近的位置以加快处理速度。
大型网站架构设计在很多方面都使用了缓存设计。
- CDN 内容分发网络,部署在距离用户最近的网络提供商机房,缓存着网站的一些静态资源,用户发送请求后,能快速获得响应。如视频网站和门户网站会将用户访问量大的热点内容缓存在CDN。
- 反向代理 属于网站前段架构的一部分,用户请求到达网站的数据中心时,最先访问的就是反向代理服务器,缓存着网站的静态资源。
- 本地缓存 在应用服务器上缓存数据
- 分布式缓存 应用程序通过网络远程访问
使用缓存的前提条件
- 数据访问热点不均衡。频繁访问的数据放在缓存中。
- 数据在某个时间段内有效,不会很快过期,否则会因失效而导致藏独,影响结果的正确性
异步
异步是系统降低耦合度的重要手段。业务之间的消息传递不是同步调用,而是将业务操作分成多个阶段,每个阶段之间通过共享数据的方式异步执行进行协作。
异步的使用方式 单一服务器内部通过多线程共享内存队列的方式实现异步。业务操作前的线程将输出写入队列,后面的线程从队列中取数据进行处理。 分布式系统中,多个服务器集群通过分布式消息队列实现异步。
异步架构是典型的生产者消费者模式,两者不直接调用,只要保证数据结构不变,彼此功能的实现就可以随意变化不受影响。
使用异步方式处理业务会对用户体验、业务流程造成影响,需要网站产品设计方面的支持。
异步的特性
- 提高系统可用性:消费者服务器发生故障,数据会在消息队列中存储堆积,系统整体表现无障碍,恢复正常后,继续处理消息队列中的数据。
- 加快网站响应速度:处在业务处理前端的生产者服务器在处理完业务请求后,将数据写入消息队列,不需要等待消费者服务器处理就可以返回,减少响应延迟。
- 消除并发访问高峰:网站并发访问突然增大时,将突然增加的请求数据放入消息队列中,等待消费者服务器依次处理,就不会对整个网站负载造成太大的压力。
冗余
通过冗余能够实现高可用。要想保证在服务器宕机的情况下依然可以继续服务,不丢失数据,就需要一定程度的服务器冗余运行、数据冗余备份。
数据库除了定期备份、存档保存、实现冷备份外,为了保证在线业务高可用,还需要对数据库进行主从分离,实时同步实现热备份。
为了抵御地震、海啸等不可抗力导致的网站瘫痪,某些大型网站会对整个数据中心进行备份,全球范围内部署灾备数据中心。网站程序和数据实时同步到多个灾备数据中心。
自动化
一切都可以自动化是网站的理想状态。目前大型网站的自动化架构设计主要集中在发布运维方面。
减少人为干预,使发布过程自动化可以有效减少故障。发布过程包含诸多环节:
- 自动化代码管理:代码版本控制、代码分支创建合并等过程自动化。
- 自动化测试:系统自动将代码部署到测试环境,启动自动化测试用例进行测试,并发送测试报告。
- 自动化安全检测:对代码进行静态安全扫描,部署到安全测试环境进行安全攻击测试,评估其安全性。
- 自动化部署:自动部署到生产环境
网站在运行过程中会遇到很多问题,如服务器宕机、程序bug、存储空间不足、爆发式访问高峰。
因此需要进行自动化监控,对服务器进行心跳检测,并监控其各项性能指标和应用的关键数据指标。
如发现异常、超出预设的阀值,就进行自动化报警。
在检测到发生故障后,系统会进行自动化失效转移,将失效的服务器从集群中隔离出去。
待故障消除之后,系统进行自动化失效恢复,重新启动服务,同步数据保证一致性。
在网站遇到访问高峰时,会进行自动化降级,通过拒绝部分请求及关闭部分不重要的服务将系统负载降至一个安全的水平。
必要时,还需要自动化分配资源,将空闲资源分配给重要服务,扩大其部署规模。
安全
互联网的开放特性使得其从诞生起就面临巨大的安全挑战。网站在安全方面也积累了许多模式。
- 通过密码和手机校验码进行身份验证
- 登录、交易等操作要对网络通信进行加密,存储的敏感数据进行加密处理
- 使用验证码防止机器人程序滥用网络资源攻击网站
- 对常见的攻击网站的XSS攻击、SQL注入进行编码转换等相应处理
- 对垃圾信息、敏感信息过滤
- 对交易转账等重要操作更具交易模式和交易信息进行风险控制
架构模式在新浪微博的应用
在短短几年时间新浪微博的用户数就从零增长到数亿,围绕着新浪微博正在形成一个集社交、媒体、游戏、电商等多位一体的生态系统。
微博最初也是从一个小网站发展而来,使用简单的LAMP架构。随着用户数不断增加,系统不堪重负。新浪微博在较短时间内几经重构,最后形成现在的架构。
系统分为三层,最下层(基础服务层)是整个系统的技术基础,支撑了新浪微博海量数据及高并发访问。
中间层是平台服务和应用服务,将核心的业务分割成独立的服务模块,通过依赖调用和数据共享构成新浪微博的业务基础。
最上层是API和新浪微博的业务层,客户端(WEB网站)和第三方应用通过调用API集成到系统中,共同组成一个生态系统。
分层和分割后的业务模块和基础技术模块分布式部署,每个模块都构成集群。
早期架构中,微博发布使用同步推模式,用户发布微博后,系统会立即将微博插入到数据库中所有粉丝的订阅列表,会引起大量写操作,超出数据库负载,系统性能急剧下降,用户响应延迟下降。后来改用异步推拉结合的模式,用户发布微博后将微博写入消息队列后立即返回,用户响应迅速,消费者任务再将微博推送给在线粉丝的订阅列表中,非在线用户登录后再根据关注列表拉取微博。
由于微博频繁刷新,系统使用多级缓存策略,热门微博和明星微博缓存在所有的微博服务器上,在线用户的微博和近期微博缓存在分布式缓存集群上。
为了提高系统整体可用性和性能,启用了多个数据中心,既是地区用户访问中心,也是数据冗余复制的灾备中心,所有数据通过远程消息系统在不同数据中心之间同步。
新浪微博还开发了一系列自动化工具,改善运维水平提高可用性。使用多级安全审核策略保护系统和用户。
小结
本文首先介绍了什么是架构模式和常用的几种架构模式,最后通过新浪微博的例子介绍这些架构模式在实际中的运用。
正确的使用架构模式可以更好的利用业界和前人的思想和实践,在短时间内开发出更好的系统。但是模式受其使用场景限制,对系统的要求和约束很多,生搬硬套某个模式,只会带来更多的问题。因此我们要多注重对问题的深刻理解,恰当使用模式并作出创造和创新。