HTTP请求是如何断开TCP连接的?

比如说:IE访问IIS,获取文件,肯定是要建立一个连接,这个连接在完成通讯后,是客户端Close了连接,还是服务端Close了连接。我用程序测模拟IE和IIS,都没有收到断开连接的消息,也就是都没有触发OnClose事件。我是用Socket建立的连接。如果两方面都没有主动断开连接,那么我猜测可能是传输的数据中有结束的标志,请问这个标志是怎样的?谢谢各位。

解决方案 »

不知道iis是怎么弄得http的回应包中有个字段通常是close
收到指定长度之后就应该断开的。

HTTP 你的意思是B/S模式的系统设计吧。
根本不存在保持连接这种说法。一个页面在刷新完闭之后,页面和服务器端即断开连接,两者不保持连接。
总感觉你是在说TCP、编程。如果是的话,双方都可以主动断开连接。

TO: akirya
其中传输的数据都是HTTP包,应该不会包含Close字段的。TO:minger909
我在做C/S的程序,用TCP的方式实现HTTP。您说的不保持连接,是对的,我就是想知道,不保持连接,是哪一方断开的?是IIS发送完数据进行Close的呢,还是IE接收完数据进行Close的呢。不解,也没有测试出来,就是没有收到OnClose的事件。To:在什么地方,什么时候来处理CExpcetion呢?

HTTP/1.1都把TCP作为底层的传输协议。HTTP客户端首先发起建立与服务器TCP连接。一旦建立连接,浏览器进程和服务器进程就可以通过各自的套接字来访问TCP。如前所述,客户端套接字是客户进程和TCP连接之间的“门”,服务器端套接字是服务器进程和同一TCP连接之间的“门”。客户往自己的套接字发送HTTP请求消息,也从自己的套接字接收HTTP响应消息。类似地,服务器从自己的套接字接收HTTP请求消息,也往自己的套接字发送HTTP响应消息。客户或服务器一旦把某个消息送入各自的套接字,这个消息就完全落入TCP的控制之中。TCP给HTTP提供一个可靠的数据传输服务;这意味着由客户发出的每个HTTP请求消息最终将无损地到达服务器,由服务器发出的每个HTTP响应消息最终也将无损地到达客户。我们可从中看到分层网络体系结构的一个明显优势——HTTP不必担心数据会丢失,也无需关心TCP如何从数据的丢失和错序中恢复出来的细节。这些是TCP和协议栈中更低协议层的任务。  TCP还使用一个拥塞控制机制。该机制迫使每个新的TCP连接一开始以相对缓慢的速率传输数据,然而只要网络不拥塞,每个连接可以迅速上升到相对较高的速率。这个慢速传输的初始阶段称为缓启动(slow start)。  需要注意的是,在向客户发送所请求文件的同时,服务器并没有存储关于该客户的任何状态信息。即便某个客户在几秒钟内再次请求同一个对象,服务器也不会响应说:自己刚刚给它发送了这个对象。相反,服务器重新发送这个对象,因为它已经彻底忘记早先做过什么。既然HTTP服务器不维护客户的状态信息,我们于是说HTTP是一个无状态的协议(stateless protocol)。HTTP协议状态码的含义   号码 含义 
----------------------------------------- 
"100" : Continue 
"101" : witching Protocols 
"200" : OK 
"201" : Created 
"202" : Accepted 
"203" : Non-Authoritative Information 
"204" : No Content 
"205" : Reset Content 
"206" : Partial Content 
"300" : Multiple Choices 
"301" : Moved Permanently 
"302" : Found 
"303" : See Other 
"304" : Not Modified 
"305" : Use Proxy 
"307" : Temporary Redirect 
"400" : Bad Request 
"401" : Unauthorized 
"402" : Payment Required 
"403" : Forbidden 
"404" : Not Found 
"405" : Method Not Allowed 
"406" : Not Acceptable 
"407" : Proxy Authentication Required 
"408" : Request Time-out 
"409" : Conflict 
"410" : Gone 
"411" : Length Required 
"412" : Precondition Failed 
"413" : Request Entity Too Large 
"414" : Request-URI Too Large 
"415" : Unsupported Media Type 
"416" : Requested range not satisfiable 
"417" : Expectation Failed 
"500" : Internal Server Error 
"501" : Not Implemented 
"502" : Bad Gateway 
"503" : Service Unavailable 
"504" : Gateway Time-out 
"505" : HTTP Version not supported

