浅谈网络架构及其演变

现在大型网站的架构变得越来越复杂,不过架构的演变过程并不是没有规律的,它们是在遇到相应问题之后为了解决问题次啊演变出来的。此文首先从软件的三大类型说起,再简单介绍各种架构的演变过程。

1. 软件的三大类型

在零几年那个时代,软件主要以单机软件为主,如画图板、五笔打字等,当时学习电脑和打字时一个概念,那些不需要联网的单机软件就是最开始的软件。

后来有的程序需要将数据统一管理软件中使用的数据,所以就将保存数据的数据库统一存放在一台主机中,所有的用户在需要数据的时都要从主机获取,这时就分出来了客户端和服务端。

用户安装的软件叫客户端(Client),统一管理数据的主机中的软件就叫服务端(Server),这种结构就叫CS结构。

再后来,这种结构的服务端就不只是管理数据了,另外还可以处理一些业务逻辑。业务放到服务端统一处理可以提供更好的安全性和稳定性,不过服务端的负担也就加重了。CS结构如下图。

CS结构的程序已经可以完成网络通信了,不过使用起来有点麻烦,首先时开发者要提供客户端和服务端两套软件;其次每个用户再使用时都需要单独安装客户端软件,而且升级的时候也需要每个用户都就行升级。
为了解决这个问而设计了统一的客户端,而且默认安装在用户电脑里面,这就是电脑中的浏览器(Browser),而且一个浏览器可以访问所有同种类型的网站,当然能它主要用于展示数据,具体业务处理是在不同的服务端进行的,这种结构就叫BS结构。
BS结构如下图。

这就是软件的三大类型:单机类型、CS类型和BS类型。但BS结构的灵活性和处理效率不如CS结构,所以像QQ、微信、大型游戏等软件使用的还是CS结构。

2. 基础结构并不见简单

BS结构是最基础的结构,不过即使这种最基础的结构的底层是实现并不简单,互联网是个错综复杂的结构,其中包含的节点不计其数,两个节点之间的距和连接路线都是不确定的,数据在传输过程中还可能会丢失, 所以非常复杂。

不过对于复杂的问题,我们可以将其分为若干简单问题来解决。BS结构网络传输的分解方式有两种:一种是标准的OSI参考模型,另一种是TCP/IP参考模型。
分层关系与对应关系如下图。

实际使用中更多的是TCP/IP模型,其中的四层模型可简单理解为:

网络接入层:将需要相互连接的节点接入网络中,从而为数据传输提供条件。
网际互联层:找到传输数据的目标节点。
传输层:实际传输数据。
应用层:使用接收到的数据。
简单理解,就好像我们在网上买东西,首先确定自己所在的位置有相应的快递,这就相当于网络接入层,然后告诉卖家地址,地址就相当于网际互联层,快递送货就相当于传输层,最后我们收到货物之后拆包使用就相当于应用层。

由于网络传输应用非常广泛,所以需要大家都遵守规矩,不过网络传输中的这些规矩不是强制性的,所以不叫制度也不叫标准,而叫协议。BS结构中TCP/IP模型中的网络接入层没有相应的协议,网际互联层是IP协议,传输层是TCP协议,应用层是HTTP协议。当然这些协议,我们也可以人为更改。

3. 架构演变的起点

当服务端数据流量变得越来越大时,主机就难以应付,这时候就需要将应用程序和数据库分别放在不同的主机中。

4. 海量数据的解决方案

无论是企业的业务系统还是互联网上的网站程序都面临者数据量大的问题,这个问题解不好将严重影响系统 的运行速度,下面针对这个问题的解决方法进行系统的介绍。

4.1 缓存和页面静态化

数据量大这个问题最直接的解决方案就是使用缓存,缓存就是将从数据库中获取的结果暂时保存起来,在下次使用的时候无需重新到数据库中获取,这样就能大大降低数据库的压力。

跟缓存相似的另外一种技术叫页面静态化,它在原理上跟缓存非常相似,缓存是将从数据库中获取到的数据(当然也可以是别的任何可以序列化的东西)保存起来,而页面静态化是将程序最后生成的页面保存起来,使用页面静态化后就不需要每次调用都重新生成页面了,这样不但不需要查询数据库,而且连应用程序处理都省了,所以页面静态化同时对数据量大和并发量高两大问题都有好处。

页面静态化可以在程序中使用模板技术生成,如常用的 Freemarker和 Velocity都可以根据模板生成静态页面,另外也可以使用缓存服务器在应用服务器的上一层缓存生成的页面,如可以使用 Squid,另外 Nginx也提供了相应的功能。

