[转】:HTTP请求流程(一)----流程简介

http://www.cnblogs.com/stg609/archive/2008/07/06/1236966.html

 

HTTP请求流程(一)----流程简介

      最近一直在研究如何让asp.net实现上传大文件的功能,因此都没怎么写技术类的文章了。惋惜的是至今还没研究出来,惭愧~~~。不过由于这样,也了解了一下http消息请求的大体过程。我就先简单介绍下,而后再来说如何利用Telnet来模拟Http请求。讲得不对的地方还但愿你们给我指出来。由于内容比较多,因此分红两部分来写。
      一、流程简介
      二、Telnet模拟HTTP请求


      这篇咱们就来作一个简单介绍。
      先提个问题:当咱们在浏览器的地址栏中输入"http://www.baidu.com/",而后按"回车",这以后发生了什么事?这里先不回答,你们接着往下看先。

      咱们来分析一下:

      ·HTTP请求流程

      首先,http属于Tcp/Ip模型中的应用层协议,而两个应用程序(咱们这里指的就是浏览器与服务器)之间要进行互相通讯,首先得创建Tcp链接,而后浏览器才能向服务器发送请求信息,服务器在接受到请求信息后,返回相应的应答信息,浏览器接收到来自服务器的应答信息后,对这些数据进行解释执行。

      在http 1.0的版本中,浏览器的每次请求(也就是对每个页面的访问)都要求创建一次单独的链接,在处理完每一次的请求后,就自动释放链接。(这点咱们应该都有感受,好比咱们访问一个页面,当该页面在浏览器中显示出来的时候,咱们能够拔掉网线,此时该页面上的信息并不会丢失。)而当咱们请求的网页文件中有不少图片、音乐、电影等信息时,服务器返回的信息中并不直接包含图片数据,而只是保存该图片的连接,当浏览器进行解释的时候,遇到图片的url时,才向服务器发出对图片的请求信息。可见若是一个网页中包含多个图片数据时,将会频繁的与服务器创建链接,与释放链接,这无疑会形成资源的浪费。html

                                                                                        http 1.0 请求模式

      而http 1.1则能够在一次链接中处理多个请求,而且多个请求能够重叠进行,不须要等待一个请求结束后再发送下一个请求。web

创建链接的方式浏览器

HTTP支持2中创建链接的方式:非持久链接和持久链接(HTTP1.1默认的链接方式为持久链接)。缓存

1)  非持久链接服务器

让咱们查看一下非持久链接状况下从服务器到客户传送一个Web页面的步骤。假设该贝面由1个基本HTML文件和10个JPEG图像构成,并且全部这些对象都存放在同一台服务器主机中。再假设该基本HTML文件的URL为:gpcuster.cnblogs.com/index.html。asp.net

下面是具体步骡:工具

1.HTTP客户初始化一个与服务器主机gpcuster.cnblogs.com中的HTTP服务器的TCP链接。HTTP服务器使用默认端口号80监听来自HTTP客户的链接创建请求。2.HTTP客户经由与TCP链接相关联的本地套接字发出—个HTTP请求消息。这个消息中包含路径名/somepath/index.html。3.HTTP服务器经由与TCP链接相关联的本地套接字接收这个请求消息,再从服务器主机的内存或硬盘中取出对象/somepath/index.html,经由同一个套接字发出包含该对象的响应消息。post

4.HTTP服务器告知TCP关闭这个TCP链接(不过TCP要到客户收到刚才这个响应消息以后才会真正终止这个链接)。网站

5.HTTP客户经由同一个套接字接收这个响应消息。TCP链接随后终止。该消息标明所封装的对象是一个HTML文件。客户从中取出这个文件,加以分析后发现其中有10个JPEG对象的引用。ui

6.给每个引用到的JPEG对象重复步骡1-4。

