目录
  1. 1. Http
    1. 1.0.1. 概念
    2. 1.0.2. 状态码
    3. 1.0.3. 结构
      1. 1.0.3.1. 请求报文
      2. 1.0.3.2. 返回报文
    4. 1.0.4. Http请求方式
      1. 1.0.4.1. Get
      2. 1.0.4.2. Post
      3. 1.0.4.3. Put
      4. 1.0.4.4. Delete
      5. 1.0.4.5. Post和Get区别
    5. 1.0.5. HTTP是基于TCP/IP的
      1. 1.0.5.1. TCP 三次握手
      2. 1.0.5.2. TCP 四次挥手
    6. 1.0.6. Http 版本
      1. 1.0.6.1. http1.0
      2. 1.0.6.2. http1.1
      3. 1.0.6.3. http2.0
Http相关

看了老是忘系列

Http

概念

超文本传输协议 HyperText Transfer Protocol

状态码

· 1xx

1xx 类状态码属于提示信息,是协议处理中的⼀种中间状态,实际⽤到的⽐较少。

· 2xx

2xx 类状态码表示服务器成功处理了客户端的请求,也是我们最愿意看到的状态。
· 3xx

3xx 类状态码表示客户端请求的资源发送了变动,需要客户端⽤新的URL新发送请求获取资源,也就是重定向。

· 4xx

4xx 类状态码表示客户端发送的报⽂有误,服务器⽆法处理,也就是错误码的含义。

· 5xx

5xx 类状态码表示客户端请求报⽂正确,但是服务器处理时内部发⽣了错误,属于服务器端的错误码

结构

请求报文

1
2
3
4
5
6
7
8
9
POST /xxx/xxx/ HTTP/1.1
Content-Type: application/x-www-form-urlencoded
Content-Length: 450
Host: sovwcwsfm.com
Accept-Encoding: gzip
User-Agent: okhttp/3.14.8
Connection: keep-alive

encryptData=xYLXcXG0WN35KakH8Q8u3WtN79TzB6a3N6SccGC9L1gQxta9IY040cc7zY2w%2FdMAM%2BQbhzs%2B0KufSHtooIPMyBprMNyIuMwqZrKd7rQdmEiXtF6DjMUBhOLLjymFlMv8vuCH9T%2BAdox%2BzAOMWoKrEMU8haVBkjhHDA7HIyFfewW9np4Y%2FmpENeYzx86VYE1w%2Bf7F11VMcJxN%2BH23qvbDem7okz4fkyF8D%2FU349hf6TsjJDM1Z4eWy%2BpwaPM60Fxe640An6lqL4CbMCTPniqLr4HtyiomjIV7iyxJEJ9z5qj6L5JuAH2VkrEsK6G4itefWqy4Al0VDZVkE2%2BcVnwlU64WVQP1%2FQDOUrSISKlJYYqJ8LEU1nDAahkVG70drlu%2BAzRtNWfwkbGUuImzydTZXQ%3D%3D

POST 为请求方法, /xxx/xxx/ 为请求路径, HTTP/1.1 为http版本

Content-Type、Content-Length、Host、Accept-Encoding、User-Agent、Connection 均为请求头 Head中的内容

请求头换行内容为Request Body内容

返回报文

1
2
3
4
5
6
7
8
9
10
11
12
HTTP/1.1 200 OK
Date: Thu, 05 Nov 2019 08:58:07 GMT
Server: Apache/2.4.25 (Unix) PHP/5.6.30
X-Powered-By: PHP/5.6.30
Access-Control-Allow-Origin: *
Access-Control-Allow-Headers: X-Requested-With,X_Requested_With
Content-Length: 104
Keep-Alive: timeout=5, max=100
Content-Type: application/json; charset=utf-8
Connection: keep-alive

{"respCode":"00","respDesc":"success","respData":{"forumInfo":null,"incomeLink":null,"businessLink":""}}

HTTP/1.1 为http版本,200 请求结果状态码, OK 请求结果描述

剩下的为返回报文的 头部信息

请求头换行内容为Result Body内容

Http请求方式

Get

⽤于获取资源、对服务器数据不进⾏修改、不发送 Body、GET把参数包含在URL

1
GET /xxx/xxx?aaa=111 HTTP/1.1

Post

⽤于增加或修改资源发送给服务器的内容写在 Body ⾥⾯

1
2
3
4
5
6
7
8
9
POST /xxx/xxx/ HTTP/1.1
Content-Type: application/x-www-form-urlencoded
Content-Length: 450
Host: sovwcwsfm.com
Accept-Encoding: gzip
User-Agent: okhttp/3.14.8
Connection: keep-alive

encryptData=this is post data

Put

和POST 用法一致

Delete

⽤于删除资源,不发送 Body