4.2 数据库优化

要解决数据量大的问题,是避不开数据库优化的数据库优化的方法非常多,常用的有表结构优化、SL语句优化、分区和分表、索引优化、使用存储过程代替直接操作等,另外有时候合理使用冗余也能获得非常好的效果。

表结构优化

表结构优化是数据库中最基础也是最重要的,如果表结构优化得不合理,就可能导致严重的性能问题,具体怎么设计更合理也没有固定不变的准则,需要根据实际情况具体处理。

SQL语句优化

SQL语句优化也是非常重要的,基础的SQL优化是语法层面的优化,不过更重要的是处理逻辑的优化,这也需要根据实际情况具体处理,而且要和索引缓存等配合使用。不过SQL优化有一个通用的做法就是,首先要将涉及大数据的业务的SQL语句执行时间详细记录下来,其次通过仔细分析日志(同一条语句对不同条件的执行时间也可能不同,这点也需要仔细分析)找出需要优化的语句和其中的问题,然后再有的放矢地优化,而不是不分重点对每条语句都花同样的时间和精力优化。

分区

当一张表中的数据量变多的时候操作速度就慢了,所以很容易想到的就是将数据分到多个表中保存,但是这么做之后操作起来比较麻烦,想操作(增删改査)一个数据还需要先找到对应的表,如果涉及多个表还得跨表操作。其实在常用的数据库中可以不分表而达到跟分表类似的效果,那就是分区。分区就是将一张表中的数据按照一定的规则分到不同的区来保存,这样在查询数据时如果数据的范围在同一个区内那么可以只对一个区的数据进行操作,这样操作的数据量更少,速度更快,而且这种方法对程序是透明的,程序不需要做任何改动。

分表

如果一张表中的数据可以分为几种固定不变的类型,而且如果同时对多种类型共同操作的情况不多,那么都可以通过分表来处理,这也需要具体情况具体对待。例如对一个业务系统进行重构开发时就将其中保存工人工作卡片的数据表分成了三个表,并且对每个表进行分区,在同时使用缓存(主要用于在保存和修改时对其他表的数据获取中,如根据工人Id获取工人姓名、工人类别、所在单位、所在工段及班组等信息)、索引、SOL优化等的情况下操作速度比原来提高了100倍以上。

另外一种分表的方法是将一个表中不同类型的字段分到不同的表中保存,这么做最直接的好处就是增删改数据的时候锁定的范围减小了,没被锁定的表中的数据不受影响。如果个表的操作频率很高,在增删改其中一部分字段数据的同时另一部分字段也可能被操作,而且(主要指查询)用不到被增删改的字段,那么就可以把不同类型的字段分别保存到不同的表中,这样可以减少操作时锁定数据的范围。不过这样分表之后,如果需要查询完整的数据就得使用多表操作了。

索引优化

索引的大致原理是在数据发生变化(增删改)的时候就预先按指定字段的顺序排列后保存到一个类似表的结构中,这样在查找索引字段为条件的记录时就可以很快地从索引中找到对应记录的指针并从表中获取到记录,这样速度就快多了。

不过索引也是一把双刃剑,它在提高査询速度的同时也降低了增删改的速度,因为每次数据的变化都需要更新相应的索引。

使用存储过程代替直接操作

在操作过程复杂而且调用频率高的业务中,可以通过使用存储过程代替直接操作来提高效率,因为存储过程只需要编译一次,而且可以在一个存储过程里面做一些复杂的操作。

4.3 分离活跃数据

