参考:《HTTP权威指南》
所有HTTP客户端、服务器或者代理都可以任意时刻关闭一条TCP传输连接。但是服务器永远无法确定它关闭“空闲”连接的那一刻,在线路那一头的客户端有没有数据要发送。
每条HTTP响应都应该有精确的Content-Length首部,用来描述响应主体的尺寸。如果老的HTTP服务器省略了Content-Length或者包含错误的长度指示,这样就要一来服务器发出连接关闭来说明数据的真是末尾。
如果一个事务,不管是执行一次还是很多次,得到的结果都相同,这个事务就是幕等的。GET,HEAD,PUT,DELETE,TRACE,OPTIONS方法都具有幕等性。POST方法时非幕等的。要发送一条非幕等请求,就需要等待来自前一条请求的响应状态。用户Agent代理可能会让用户来选择是否对请求进行重试,但是一定不能自动重试非幕等方法或序列。大多数浏览器都会重载一个缓存的POST响应时提供一个对话框,询问用户是否希望再次发起事务处理。
正常关闭连接
1)完全关闭
将TCP连接的输入和输出信道都关闭了。入套接字调用close()
2)半关闭
单独关闭输入或输出信道。如,套接字调用shutdown()
当应用程序开始与很多其他类型的HTTP客户端、服务器和代理进行对话且开始使用管道化持久连接时,使用半关闭连接来防止对等实体收到非预期的写入错误。关闭输入信道比较危险,除非你知道另一端不打算再发送其他数据了。如果另一端向你已关闭的输入信道发送数据,操作系统就会向另一端的机器回送一条TCP“连接被对端重置”的报文。大部分操作系统都会将这种情况作为很严重的错误处理,删除对端还未读取的所有缓存数据。
所以,实现正常关闭的应用程序首先应该关闭它们的输出信道,然后等待连接另一端的对等实体关闭它的输出信道。当两端都告诉对方它们不会在发送任务数据之后,连接就是被完全关闭。然后,无法确保对等实体会实现半关闭,或对其进行检查,因此想要正常关闭连接的应用程序应该先关闭其输出信道,然后周期性得检查其输入信道的状态。如果在一定时间内对端没有关闭输入信道,应用程序可以强制关闭连接,以节省资源。