用户访问网站的基本流程(6个阶段):
DNS解析 tcp三次握手 http请求报文 网站集群内部处理数据的一个过程 http响应报文 tcp四次挥手断开的过程
1)DNS解析2种查询方式:递归查询->迭代查询(见下图DNS部分)
所谓 递归查询过程 就是 “查询的递交者” 更替, 而 迭代查询过程 则是 “查询的递交者”不变
当用户在浏览器地址栏敲入域名地址回车后客户端首先检查本地DNS缓存和hosts文件,如果是第一次访问的话,本地DNS缓存是没有缓存记录的,而hosts文件是用来做测试使用的也是没有结果的,此时客户端会请求local DNS,local DNS是客户端在本地网卡中配置的DNS服务器,local DNS首先会检测DNS缓存,DNS缓存中如果有结果,会将结果返回给客户端,如果没有结果local DNS会负责域名解析,local DNS首先访问请求全球13台根服务器(据说美国有8台,日本2台,中国没有)根服务器会根据local DNS请求域名地址,将此域名地址的顶级域名服务器返回给local DNS,local DNS在继续访问顶级域名服务器,顶级域名服务器根据local DNS请求的地址将此地址的二级域名服务器返回给local DNS,local DNS又访问二级域名服务器,二级域名服务器我们又叫做授权DNS服务器,授权服务器检查自己的A记录将结果返回给local DNS,local DNS进行本地缓存并发给客户端。
2) 客户端接到结果后与服务端建立TCP三次握手连接
首先客户端发送syn seq序列给服务端,客户端从close的状态进入syn send状态,服务端接收到syn请求的时候, 从closed状态进入listen,服务端同时发送ack和syn请求,此时服务端从listen状态进入到syn received,客户端接收到ack确认和syn请求后进行返回ack确认,此时客户端进入establised状态, 服务端接收到ack确认也进入establised状态。
《TCP连接11种状态详解》
LISTEN: 侦听来自远方的TCP端口的连接请求
SYN-SENT: 再发送连接请求后等待匹配的连接请求
SYN-RECEIVED:再收到和发送一个连接请求后等待对方对连接请求的确认
ESTABLISHED: 代表一个打开的连接
FIN-WAIT-1: 等待远程TCP连接中断请求,或先前的连接中断请求的确认
FIN-WAIT-2: 从远程TCP等待连接中断请求
CLOSE-WAIT: 等待从本地用户发来的连接中断请求
CLOSING: 等待远程TCP对连接中断的确认
LAST-ACK: 等待原来的发向远程TCP的连接中断请求的确认
TIME-WAIT: 等待足够的时间以确保远程TCP接收到连接中断请求的确认
CLOSED: 没有任何连接状态
3)客户端发送http请求报文,http请求又分为四部分
第一部分:请求行
请求行又分为三块,第一块是请求方法,第二块是请求URL,第三块是请求的http协议版本,我们常用的方法有GET head POST等,get就是用来客户端向服务端获取资料的时候就是使用get方式,post是用来客户端向服务端注册一些信息等使用的是post方式,而我们使用curl -I 是使用服务端的响应头部信息head。
第二部分:请求头部信息,包含媒体类型、语言类型、压缩方式、客户端类型主机名等
媒体类型包含image/gif、jpeg图片类型,音频类型,这些类型起初是为了解决邮件系统的传输搬移数据,现在广泛应用于http协议当中
第三部分是空行
空行表示请求头部与请求主体的分隔行。
第四部分:请求主体
常用的get方式是没有请求主体的,post方式才有请求主体,这个请求发送到服务端。
4)负载均衡 首先接受请求
负载均衡器:有软硬件2种
1)企业常用的有硬件F5;
2)软件应用层的nginx、haproxy 传输层的lvs等;
然后负载均衡器会根据自己特殊的算法轮询啊,最小连接数将这些请求一一发送给web服务器,
到了web服务器,这些请求又分为动态请求和静态请求,静态请求一般就是静态页面一般是用html css xml等语言编写的网页,静态网页的特点性能高速度快,
在客户端的浏览器解析,不需要数据库的支持,容易被搜索引擎收录,缺点用户交互性比较差,不易于维护,常用的处理静态页面的软件有apache nginx等
国内最为主流的就是nginx,动态网页一般是与aspx php jsp等结尾的,动态网页的url中,会有一些特殊字符,像= &符号等,动态网页的特点,
与用户的交互性比较强,容易维护,但是在服务端进行解析,并不容易被搜索引擎收录,因此性能会比较差,
常用处理动态页面的软件有php引擎,tomcat resin等,php配合apache nginx使用,解析php编程语言开发的程序,配合apache是以php模块的方式来进行对接,跟nginx是fastCGI守护进程来进行解析,还有一些tomcat resin这些是
解析java语言开发的程序,这些状态程序会请求一些结构化的数据,结构化的数据我们会存放在后端的数据库中,目前互联网最主流的关系型数据库就是mysql,
类似于二维表,但是性能会比较低,因此有些企业会使用memcached redis非关系型数据库进行做mysql的缓存数据库来提高访问速度,
还有一些非结构化的数据,像图片、视频、音频等这些数据我们会存放在存储服务器上,常用的存储服务器有nfs、mfs、glusterfs等,
这些非结构化的数据属于静态数据,很多公司会选择把这些静态数据推送到CDN节点上来提高用户的体验。
5) http响应报文又分为四部分
第一部分 响应起始行
起始行分为三块
第一块是http协议版本
第二块是状态码
第三块是状态码描述,一般我们常见的状态码像200正常,301永久跳转,302是临时跳转
第二部分:响应头部信息
一般是在内容服务器的一些参数,比如说处理请求的是哪个软件
第三部分:响应空行
表示响应头部与主体的分隔行。
第四部分:响应主体
响应主体信息就是客户端真正在浏览器中的数据会在响应主体中返回给客户端。
此时客户端返回完之后:在常链接超时后
6) 客户端会进行tcp断开链接
首先客户端会发送FIN请求给服务端,此时客户端从established状态进入到FINWAIT-1状态,服务端接收到请求后从established状态进入closewait状态
服务端在进行ack确认,先返回给客户端,客户端进入finwait2状态,此时已经进入了一个半链接状态,所谓的半链接状态就是客户端向服务端发送数据完毕了,
但是服务端向客户端发送的数据还没有发送过来,当服务端向客户端发送完数据之后,继续发送fin请求,此时客户端接到fin请求进行返回ack确认,
此时客户端进入timewait状态,客户端接到ack,ack接着发送给服务端,此时服务端进入closed状态,断开链接。此时客户端会
等待2倍的MSL值。(2倍的MSL值就是linux的生存周期,2MSL值就是一般默认是30秒)就是1分钟后客户端会进入closed状态,就是从timewait状态自动进入closed状态。
"查看上面TCP11种状态中,包含三次握手和四次断开"
网站访问流程故事版
我们的主角小王,是个活雷锋,哪里需要哪里搬,今天他又来了。
小王打开了自己的百度浏览器,输入www.baidu.com,按下回车,等了一会,就打开了网页,小王很困惑,在敲下回车的一瞬间,电脑到底做了什么?
为了一探究竟,小王打开百宝箱,并念出了那句开启百宝箱的咒语(我是韩以安,关注我,有更多精彩内容哦)。百宝箱闪出一个耀眼光芒,小王眼前一黑,过了好一会儿小王醒才过来,醒过来后发现自己被困在了电脑里,一个美女正在电脑前跟闺蜜聊着天。突然美女像是想起了什么,她飞快的打开浏览器,输入了www.taobao.com
小王的身体突然就不听使唤,直奔电脑的host文件飞去, 小王这才明白,百宝箱把自己变成了一个用户请求,根据请求的处理流程,小王飞快的看了一眼host,发现文件中已经有www.taobao.com对应的ip地址,于是获取到ip,直接扔给了美女,美女很开心的购起物来。
小王正要好好欣赏一下眼前的美人,QQ上一个消息弹出,是一个不常见的网址,www.wsmv.com 美女想也没想,直接打开, 小王立即赶往host查看网址对应的ip,结果发现host里没有对应的ip。小王心想,这应该是美女第一次打开这个网站,所以电脑里没有缓存。
既然在host里没有找到,小王赶紧询问了下周边忙碌的其他请求,接下来该怎么办,一个看上去很老成的nginx请求路过,指了指旁边的路由器(在你的城市的某个角落,但是不会太远)说,“诺,那个是本地域名服务器,你去向他寻求帮助吧”
小王飞奔过去,向本地DNS服务器询问是否有刚刚美女输入的网址的ip, 本地DNS快速扫描了下,发现没有,但给出了提示,可以去根服务器去问问。
小王来到根服务器,小王问,有没有www.wsmv.com对应的ip, 根域缓缓的答道,“我这边没有,但是我有.com.的服务器地址,你可以去问问他”,说着根域服务器甩出了 一条信息,上面写在.com服务器的ip地址。
小王又马不停蹄的根据ip找到对应的.com服务器,询问是否有美女输入的网站ip的地址, .com服务器头也没抬的回了一句:“又是根域让你来的吧,我这边有wsnv.com对应的ip地址,你可以直接去,但是我们这有个不成文的规定,不是所有人都可以随便访问服务器的,IP给你,接下来能不能请求到资源还得靠你自己”
小王拿到了 wsnv.com的ip地址正要进去获取数据,却被一个叫TCP协议挡住了去路。小王知道这是要进行TCP连接了, 需要与服务器进行三次对话,跟对暗号一样,通过后才能获取数据。
但是要进行TCP连接,小王得先把消息成功的发送到服务器上,小王根据书中讲的准备了IP协议,ARP协议和OSPF协议, IP地址只指定了美女的PC的ip和刚从.com获得的要登陆网站的ip地址, 然后经过一个个路由器传送给服务器,然后进行了tcp的链接。
连接成功了,小王兴奋的跳了起来,能给美女获取到数据是小王最开心的事情。 but,小王听到一个声音 “恭喜你,成功跟tcp进行了链接,现在你可以寻求HTTP协议的帮助来请求网页了,请先熟悉HTTP协议的请求规则”
小王赶紧查看HTTP请求规则,规则里有条重要提示: 虽然你通过了tcp协议,但是还是有被服务器拒绝的可能,如果服务器拒绝了你的请求会返回"Forbiden",如果服务器没有拒绝,能够正常访问,就返回200OK,然后才会给你传输数据。
小王连忙根据规则发送HTTP请求报文给服务器,经过了硬件防火墙,到了负载均衡,又通过负载均衡到了web,后面又有缓存,最后才到数据库。成功了,小王收到了服务器的回复,接收到一堆HTML形式的文本。然后快速返回到美女的电脑,当然也没忘了在本地缓存上存一份,毕竟下次再按这个流程走一遍,小王会累死的。
在本地缓存好之后,小王把接收的文本给了浏览器,浏览器是个聪明的家伙,很快就翻译出来,并渲染到屏幕上,看到屏幕前美女开心的笑容,小王感觉好满足,顺便瞅了一眼浏览器,不看不要紧,一看吓一跳,浏览器上是美女男朋友发来的礼物,满屏的烟花和一句我爱你。
小王的心突然疼了一下,原来有男朋友啊,那我这还忙活的这么起劲,算了,百宝箱带我回去吧。
随着一阵耀眼的光芒,小王最后看了一眼美女,恋恋不舍的离开了。
小王回来后,快速整理了今天的见闻,爱学习的小王在笔记本上写到:美女(此处划掉)
小王又重新写到: 用户发起一个请求到最终落地数据,中间经历了:
用户(电脑,网络,本地缓存)–域名服务器–tcp三次握手 --HTTP协议
进入了HTTP协议之后,小王回忆了下,先是看到了硬件防火墙F5,然后是请求发给了负载均衡nginx, nginx转发给了其中的tomcat,tomcat有相应的配置文件,根据配置文件搜索相应的资源-好像在获取资源的时候还遇到了缓存redis,然后才是访问数据库,这一圈下来好麻烦。