非持久连接和持久连接 HTTP既可以使用非持久连接(nonpersistent connection),也可以使用持久连接(persistent connection)。HTTP/1.0使用非持久连接,HTTP/1.1默认使用持久连接。  非持久连接  让我们查看一下非持久连接情况下从服务器到客户传送一个Web页面的步骤。假设该贝面由1个基本HTML文件和10个JPEG图像构成,而且所有这些对象都存放在同一台服务器主机中。 再假设该基本HTML文件的URL为:www.yesky.com/somepath/index.html。  下面是具体步骡:  1.HTTP客户初始化一个与服务器主机www.yesky.com中的HTTP服务器的TCP连接。HTTP服务器使用默认端口号80监听来自HTTP客户的连接建立请求。  2.HTTP客户经由与TCP连接相关联的本地套接字发出—个HTTP请求消息。这个消息中包含路径名/somepath/index.html。  3.HTTP服务器经由与TCP连接相关联的本地套接字接收这个请求消息,再从服务器主机的内存或硬盘中取出对象/somepath/index.html,经由同一个套接字发出包含该对象的响应消息。  4.HTTP服务器告知TCP关闭这个TCP连接(不过TCP要到客户收到刚才这个响应消息之后才会真正终止这个连接)。  5.HTTP客户经由同一个套接字接收这个响应消息。TCP连接随后终止。该消息标明所封装的对象是一个HTML文件。客户从中取出这个文件,加以分析后发现其中有10个JPEG对象的引用。  6.给每一个引用到的JPEG对象重复步骡1-4。  浏览器在接收web页面的同时把它显示给用户。不同的浏览器可能会以略有不同的方式解释(也就是向用户显示)同一个web页面。HTTP与客户如何解释Web页面没有任何关系,其规范([RFC 1945]和[RFC 2616I)仅仅定义HTTP客户程序和服务器程序之间的通信协议。  上述步骤之所以称为使用非持久连接,原因是每次服务器发出一个对象后,相应的TCP连接就被关闭,也就是说每个连接都没有持续到可用于传送其他对象。每个TCP连接只用于传输一个请求消息和一个响应消息。就上述例子而言,用户每请求一次那个web页面,就产生11个TCP连接。  在上述步骡中,我们有意不说清客户是通过10个串行的TCP连接先后取得所有JPEG对象,还是通过并行的TCP连接同时取得其中某些JPEG对象。实际上,现今的浏览器允许用户通过配置来控制并行连接的程度。大多数浏览器默认可以打开5到10个并行的TCP连接,每个连接处理一个请求—响应事务。用户要是喜欢,可以把最大并行连接数设为l,那样的话这10个连接是串行地建立的。我们使用并行连接可以缩短响应时间。

HTTP消息格式  HTTP规范1.0[RPcl945]和1.1[RFC 2616]定义了HTTP消息的格式。HTTP消息分为请求消息和响应稍息两类。下面我们分别进行介绍。  HTTP请求消息  下面是一个典型的HTTP请求消息:  GET /somedir/page.html H7TP/1.1 
  Host:www.yesky.com 
  Connection:close 
  User-agent:Mozilla/4.0 
  Accept-language:zh-cn 
  (额外的回车符和换行符)

  仔细检查这个简单的请求消息,我们可从中学到不少东西。首先,这个消息是用普通的ASCII文本书写的。其次,这个消息共有5行(每行以一个回车符和一个换行符结束),最后一行后面还有额外的一个回车特和换行符。当然,一个请求消息可以不止这么多行,也可以仅仅只有一行。该请求消息的第一行称为请求行(request line),后续各行都称为头部行(header)。请求行有3个宁段:方法字段、URL字段、HTTP版本宇段。方法字段有若干个值可供选择,包括GET、POST和HEAD。HTTP请求消息绝大多数使用GET方法,这是浏览器用来请求对象的方法,所请求的对象就在URL字段中标识。本例表明浏览器在请求对象/somedir/page.html。版本字段是不言自明的;本例中浏览器实现的是HTTP/1.1版本。  现在看一下本例中的各个头部行。头部行Host:www.yesky.com定存放所请求对象的主机。请求消息中包含头部Connection:close是在告知服务器本浏览器不想使用持久连接;服务器发出所请求的对象后应关闭连接。尽管产生这个请求消息的浏览器实现的是HTTP/1.1版本,它还是不想使用持久连接。User-agent头部行指定用户代理,也就是产生当前请求的浏览器的类型。本例的用户代理是Mozilla/4.0,它是Nelscape浏览器的一个版本。这个头部行很有用,因为服务器实际上可以给不同类型的用户代理发送同一个对象的不同版本(这些不同版本位用同一个URL寻址)。最后,Accept-languag:头部行指出要是所请求对象有简体中文版本,那么用户宁愿接收这个版本;如果没有这个语言版本,那么服务器应该发送其默认版本。Accept-languag:仅仅是HTTP的众多内容协商头部之一。-----------------------
参考:了解WWW服务与HTTP协议
http://biz.chinabyte.com/209/2151709_2.shtml

可以是任何一方主动断开。
就像你编过的CS其他程序一样。
一旦一方确认信息发送完闭,就可以Close()。另一方同样会接收到FD_CLOSE消息的。只要在Close()中处理你的释放工作就可以了。

你可以在用程序测试的时候,用netstat查看一下当前的TCP连接,如果出现close_wait状态,则说明套接字是“被动关闭的”。如果出现“time_wait"状态,说明套接字是“主动关闭的”。TCP结束的过程如下:Server Client-------------- FIN --------------> server: fin_wait_1<------------- ACK --------------- client: close_wait server:fin_wait_2<------------- FIN --------------- client发出fin之后就关闭 -------------- ACK -------------> server发出ack后进入time_wait状态正常情况下,应该是IIS主动关闭连接的。如果客户端(IE)主动关闭了连接,那么就会在客户端出现time_wait状态。
Time_Wait的默认时间是2倍的MLS,就是240秒钟。MLS是TCP 片在网上的最长存活时间。
TIME_Wait的主要作用是保证关闭的TCP端口不立即被使用。因为当网络存在延迟时,可能当某个端口被关闭后,网络中还有一些重传的TCP片在发向这个端口,如果这个端口立即建立新的TCP连接,则可能会有影响。所以使用2倍的MSL时间来限制这个端口立即被使用。
现在的问题在于,4分钟的时间有点长。大量的Time_wait会带来一些不好的影响,首先每个TCP连接都各自有个数据结构,叫TCP Control Block.Time_wait的时候这个数据结构没有被释放。所以当有太多的TCP连接时,内存可能会被占用很多。
你可以权衡一下,然后决定是由客户端还是服务端主动断开连接。

我记得这个close是在http的头部信息,和 200 OK是一样的.

http头里有个connection的关键字的,如果是close状态,那就是服务器主动关闭了连接

汗,楼主问的问题HTTP的细节问题,怎么这么多人和TCP拉上了。HTTP是请求-响应模式的,而有时候会以关闭连接来表示数据发送完毕,所以在其协议定义中有个字段来表示谁关闭连接。HTTP1.0/1.1都支持持久连接在1.1中,如果客户端在请求中使用Connection: Close ,服务器端就会在发送完响应后从容关闭连接。但是即使客户端要求使用持久连接,但是服务器也有权在响应完请求后主动关闭连接,但是要在响应头在包含Connection: Close 。1.0和1.1一样,但是HTTP1.1默认是持久连接的,而且HTTP1.0不是。
刚才查资源得的结果,有错请指出。

HTTP是应用层协议,在TCP之上才能工作。真正建立连接和断开连接都是由TCP来完成的,所以说到连接问题,自然要和TCP扯上了。

感谢大家。讨论的很细,我想很多朋友可以通过该帖子了解一下HTTP。HTTP是建立在TCP上的超文本传输协议。

写过http服务器考虑两种方式:持久连接和非持久连接
这两种连接方式首先取决于http服务器是否支持
标准HTTP服务器支持这两种方式,特殊HTTP服务器只支持非持久连接持久连接和非持久连接都是服务器端/IE端均可控制的
控制方式是用Connection : xxxxx字段
Connection: Close告诉对方这次传输结束以后关闭socket
Connection: Alive告诉对方这次传输结束以后可以再次利用这个socket以下模拟持久连接:
IE Request 包含Connection:Alive -> HTTP服务器返回网页,HTTP头部包含 Connection: Alive -> IE在HTTP头部描述的字节数接收完毕以后提交下一个请求,其中继续包含 Connection: Alive -> HTTP服务器继续返回网页以下模拟非持久连接:
IE Request 包含Connection:Alive -> HTTP服务器返回网页,HTTP头部包含 Connection: Close,表示自己无视IE的Alive请求 -> IE在HTTP头部描述的字节数接收完毕以后关闭socket需要说明的是,对于持久连接,Server返回的HTTP头部必须包含一个内容大小字段用来确定IE需要接收的data字节,否则持久连接就会发生问题,因为IE无法获知自己什么时候应该发送下一个请求.所以无法确定data字段大小的时候,服务器必须在适当的时候(通常是data发送结束)主动关闭socket

建议不要用mfc,好象可移植性不行.

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值