1
DELETE /xxx/xxx?id=111 HTTP/1.1

HEAD 和 GET 使⽤⽅法完全相同, 和 GET 唯⼀区别在于,返回的响应中没有 Body

当然还有PATCH 这种。平常用到get,post 比较多。 其他的用在RESTful API 中比较多

Post和Get区别

  1. GET在浏览器回退时是无害的,而POST会再次提交请求。
  2. GET产生的URL地址可以被Bookmark,而POST不可以。
  3. GET请求会被浏览器主动cache,而POST不会,除非手动设置。
  4. GET请求只能进行url编码,而POST支持多种编码方式。
  5. GET请求参数会被完整保留在浏览器历史记录里,而POST中的参数不会被保留。
  6. GET请求在URL中传送的参数是有长度限制的,而POST么有。
  7. 对参数的数据类型,GET只接受ASCII字符,而POST没有限制。
  8. GET比POST更不安全,因为参数直接暴露在URL上,所以不能用来传递敏感信息。
  9. GET参数通过URL传递,POST放在Request body中。
  10. GET方式的请求,浏览器会把http header和data一并发送出去,服务器响应200(返回数据);
    而对于POST,浏览器先发送header,服务器响应100 continue,浏览器再发送data,服务器响应200 ok(返回数据)。
    GET产生一个TCP数据包;POST产生两个TCP数据包。

HTTP是基于TCP/IP的

HTTP是基于TCP/IP的,所以HTTP的请求就是TCP/IP的连接过程。

TCP是什么?

  1. TCP 提供一种面向连接的、可靠的字节流服务
  2. 在一个 TCP 连接中,仅有两方进行彼此通信。广播和多播不能用于 TCP
  3. TCP 给数据分节进行排序,并使用累积确认保证数据的顺序不变和非重复
  4. TCP 使用滑动窗口机制来实现流量控制,通过动态改变窗口的大小进行拥塞控制

TCP 为什么可靠

TCP 可靠不是保证数据一定会被对方接收到,因为这是不可能的。TCP 能够做到的是,如果有可能,就把数据递送到接收方,否则就(通过放弃重传并且中断连接这一手段)通知用户。因此准确说 TCP 也不是 100% 可靠的协议,它所能提供的是数据的可靠递送或故障的可靠通知。

TCP链接需要经过三次握手,断开连接需要经过四次挥手

TCP 三次握手

所谓三次握手(Three-way Handshake),是指建立一个 TCP 连接时,需要客户端和服务器总共发送3个包。

三次握手的目的是连接服务器指定端口,建立 TCP 连接,并同步连接双方的序列号和确认号,交换 TCP 窗口大小信息。在 socket 编程中,客户端执行 connect() 时。将触发三次握手

  1. 第一次握手(SYN=1, seq=x):

    客户端发送一个 TCP 的 SYN 标志位置1的包,指明客户端打算连接的服务器的端口,以及初始序号 X,保存在包头的序列号(Sequence Number)字段里。

    发送完毕后,客户端进入 SYN_SEND 状态。

    (啊喂,胖胖 是我 你在嘛?)

  2. 第二次握手(SYN=1, ACK=1, seq=y, ACKnum=x+1):

    服务器发回确认包(ACK)应答。即 SYN 标志位和 ACK 标志位均为1。服务器端选择自己 ISN 序列号,放到 Seq 域里,同时将确认序号(Acknowledgement Number)设置为客户的 ISN 加1,即X+1。 发送完毕后,服务器端进入 SYN_RCVD 状态。

    (诶 我是胖胖 我在的)

  3. 第三次握手(ACK=1,ACKnum=y+1)

    客户端再次发送确认包(ACK),SYN 标志位为0,ACK 标志位为1,并且把服务器发来 ACK 的序号字段+1,放在确定字段中发送给对方,并且在数据段放写ISN的+1

    发送完毕后,客户端进入 ESTABLISHED 状态,当服务器端接收到这个包时,也进入 ESTABLISHED 状态,TCP 握手结束。

    (噢,胖胖 待会快递到)

TCP 四次挥手