上述步骤之因此称为使用非持久链接,缘由是每次服务器发出一个对象后,相应的TCP链接就被关闭,也就是说每一个链接都没有持续到可用于传送其余对象。每一个TCP链接只用于传输一个请求消息和一个响应消息。就上述例子而言,用户每请求一次那个web页面,就产生11个TCP链接。

2)   持久链接

非持久链接有些缺点。首先,客户得为每一个待请求的对象创建并维护一个新的链接。对于每一个这样的链接,TCP得在客户端和服务器端分配TCP缓冲区,并维持TCP变量。对于有可能同时为来自数百个不一样客户的请求提供服务的web服务器来讲,这会严重增长其负担。其次,如前所述,每一个对象都有2个RTT的响应延长——一个RTT用于创建TCP链接,另—个RTT用于请求和接收对象。最后,每一个对象都遭受TCP缓启动,由于每一个TCP链接都起始于缓启动阶段。不过并行TCP链接的使用可以部分减轻RTT延迟和缓启动延迟的影响。

在持久链接状况下,服务器在发出响应后让TCP链接继续打开着。同一对客户/服务器之间的后续请求和响应能够经过这个链接发送。整个Web页面(上例中为包含一个基本HTMLL文件和10个图像的页面)自不用说能够经过单个持久TCP链接发送:甚至存放在同一个服务器中的多个web页面也能够经过单个持久TCP链接发送。一般,HTTP服务器在某个链接闲置一段特定时间后关闭它,而这段时间一般是能够配置的。持久链接分为不带流水线(without pipelining)和带流水线(with pipelining)两个版本。若是是不带流水线的版本,那么客户只在收到前一个请求的响应后才发出新的请求。这种状况下,web页面所引用的每一个对象(上例中的10个图像)都经历1个RTT的延迟,用于请求和接收该对象。与非持久链接2个RTT的延迟相比,不带流水线的持久链接已有所改善,不过带流水线的持久链接还能进一步下降响应延迟。不带流水线版本的另外一个缺点是,服务器送出一个对象后开始等待下一个请求,而这个新请求却不能立刻到达。这段时间服务器资源便闲置了。

HTTP/1.1的默认模式使用带流水线的持久链接。这种状况下,HTTP客户每碰到一个引用就当即发出一个请求,于是HTTP客户能够一个接一个紧挨着发出各个引用对象的请求。服务器收到这些请求后,也能够一个接一个紧挨着发出各个对象。若是全部的请求和响应都是紧挨着发送的,那么全部引用到的对象一共只经历1个RTT的延迟(而不是像不带流水线的版本那样,每一个引用到的对象都各有1个RTT的延迟)。另外,带流水线的持久链接中服务器空等请求的时间比较少。与非持久链接相比,持久链接(不管是否带流水线)除下降了1个RTT的响应延迟外,缓启动延迟也比较小。其缘由在于既然各个对象使用同一个TCP链接,服务器发出第一个对象后就没必要再以一开始的缓慢速率发送后续对象。相反,服务器能够按照第一个对象发送完毕时的速率开始发送下一个对象。      ·

