《HTTP权威指南》读书笔记1

URL语法

完整的URL是建立在由以下9个部分构成的通用格式上的。

1
<scheme>://<user>:<password>@<host>:<port>/<path>;<params>?<query>#<frag>

其中各个部分代表:

  • scheme(方案):使用的哪种协议;默认无
  • user(用户):用户名;默认匿名
  • password(密码):密码
  • host(主机):服务器主机名或点分IP地址
  • port(端口):服务器监听端口。不同协议,默认值不一样,HTTP默认80
  • path(路径):/分割的资源路径
  • params(参数):名/值对,使用;分割。
  • query(查询):名=值对,用&分割多个
  • frag(片段):小片资源的名字。在html就是一个锚点名了。自动从锚点开始显示。

HTTP报文格式

1.请求报文(request message)

1
2
3
4
<method> <request-URL> <version>
<headers>

<entity-body>

例如:

1
2
GET /images/blog/qunit-pic.png HTTP/1.0
Host: www.shenyanchao.cn

2.响应报文(request message)

1
2
3
4
<version> <status-code> <reason-phrase>
<headers>

<entity-body>

例如:

1
2
3
HTTP/1.1 200 OK
Content-Type: image/png
Content-Length: 18107

以上报文格式中,各个部分的描述如下:

  • method(方法):希望服务器对资源执行的动作。如GET,POST等。
  • request-URL(请求的URL):要请求的资源。
  • version(版本):报文使用的HTTP协议版本。
  • status-code(状态码):描述了请求过程中的状态。
  • reason-phrase(原因短语):状态码的可读版本。
  • header(首部):可以有0或多个首部。每个首部,名字跟着一个冒号,紧接着是空格,然后是一个值,最后是一个CRLF。
  • entity-body(实体的主题部分):任意数据组成的数据块。

HTTP方法

1.GET

请求服务器发送某个资源。请求无主体部分。

2.HEAD

与GET方法类似,但服务器在响应中只返回header。请求无主体部分,同时服务器也不会返回主体部分。使用HEAD方法,主要用于以下:

  • 在不获取资源的情况下了解资源的情况(比如其类型);
  • 通过查看响应中的状态码,判断某个对象是否存在。
  • 通过查看header,测试资源是否被修改了。

3.PUT

PUT方法用于向服务器写入文档。请求有主体部分。

4.POST

POST方法用于向服务器输入数据。经常用于表单提交。请求有主体部分。

5.TRACE

客户端发起一个请求时,这个请求可能要船防火墙、代理、网关或其他一些应用程序。每个中间点都可能修改原始HTTP请求。TRACE方法允许客户端在最终将请求发送给服务器时,看看它变成什么样子。简单说,就是TRACE方式会把服务器接受到的请求,返回给客户端。请求无主体部分。

6.OPTIONS

OPTIONS方法请求WEB服务器告知其支持的各种功能。可以询问服务器支持哪些方法,或者对某些特殊资源支持哪些方法。这位客户端提供了一种手段,使其不用访问那些资源就能判定访问各资源的最优方式。请求无主体部分。

7.DELETE

DELETE方法,请求服务器删除请求URL所指定的资源。请求无主体部分。

HTTP连接

HTTP通信都是由TCP/IP所承载的。HTTP连接实际上就是TCP连接及其使用规则,TCP连接是因特网上的可靠连接。TCP有著名的“三次握手”以及“四次挥手”来保证有效可靠的连接。
HTTP性能在很大程度上取决于底层TCP通道的性能。影响TCP性能主要有以下几个方面:

  • 客户端需要根据URI确定WEB服务器的IP和端口号。这依赖于DNS解析速度,有可能很慢。
  • 客户端与服务器端建立TCP连接有时延。如果并发大的话,时延更长。
  • 连接建立后,通过TCP管道发送HTTP请求,然后服务器读取报文并处理都耗费时间。
  • 服务器回送响应也花费时间。

1.TCP连接握手时延

由于3次握手的存在,很可能造成:小的HTTP事务可能在TCP建立上花费50%乃至更多的时间。这样很不划算了。

2.延迟确认

网络无法确保可靠的分组传输,因此TCP实现了自己的确认机制来确保数据的成功传输。每个TCP段都有一个序列号和数据完整性校验和。每个段的接收者收到完好的段,都会向发送者回送小的确认分组。如果发送者没有在指定的窗口时间内收到确认信息,发送者认为没发送成功,并重发数据。
由于确认报文很小,所以TCP允许在发往同方向的输出数据分组中对其进行“捎带”。TCP中称之为“延迟确认”。延迟确认算法在一个特定的窗口时间(100~200ms)内将输出确认放在缓冲区内,以寻找能够捎带它的数据分组。如果那段时间没没有,就单独发送。延迟确认算法会引入相当大的时延。

3.TCP慢启动

TCP数据传输的性能取决于TCP连接的使用时间。TCP连接随着时间进行自我调谐,防止因特网的突然过载和拥塞。因此新连接的传输速度会比已经调谐的连接慢一些。

4.Nagle算法与TCP_NODELAY

一个TCP段都至少装载了40个字节的标记和首部,如果TCP发送大量只包含少量的分组(一个字节),网络的性能就会严重下降。Nagle算法试图在发送一个分组前,将大量TCP数据绑定在一起来提高网络效率。但是这样也造成了不少时延,HTTP应用程序常常在自己的栈中设置参数TCP_NODELAY来禁用Nagle算法。

5.TIME_WAIT累积与端口耗尽

在四次挥手中,客户端关闭TCP连接时,会在内存维护一个小的控制块,用来记录最近所关闭的连接的IP地址和端口号。此时客户端处于TIME_WAIT状态,并维持2MSL(2分钟)的时间,确保这段时间内不会创建具有相同地址和端口号的新连接。这个时候问题就来了,在做性能测试的时候,很容易造成大量TIME_WAIT的连接,同时也不能新建新的连接了,因为无端口可用了。这也是增加时延的因素。可以考虑改小MSL。

HTTP状态码

整体范围 已定义范围 分类
100~199 100~101 信息提示
200~299 200~206 成功
300~399 300~305 重定向
400~499 400~415 客户端错误
500~599 500~505 服务器错误