虽然有些数据总数据量非常大,但是活跃数据并不多,这种情况就可以将活跃数据单独保存起来从而提高处理效率。比如,对网站来说。用户很多时候就是这种数据,注册用户问题多,但是活跃用户却不多,而不活跃的用户中有的偶尔也会登录网站,因此还不能删除。这时就可以通过一个定期处理的任务将不活跃的用户转移到别的数据表中,在主要操作的数(增删改表中只保存活跃用户,查询时先从默认表中查找,如果找不到再从不活跃用户表中查找,这样就可以提高查询的效率。判断活跃用户可以通过最近登录时间,也可以通过指定时间段内登录次数。除了用户外还有很多这种类型的数据,如一个网站上的文章(特别是新闻类的)、企业业务系统中按时间记录的数据等。

4.4 批量读取和延迟修改

批量读取和延迟修改的原理是通过减少操作的次数来提高效率,如果使用得恰当,效率将会呈数量级提升。

4.5 读写分离

读写分离的本质是对数据库进行集群,这样就可以在高并发的情况下将数据库的操作分配到多喝数据库服务器去处理从而降低单台服务器的压力不过由于数据库的特殊性——每台服务器所保存的数据都需要一致,所以数据同步就成了数据库集群中最核心的问题。如果多台服务器都可以写数据那么数据同步将变得非常复杂,所以一般情况下是将写操作交给专门的一台服务器处理,这台专门负责写的服务器叫做主服务器。当主服务器写入(增删改)数据后从底层同步到别的服务器(从服务器),读数据的时候到从服务器读取,从服务器可以有多台,这样就可以实现读写分离,并且将读请求分配到多个服务器处理。主服务器向从服务器同步数据时,如果从服务器数量多,那么可以让主服务器先向其中一部分从服务器同步数据,第一部分从服务器接收到数据后再向另外一部分同步。结构如下图。

4.6 分布式数据库

分布式数据库是将不同的表存放到不同的数据库中然后再放到不同的服务器。这样在处理请求时,如果需要调用多个表,则可以让多台服务器同时处理,从而提高处理速度。

数据库集群(读写分离)的作用是将多个请求分配到不同的服务器处理,从而减轻单台服的存储思务器的压力,而分布式数据库是解决单个请求本身就非常复杂的问题,它可以将单个请求分配到多个服务器处理,使用分布式后的每个节点还可以同时使用读写分离,从而组成多个节点群,结构图如图。

4.7 NoSQL和Hadoop

NoSQL是近年来发展非常迅速的一项技术,它的核心就是非结构化。我们一般使用的数据库(SOL数据库)都是需要先将表的结构定义出来,一个表有几个字段,每个字段各是什么类型,然后才能往里面按照相应的类型保存数据,而且按照数据库范式的规定,一个字段只资源能保存单一的信息,不可以包括多层内容,这就对使用的灵活性带来了很大的制约, NOSQL些文就是突破了这些条条框框,可以非常灵活地进行操作,另外因为 NOSQL通过多个块存储数据的特点,其操作大数据的速度也非常快,这些特性正是现在的互联网程序最需要的,所以NoSQL发展得非常快。现在 NOSQL主要使用在互联网的程序中,在企业业务系统中使用的还不多,而且现在 NoSQL还不是很成熟,但由于灵活和高效的特性,NOSQL发展的前景是非常好的。(关于NoSQL的介绍后续了解之后再介绍)

Hadoop是专门针对大数据处理的一套框架,随着近年来大数据的流行Hadoop也水涨船高,出世不久就红得发紫。Hadoop对数据的存储和处理都提供了相应的解决方案,底层数据的存储思路类似于分布式加集群的方案,不过 Hadoop是将同一个表中的数据分成多块保存到多个节点(分布式).而且每一块数据都有多个节点保存(集群).这里集群除了可以并行处理相同的数据,还可以保证数据的稳定性,在其中一个节点出现问题后数据不
会丢失。这里的每个节点都不包含一个完整的表的数据,但是一个节点可以保存多个表的数据,结构图如图。

5. 高并发的解决方案

除了数据量大,另一个常见的问题就是并发量高,很多架构就是针对这个问题设计出来的,下面分别介绍。

5.1 应用和静态资源分离

刚开始的时候应用和静态资源是保存在一起的,当并发量达到一定程度时就需要将静态资源保存到专门的服务器中,静态资源主要包括图片,视频、js.css和一些资源文件等,这些文件因为没有状态,所以分离比较简单,直接存放到相应的服务器就可以了,一般会使用专门的域名去访问。通过不同的域名可以让浏览器直接访问资源服务器而不需要再访问应用服务器了。架构如图。

5.2 页面缓存

页面缓存是将应用生成的页面缓存起来,这样就不需要每次都重新生成页面了,从面可以节省大量CPU资源,如果将缓存的页面放到内存中速度就更快了。如果使用了 Nginx服务器就可以使用它自带的缓存功能,当然也可以使用专门的Squid服务器。页面缓存的默认失效机制一般是按缓存时间处理的,当然也可以在修改数据之后手动让相应缓存失效。

5.3 集群与分布式

集群和分布式处理都是使用多台服务器进行处理的,集群是每台服务器都具有相同的功能,处理请求时调用哪台服务器都可以,主要起分流的作用,分布式是将不同的业务放到不同的服务器中,处理一个请求可能需要用到多台服务器,这样就可以提高一个请求的处理速度,而且集群和分布式也可以同时使用,结构如图所示。

集群有两个方式:一种是静态资源集群。另一种是应用程序集群。静态资源集群比较简单,而应用程序集群就有点复杂了。因为应用程序在处理过程中可能会使用到一些缓存的数据,如果集群就需要同步这些数据,其中最重要的就是 Session, Session同步也是应用程序集
群中非常核心的一个问题。

5.4 反向代理

反向代理指的是客户端直接访问的服务器并不真正提供服务,它从别的服务器获取资源,然后将结果返回给用户的,如图所示。

代理服务器可以和实际处理请求的服务器在同一台主机上,而且一台反向代理服务器也可以访问多台实际处理请求的服务器。反向代理服务器主要有三个作用:①可以作为前端服务器跟实际处理请求的服务器(如Tomcat)集成;②可以用做负载均衡;③转发请求,比如,可以将不同类型的资源请求转发到不同的服务器去处理,可以将动态资源转发到Tomcat、PHP等动态程序而将图片等静态资源的请求转发到静态资源的服务器,另外也可以在url地址结构发生变化后将新地址转发到原来的旧地址上。

5.5 CDN

CDN其实是一种特殊的集群页面缓存服务器,它和普通集群的多台页面缓存服务器比主要是它存放的位置和分配请求的方式有点特殊。CDN的服务器是分布在全国各地的,当接收到用户的请求后会将请求分配到最合适的CDN服务器节点获取数据,比如,联通的用户会分配到联通的节点,电信的用户会分配到电信的节点;另外还会按照地理位置进行分配,北京的用户会分配到北京的节点,上海的用户会分配到上海的节点。CDN的每个节点其实就是个页面缓存服务器,如果没有请求资源的缓存就会从主服务器获取,否则直接返回缓存的页面。CDN分配请求的方式比较特殊,它并不是使用普通的负载均衡服务器来分配的,而是用专门的CDN域名解析服务器在解析域名的时候就分配好的,一般的做法是在ISP那里使用CNAME将域名解析到一个特定的域名,然后再将解析到的那个域名用专门的CDN服务器解析到相应的CDN节点,结构如图所示。

第二步访问CDN的DNS服务器是因为 CNAME记录的目标域名使用NS记录指向了CDN的DNS服务器。CDN的每个节点可能也是集群了多台服务器。CDN的原理并不复杂,不过如果要自己去架设则需要投入大量的资金,现在有专门的CDN服务商,可以直接购买它们的服务。

6. 底层的优化

我们前面讲到的所有架构都是建立在最前面介绍的基础架构之上的,而且很多地方都需要通过网络传输数据,如果可以加快网络传输的速度,那将会让整个系统从根本上得到改善网络传输数据都是按照各种协议进行的,不过协议并不是不可以改变, Google就迈出了这
步,它制定了Ouic、Spdy等协议来传输数据,Ouic比TCP效率高而且比UDP安全,Spdy协议在现有HTTP协议的基础上增加了很多新特性,提高了传输的效率,不过有些特性已经包含到了HTTP/2协议中,而且Google也已经放弃了Spdy而使用HTTP/2了。

7. 小结

网站架构的整个演变过程主要是围绕大数据和高并发这两个问题展开的,解决的方案主要分为使用缓存和使用多资源两种类型。多资源主要指多存储(包括多内存)、多CPU和多网络,对于多资源来说又可以分为单个资源处理一个完整的请求和多个资源合作处理一个请求两种类型,如多存储和多CPU中的集群和分布式,多网络中的CDN和静态资源分离。理解了整个思路之后就抓住了架构演变的本质,而且自己可能还可以设计出更好的架构。

一个网站具体使用什么样的架构需要根据实际需要做出选择,网站架构并不是竟技场,更不是使用的技术越复杂越好,只要可以满足自己的需要、可以解决自己所遇到的问题就可以了。要想设计出合理的架构首先需要理解每种架构所针对的问题和它背后的本质,只有这样才能真正把架构用做解决问题的工具,而不是为了架构而架构,最后问题不一定能解决还浪费了资源。另外在使用复杂架构之前一定要先将自己的业务优化好,这是基础中的基础,非常重要!

无论架构还是协议都要以正确的态度对待,它们都是为了解决特定的问题而设计出来的,我们要认真并且谦虚地学习,不过也不需要将它们当成神圣不可侵犯的东西,它们的本质还是为我们解决问题的工具。另外这些架构、协议以及相关的产品都是经过实际的考验可以解决问题的,不过也并不是说它们就是最优的解决方案,我们只有真正理解了它们所针对的问题才能对它们理解得更透彻、使用得更灵活。
--------------------- 
作者:米奇罗 
来源:CSDN 
原文:https://blog.csdn.net/chachapaofan/article/details/83626674 
版权声明:本文为博主原创文章,转载请附上博文链接!

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值