HTTP请求消息

      1次完整的http请求消息包括:一个请求行、若干消息头以及实体内容,而消息头和实体内容能够没有,消息头和实体内容间有一个空行。
      咱们来看一个例子(为了便于说明,我在每行前加了序号):
            1 Get /mattmarg/ HTTP/1.0
            2 User-Agent: Mozilla/2.0 (Macintosh; I; PPC)
            3 Accept: text/html; */*
            4 Cookie: name = value
            5 Referer: http://www.XXX.com/a.html
      其中,第1行就是请求行:请求方式为Get(除了Get以外,还有Post、Put、Delete方式),请求的文件位于"根目录/mattmarg/"下,固然也能够直接给出须要的页面(如:/mattmarg/index.asp,也能够加上一些其它字段 如:/mattmarg/index.asp?id=1&uid=xxx。当咱们经过Get请求时,提交给服务器的请求行长度不能超过1K,而若是利用Post方式,则是把所提交的信息以实体内容形式发送给服务器,因此若是服务器没有限制的话,原则上讲能够传输无限大的内容),HTTP/1.0 表示了http的版本为1.0。其他几行就是消息头了,消息头主要是用来向服务器传达某种信息或指示。如告诉服务器本身的终端(User-Agent)是什么(若是是浏览器则返回相应的浏览器型号),终端所能够解释的类型(Accept)是什么,是从哪一个页面提交的请求(Referer),以及浏览器所能解释的语言(Accept-Language)等等。咱们这里拿Accept-Language来举个例子,你们都知道google在中国大陆显示的是简体中文,而在其它的国家则显示对应的语言,这个是怎么作到的呢?其实就是浏览器向服务器递交的请求信息中包含了Accept-Language,而咱们的浏览器默认是zh-cn,而后服务器在接受到该信息时返回对应的页面。
      咱们能够经过如下方法来验证一下:
      一、打开浏览器->工具->internet选项->常规选项卡
      二、选择"语言",可见默认的语言是中文
      三、选择"添加",选择一种语言,而后调节一下优先顺序

      四、肯定以后,咱们再访问一下 http://www.google.com/,是否是发现原来的简体中文全都成了繁体字了。

      · HTTP响应消息

      
Http响应消息的格式为:一个状态行、若干消息头和实体内容,其中消息头和实体内容能够没有,消息头和实体内容间有一个空行。
      咱们依旧先来看一个例子:
            01 HTTP/1.1 200 OK
            02 Server: Microsoft-IIS/5.1
            03 X-Powered-By: ASP.NET
            04 Date: Sun, 06 Jul 2008 11:01:21 GMT
            05 Content-Type: text/html
            06 Accept-Ranges: bytes
            07 Last-Modified: Wed, 02 Jul 2008 01:01:26 GMT
            08 ETag: "0f71527dfdbc81:ade"
            09 Content-Length: 46
            10
            11 <html><head></head><body>adfasfa</body></html>
      其中,01行是状态行,用于显示服务器响应的状态,HTTP/1.1显示了对应的http协议版本,200为状态数字,OK为状态信息用于解释状态数字(这里OK对应200,表示请求正常);02~09是消息头部分,10为空行,11为实体内容(也就是服务器返回的网页内容)。

      好了,相信你们应该已经对这个http请求的流程有了一个大概的了解了吧,那么咱们反过来回答下最初留下的问题:当咱们在浏览器的地址栏中输入 " http://www.baidu.com/ " ,而后按"回车",这以后发生了什么事?

      首先,浏览器找到该网址所指向的IP,而后与其创建TCP链接,接着向百度服务器提出Get请求,当服务器接收到咱们的请求后,向咱们传送应答信息--百度的页面,而后断开链接。

      [补充]以上文章中主要是描述HTTP请求的大体流程,至于HTTP以前所创建的一系列链接,只用了"浏览器找到该网址所指向的IP,而后与其创建TCP链接"这句话或相似的话来带过。根据朋友们的回复显得这个说法不是很恰当。因此我在这里再补充些东西。
       一、获取IP。浏览器地址栏中输入"http://www.xxx.edu.cn/"并提交以后,首先它会在DNS本地缓存表中查找,若是有则直接告诉IP地址。若是没有则要求网关DNS进行查找,如此下去,当找到对应的ip后,则返回给浏览器。
       二、创建TCP链接。当获取到IP以后,就开始与所请求的服务器创建TCP链接,你能够在下图中发现syn,ack,这些标识符就是用来同步用的。
       三、链接创建后,就向服务器发出http请求(你们能够从图中看出来)。若是是HTTP1.0的版本则,每一次请求结束后,就释放TCP链接。

(上图中,因为是第一次访问网站,没法在本地找到对应IP)


(短期内,第二次访问同一网站)


参考:
1.张孝祥老师的HTTP协议详解
2.http://www.cnblogs.com/stg609/articles/1231832.html
 
相关文章
相关标签/搜索