TCP 的连接的拆除需要发送四个包,因此称为四次挥手(Four-way handshake),也叫做改进的三次握手。客户端或服务器均可主动发起挥手动作,在 socket 编程中,任何一方执行 close() 操作即可产生挥手操作

  1. 第一次挥手(FIN=1,seq=x)

    假设客户端想要关闭连接,客户端发送一个 FIN 标志位置为1的包,表示自己已经没有数据可以发送了,但是仍然可以接受数据。

    发送完毕后,客户端进入 FIN_WAIT_1 状态。

    (我:胖胖, 我想睡觉了, 等胖胖批复中。。。 = FIN_WAIT_1)

  2. 第二次挥手(ACK=1,ACKnum=x+1)

    服务器端确认客户端的 FIN 包,发送一个确认包,表明自己接受到了客户端关闭连接的请求,但还没有准备好关闭连接。

    发送完毕后,服务器端进入 CLOSE_WAIT 状态,客户端接收到这个确认包之后,进入 FIN_WAIT_2 状态,等待服务器端关闭连接。

    (胖胖:噢知道了,李佳琦呆会就要上商家我们要买的餐巾纸了 下单就完就睡。。。 胖胖看直播抓紧下单=CLOSE_WAIT 我等她下完单 = FIN_WAIT_2)

  3. 第三次挥手(FIN=1,seq=y)

    服务器端准备好关闭连接时,向客户端发送结束连接请求,FIN 置为1。

    发送完毕后,服务器端进入 LAST_ACK 状态,等待来自客户端的最后一个ACK。

    (胖胖:好勒 我买好了,睡觉把,你呢 = LAST_ACK)

  4. 第四次挥手(ACK=1,ACKnum=y+1)

    客户端接收到来自服务器端的关闭请求,发送一个确认包,并进入 TIME_WAIT状态,等待可能出现的要求重传的 ACK 包。

    服务器端接收到这个确认包之后,关闭连接,进入 CLOSED 状态。

    客户端等待了某个固定时间(两个最大段生命周期,2MSL,2 Maximum Segment Lifetime)之后,没有收到服务器端的 ACK ,认为服务器端已经正常关闭连接,于是自己也关闭连接,进入 CLOSED 状态。

    (我:好勒 睡觉 = CLOSED)

Http 版本

HTTP有这么几个重要的版本 HTTP1.0 HTTP1.1 HTTP2.0
主要用到的还是HTTP1.1

http1.0

无状态:服务器不跟踪不记录请求过的状态
无连接:浏览器每次请求都需要建立tcp连接
无状态
对于无状态的特性可以借助cookie/session机制来做身份认证和状态记录

无连接
无连接导致的性能缺陷有两种:

  1. 无法复用连接
    每次发送请求,都需要进行一次tcp连接(即3次握手4次挥手),使得网络的利用率非常低

  2. 队头阻塞
    http1.0规定在前一个请求响应到达之后下一个请求才能发送,如果前一个阻塞,后面的请求也给阻塞的

http1.1

为了解决http1.0的性能缺陷,http1.1出现了

http1.1特性:
长连接:新增Connection字段,可以设置keep-alive值保持连接不断开
管道化:基于上面长连接的基础,管道化可以不等第一个请求响应继续发送后面的请求,但响应的顺序还是按照请求的顺序返回
缓存处理:新增字段cache-control
断点传输
长连接
http1.1默认保持长连接,数据传输完成保持tcp连接不断开,继续用这个通道传输数据

管道化
基于长连接的基础,我们先看没有管道化请求响应:

tcp没有断开,用的同一个通道

请求1 > 响应1 –> 请求2 > 响应2 –> 请求3 > 响应3
管道化的请求响应:

请求1 –> 请求2 –> 请求3 > 响应1 –> 响应2 –> 响应3
即使服务器先准备好响应2,也是按照请求顺序先返回响应1

虽然管道化,可以一次发送多个请求,但是响应仍是顺序返回,仍然无法解决队头阻塞的问题

缓存处理
当浏览器请求资源时,先看是否有缓存的资源,如果有缓存,直接取,不会再发请求,如果没有缓存,则发送请求

通过设置字段cache-control来控制

断点传输
在上传/下载资源时,如果资源过大,将其分割为多个部分,分别上传/下载,如果遇到网络故障,可以从已经上传/下载好的地方继续请求,不用从头开始,提高效率

在 Header 里两个参数实现的,客户端发请求时对应的是 Range 服务器端响应时对应的是 Content-Range

host域
HTTP1.0 不支持,因为之前觉得一台服务器只有一个地址 HTTP2.0 支持,请求消息和响应消息都支持

http2.0

二进制分帧
多路复用: 在共享TCP链接的基础上同时发送请求和响应
头部压缩
服务器推送:服务器可以额外的向客户端推送资源,而无需客户端明确的请求
二进制分帧
将所有传输的信息分割为更小的消息和帧,并对它们采用二进制格式的编码

多路复用
基于二进制分帧,在同一域名下所有访问都是从同一个tcp连接中走,http消息被分解为独立的帧,乱序发送,服务端根据标识符和首部将消息重新组装起来

区别
http1.0 到http1.1的主要区别,就是从无连接到长连接
http2.0对比1.X版本主要区别就是多路复用

文章作者: Fibonacci
文章链接: http://sovwcwsfm.com/blog/page/202006171911.html
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Blog