详解 HTTP 协议
详解 HTTP 协议
- 引言
- 1. 什么是 HTTP
- (1) 超文本
- (2) 传输
- (3) 协议
- 2. 理解 HTTP
- (1) HTTP 协议属于应用层
- (2) HTTP 协议是一发一收的模型
- (3) HTTP 协议是文本格式的协议
- 一、理解 URL
- 1. URL格式
- 注意
- 2. URL encode
- 注意
- 二、HTTP 请求
- HTTP 请求的基本格式
- 1. GET 方法
- 展示
- 注意
- 2. POST 方法
- 展示
- 3. GET 和 POST 的区别( 经典面试题 )
- 注意
- 4. HTTP 请求的其他方法
- 5. 认识 HTTP 请求中的报头
- (1) Host
- (2) Content-Length
- (3) Content-Type
- (4) User-Agent
- (5) Referer
- (6) Cookie
- 6. body 正文
- 三、HTTP 响应
- HTTP 响应的基本格式
- 1. 认识状态码(经典面试题)
- (1) 200 OK
- (2) 404 Not found
- (3) 403 Forbidden
- (4) 405 Method Not Allowed
- (5) 500 Internal Server Error
- (6) 504 Gateway Timeout
- (7) 302 Move temporarily
- (8) 301 Move parmanently
- 状态码总结
- 2. 认识 HTTP 响应中的报头
- (1) Content-Type
- 3. body 正文
- 四、拓展
- 1. 多使用 fiddler 抓包
- 2. CtrI + F5 和 F5
引言
1. 什么是 HTTP
HTTP:Hyper Text Transfer Protocol(超文本传输协议)
(1) 超文本
看到超文本,就可以联想到 HTML
HTML:Hypertext Markup Language ( 超文本标记语言 )
在早期的时候,HTTP 被设计出来就是为了下载 HTML,而超文本的含义,顾名思义,它并不像早期的报纸一样,只有文字和图片的排版,它更有视频、音频、链接、动态效果…等这些特殊的信息。
超文本是用超链接的方法,将各种不同空间的文字信息组织在一起的网状文本。(来源于:百度百科)
按我个人的理解,超文本使得当代较于信息初代而言,就是让信息变得更加花里胡哨了,让信息换了不同的形式呈现在了计算机用户的面前。
(2) 传输
传输主要指的是两台计算机进行信息的交互,靠什么交互?肯定就是网络了。
客户端与服务器这样的传输模型最为常见,一般来说,客户端需要先发送请求,服务器之后再返回响应。
(3) 协议
协议就是一种约定,前面的博客有提到,不再赘述。
2. 理解 HTTP
(1) HTTP 协议属于应用层
可以看到,HTTP 协议属于应用层,应用层也是 开发人员 / 程序员 与其打交道最多的一层,这一层与 Web 开发紧密相连。
(2) HTTP 协议是一发一收的模型
此外,在网络通信中,基本上都是客户端与服务器之间的联系。它们之间的沟通一般分为:一发一收、多发一收、一发多收、多发多收。
而 HTTP 协议就是一发一收的这种模型,当然,这也是最常见的一种模型。
(3) HTTP 协议是文本格式的协议
HTTP 协议是一种文本格式的协议,所以不能直接传输二进制数据,如果是图片、视频、音频…等,需要对这些数据进行特殊编码,再进行传输。
一、理解 URL
URL:Uniform Resource Locator ( 统一资源定位器 )
URL 其实就是,俗称的 " 网址 "。互联网上的每个文件都有一个唯一的URL,它是因特网的万维网服务程序上用于指定信息位置的表示方法。URL 的详细规则由因特网标准RFC1738 进行了约定。
1. URL格式
① 协议方案名:URL支持很多种协议,例如:http, https, ftp, file…
② 登录信息(认证):现在基本已经废弃了登录信息格式;现代的做法就是:进入网页后,要求另外输入用户名和密码。
③ 服务器地址:这里不带 /。服务器地址既可以是域名,也可以是 IP 地址。
例如:www.sogou.com ( 这是一个域名,但域名本质上就是一个 IP 地址,写域名的本质只是为了方便普通用户使用,所以域名并不是硬性条件。 )
④ 服务器端口号:可写可不写,如果不写端口号,浏览器就会给一个默认端口号,http 默认值 80,https 默认值 443.
⑤ 带层次的文件路径:表示访问服务器上不同的资源,例如:HTML,CSS,JS…
⑥ 查询字符串:( query string ),查询字符串表示,浏览器给服务器传递的一些参数,开发人员可以自定义参数的内容。这些参数基本都是以键值对的方式来组织的。
查询字符串以 ? 作为起始标志。
键值对之间,用 & 分割,键和值之间,使用 = 分割
而每个键值对是什么意思,这是根据开发人员自定义来的,所以不同网页、不同公司,很大可能,键值对含义不同。
⑦ 片段标识符:不常用,通常用来定位到一个 HTML 页面中的某个具体位置。
注意
上面七个组成 URL 的要素,其实每一个都可以省略,这需要根据不同的场景来进行设定。
例如:
https://www.sogou.com/
这是我们平时登录的搜狗网站,可以看到:URL 只由协议名 https 和 域名组成,其他皆省略,那么默认端口号就是 443,路径就是 / ,表示根路径。而其他的几个元素,本来就是可有可无的。
2. URL encode
在上面的 URL 格式中,我们理解了:像【 / ? : 】等这样的字符,已经被 URL 当做特殊意义理解了,因此这些字符不能随意出现。那么,某个参数中需要带有这些特殊字符,就必须先对特殊字符进行转义。这就和 Java 中的转义字符是一个道理,但是这里的转义方式却大不相同。
特殊字符 > 转义字符: URL encode
转义字符 > 原字符: URL decode
例如:我们使用搜狗搜索【 ?+ 】这类字符的时候,就会转义成下面的形式,当然,中文也会被转义。字符遵循 ASCII 码的十六进制转换;中文遵循 UTF-8 编码转换。
注意
虽然浏览器会自动对这里的特殊符号进行 encode,但有的时候,我们需要自己手动构造的 URL,浏览器不一定支持自动的 encode。所以为了稳妥起见,我们自己构造URL中,若带有特殊符号, 一定要手动的 encode,否则就可能请求发送失败。
试想:广大电脑的使用者就是客户端,当用户上网查资料的时候,如果给服务器发送请求,但是因为特殊字符的原因,导致请求失败,那么服务器自然就无法响应,长此以往,这必然是一个重大缺陷。可能的一个原因就是:用户与用户之间使用的浏览器不同,有些非主流的浏览器并不能很好地兼容特殊字符…
例如:在前端的 HTML 中,有一个 a 标签:
二、HTTP 请求
HTTP 请求的基本格式
以下面图片为例:
HTTP 请求的基本格式一般分为四个部分:
① 首行
HTTP 请求的首行十分有特点:
【请求方法】+ 空格 +【URL】+ 空格 +【版本号】
② header 请求头:每一行都是一个键值对。
③ 空行
④ 正文 body
1. GET 方法
GET 是最常用的 HTTP 方法,常用于获取服务器上的某个资源。
哪些情况可以构造出 HTTP GET 请求呢?
① 在浏览器中直接输入 URL
② 另外,HTML 中的 link, img, script 等标签,也会触发 GET 请求。
③ 后面我们还会学习,使用 JavaScript 中的 ajax,也能构造 GET 请求。
④ form 表单
⑤ 使用 Java 代码 / 其他库
⑥ 通过 linux 下的 wget / curl
⑦ 通过第三方工具,postman 这类工具。
展示
我们在 chrome 浏览器中直接输入 URL,以搜狗首页为例,再通过抓包后,为我们呈现的请求。观察 GET 方法:
① 首行的第一部分为 GET.
② GET 后面跟了一个空格,空格后跟了当前的 URL,当前的 URL 的 【query string 】为空,这是因为我们并没有通过搜狗搜索信息。当我们搜索信息的时候,当然就不为空了。
③ header 部分有若干个键值对结构。
④ 一般给服务器发送请求情况下,GET 对应的 body 部分都为空。但也可以自己构造一个 body 不为空的请求,这需要根据不同的场景,然而,这种 body 不为空的场景较为少见。
注意
关于 GET 请求的 URL 长度问题:
HTTP 协议由 RFC 2616 标准定义,标准原文中明确说明: " Hypertext Transfer Protocol – HTTP/1.1," does not specify any requirement for URL length.
即没有对 URL 的长度有任何的限制。
然而,实际 URL 的长度取决于浏览器的实现和 HTTP 服务器端的实现。不同的浏览器设定的 URL 最大长度可能是不同的,但当代主流浏览器支持的 URL 最大长度一般都很长。
2. POST 方法
POST 方法也是一种常见的方法。多用于提交用户输入的数据给服务器 ( 例如登陆页面 )。POST 方法可以通过 HTML 中的 form 标签构造 POST 请求,也可以使用 JavaScript 的 ajax 也构造 POST 请求。
展示
我们在 chrome 浏览器中登录 QQ 邮箱,再通过 fiddler 抓包后,为我们呈现的请求。观察 POST 方法:
① 首行的第一部分为 POST.
② POST 后面跟了一个空格,空格后跟了当前的 URL。当前的 URL 的 【query string 】为空。因为 POST 的 【query string 】一般就为空,当然,开发人员也可以设计不为空。
③ header 部分有若干个键值对结构。
④ 一般给服务器发送请求情况下,POST 对应的 body 部分不为空。当然,这并不是绝对的。因为 body 中的内容是根据开发人员自己设定的,换句话说,其中的代码逻辑,只有开发人员知道。
3. GET 和 POST 的区别( 经典面试题 )
答:
HTTP 协议中的各个方法之间,尤其是 GET 和 POST ,这两者并没有本质的区别。但依然存在细微的差别,然而这些细微的差别可有可无,根据自定义情况设定。
细节上的差别,例如:
① 数据位置:一般来说,GET 请求习惯将自定义数据放到 【query string】, POST 请求则是把自定义数据放入 正文body.
② 语义区别:一般来说,GET 请求用于 获取数据,POST 请求用于提交数据。
③ 幂等性:一般来说,GET 请求会被开发人员设计成 “幂等” 的,POST请求不被设计成 “幂等” 的,
幂等:数学上的术语,某个请求,执行一次和执行多次,在结果上没有区别。
④ 可缓存:一般来说,GET 请求会被缓存,POST 请求不会被缓存。
缓存:计算机若需要通过一些复杂的、大量的计算,来得到一些结果,如果这个结果的计算过程代价太大,就可以把这样的结果事先保存下来,下次直接使用,避免重复计算了。从而提升了效率,减少了消耗。
注意
可以看到,上面的四个细节上的差别,在开头上,我都用了【一般来说】。这是因为,GET 和 POST 在细节上的区别并不是绝对的,两者的差别都是受到了开发人员设计、浏览器、实现场景等因素的影响。所以,他们之间的一些差别本身就是可以相互转换的。总而言之,在大前提上,它们没有本质区别。
此外,关于两者在【传输的安全性、传输的数据量、传输的数据类型…】等问题上,官方文档并没有给出区别说明。还是那句话,两者无本质区别,若真的有差异,这是根据开发人员的设计、浏览器、服务器…来决定的。
4. HTTP 请求的其他方法
① PUT:与 POST 相似,只是具有幂等特性,一般用于更新
② DELETE:删除服务器指定资源
③ OPTIONS:返回服务器所支持的请求方法
④ HEAD:类似于GET,只不过响应体不返回,只返回响应头
⑤ TRACE:回显服务器端收到的请求,测试的时候会用到这个
⑥ CONNECT:预留,暂无使用
我们必须明确:在HTTP 请求中,用的最多的就是 GET 和 POST。而 HTTP 请求的其他方法,作为了解即可。
5. 认识 HTTP 请求中的报头
(1) Host
Host:表示服务器主机的地址和端口。一般来说,如果我们在浏览器中输入 URL,那么,HOST 表示的信息与 URL 中的内容是一样的,但也不绝对。
(2) Content-Length
Content-Length:表示请求中 body 中的数据长度,单位是字节。如果 body 内容为空,那么,在抓包的时候,也许就看不到这个 Content-Length.
(3) Content-Type
Content-Type:表示请求中 body 中的数据类型,常见的有三种。前面提到 body 一般存在于 POST 请求中,那么下面三种情况也常对应着 POST 请求中的 body.
① application/x-www-form-urlencoded
studentID=123&classID=456
② multipart/form-data
这种类型较为复杂,主要是用来提交文件的。
③ application/json
{"studentID": 123,"classID": 456,"age": 21,......
}
(4) User-Agent
User-Agent ( UA ):表示浏览器 / 操作系统的属性。
这是我通过 chrome 浏览器查询信息后,抓包的结果:
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/104.0.0.0 Safari/537.36
【Windows NT 10.0】 表示 win10 的内核版本,【Win64;64】表示操作系统的版本信息,后面跟的是浏览器的版本信息。
UA 不仅能表示 PC 端的浏览器属性,还能表示移动端的浏览器属性。鉴于此,它能够区分当前设备是 PC 端 还是 移动端,从而对网页排版做出不同的尺寸。
(5) Referer
Referer:表示当前页面是从哪个页面跳转过来的。
(6) Cookie
Cookie 机制:当浏览器访问网页对应的服务器时,服务器会在 HTTP 的响应头中添加一个键值对传送给浏览器,往后每次访问此网页所属的网站时,都会在请求头中带着这个网站的所有 Cookie 值。
举个例子:你现在通过用户名和密码登录了 CSDN,这时,浏览器会向服务器发送请求;之后,服务器就会返回响应,而在响应的过程中,它给予了浏览器一个 “令牌”,告知浏览器,之后所以的操作都在你的用户名下,不管是浏览 CSDN 的文章也好、不管是自己写博客也好、不管是点赞收藏博客也好…这都基于你当前的用户名。如果要切换用户,那么只有 “退出登录” 才行。
这个过程和去医院看病很相似:到了医院先挂号,挂号时候需要提供身份证,同时得到了一张 “就诊卡”,这个就诊卡就相当于患者的 “令牌”。后续病人去各个科室进行检查、诊断、开药等操作,都不必再出示身份证了,只要凭就诊卡即可识别出当前患者的身份。看完病了之后,不想要就诊卡了,就可以注销这个卡,此时患者的身份和就诊卡的关联就销毁了。
6. body 正文
body 正文:正文中的内容是开发人员自定义的,所以,就算是很多明文的数据,也只有开发人员知道使用着什么逻辑,更别提密文了。
报头中的 Content-Type 和 Content-Length 即分别表示 body 正文的类型和字节长度。
三、HTTP 响应
HTTP 响应的基本格式
以下面图片为例:
HTTP 响应的基本格式和 HTTP 请求基本相似,一般分为四个部分:
① 首行
HTTP 响应的首行十分有特点:
【协议】+ / +【协议版本号】+ 空格 +【状态码】+ 【状态码描述】
② header 响应报头:每一行都是一个键值对。
③ 空行
④ 正文 body
1. 认识状态码(经典面试题)
状态码表示访问一个页面的结果,可能访问成功,也可能访问失败,也可能是其他的一些情况。
(1) 200 OK
200 这是一个最常见的状态码,表示访问成功。
在使用 fiddler 抓包的时候,如果成功访问某页面,那么 HTTP 的响应首行末尾就是 200 OK.
(2) 404 Not found
404 表示没有找到资源。在我们日常使用浏览器的时候,如果出现问题,很多情况下就是碰到了关于 “页面丢失的情况”,所以,404 还是较为常见的。
例如:下面的一幅图分别呈现了 搜狗访问出错和 B站访问出错,这个 404 也可以由开发人员自行设计。
(3) 403 Forbidden
403 表示访问被拒绝,有的页面通常需要用户具有一定的权限才能访问。
比方说:程序员使用 gitee 码云仓库,如果用户将一些仓库设为私有,那么其他用户访问这些私有仓库的时候,就会出现 403.
(4) 405 Method Not Allowed
前面我们已经学习了 HTTP 请求中所支持的方法,有 GET, POST, PUT, DELETE…等。一旦我们使用了这些方法,在我们的视角来看,这是没问题的。但访问对方的服务器,不一定都支持所有的方法,或者说,访问的服务器限制了用户使用一些方法。那么此时,就会出现 405.
(5) 500 Internal Server Error
500 表示服务器出现内部错误,一般是在服务器的代码执行过程中遇到了一些特殊情况,比方说:服务器异常崩溃。
(6) 504 Gateway Timeout
504 表示网关超时。具体来说,当服务器负载比较大的时候,服务器处理单条请求的时候消耗的时间就会很长,就可能会导致出现超时的情况。
例如:
双十一 “秒杀” 场景;省级 / 国家级考试后,网上查分数线的时刻。
(7) 302 Move temporarily
302 表示临时重定向。具体来说,在登录页面中会经常见到 302,其用于实现登陆成功后,自动跳转到的某个页面。而 head 响应报头中的 Location 字段,即表示要跳转到的某个页面。
普通用户在使用浏览器的时候,基本见不到 302,只有通过抓包才能看到,302 状态码相当于一个瞬移功能," 从某一个链接跳到另一个链接 "。
例如:我通过 Chrome 浏览器,使用网页登录 QQ 邮箱后,Location 字段就立即记录下来接着要跳转到哪个地址上,从而,浏览器就会根据 Location 中记录的 URL,立即访问这个 URL.
(8) 301 Move parmanently
301 表示永久重定向。当浏览器收到这种响应时,后续的请求都会被自动改成新的地址,另外,301 也是通过 Location 字段来表示要重定向到的新地址。
状态码总结
2. 认识 HTTP 响应中的报头
HTTP 响应中的报头和 HTTP 请求中的报头 相比,两者格式类似,都是键值对的形式。但 Content-Type 对应的类型有很大不同。
(1) Content-Type
响应中的 Content-Type 常见取值有以下几种:
text/html: body 数据格式是 HTML
text/css: body 数据格式是 CSS
application/javascript: body 数据格式是 JavaScript
application/json: body 数据格式是 JSON
image/png body 数据格式是 图片经过特殊处理后的文本形式
3. body 正文
HTTP 响应中的 body 正文与 HTTP 请求中的 正文 相比,两者大不相同。body 正文常见的内容基于 Content-Type.
四、拓展
1. 多使用 fiddler 抓包
HTTP 协议比较抽象,如果我们真的想要理解 HTTP协议 的来龙去脉,还是以 【抓包为主】,毕竟实践出真知,并且抓包后为我们呈现的结果,可以很清晰地让我们理解到,整个页面通过网络,做了些什么事情。
2. CtrI + F5 和 F5
一个页面,不仅仅只有一个 HTML 文件,还会依赖很多其他的资源,例如:CSS, JS,图片…这些资源其实都是通过网络,下载到浏览器本地的。
为什么呢?
现在这个时代,经常使用浏览器的人都知道,很多网页做的非常精美。所以一个网页依赖的资源可能很多很大,网络传输速度又不快 ( 相对于访问内存 / 磁盘 ),这个时候加载页面就会比较慢。浏览器就会把这些依赖的资源直接缓存到本地,后续再访问的时候速度就快了(已经缓存过的资源,就不必重新下载了)
CtrI + F5 表示强制刷新。
不会重复利用缓存数据,直接清空缓存,把所有的资源重新下载。
F5 表示刷新。
但仍然会重复利用缓存的数据。
有时候我们抓包,如果抓不到想要的结果,就可以尝试在当前页面中,使用 CtrI + F5,来个强制刷新,这样会使得抓包效果好上很多。
详解 HTTP 协议相关推荐
- 一篇文章带你详解 HTTP 协议(下)
文章目录,方便阅读: 一.概述(已讲) 二.HTTP 工作过程(已讲) 三.HTTP 协议基础(已讲) 四.HTTP 协议报文结构(已讲) 五.HTTP 报文首部之请求行.状态行(已讲) 六.HTTP ...
- 详解HTTP协议~~~
详解HTTP协议~~~ HTTP 简介 HTTP协议是Hyper Text Transfer Protocol(超文本传输协议)的缩写,是用于从万维网(WWW:World Wide Web )服务器传 ...
- 通过CURL请求示例详解HTTPS协议
通过CURL请求示例详解HTTPS协议 基于HTTPS通信是当前互联网最通用便捷的通信方式,简单理解来看可以视为HTTP协议 + SSL/TLS协议,通过一个curl的示例阐述一下HTTPS协议. 特 ...
- 一篇文章带你详解 HTTP 协议
一篇文章带你详解 HTTP 协议 本篇文章篇幅比较长,先来个思维导图预览一下. 一张图带你看完本篇文章 一.概述 1.计算机网络体系结构分层 计算机网络体系结构分层 2.TCP/IP 通信传输流 利用 ...
- 图文详解Modbus-RTU协议(转载)
图文详解Modbus-RTU协议 - 知乎 (zhihu.com) Modbus RTU(Remote Terminal Unit 远程终端单元):这种方式常采用RS-485做为物理层,一般利用芯片的 ...
- 简书大佬的笔记:一篇文章带你详解 HTTP 协议(网络协议篇一)
一篇文章带你详解 HTTP 协议(网络协议篇一) 本篇文章篇幅比较长,先来个思维导图预览一下. 一张图带你看完本篇文章 一.概述 1.计算机网络体系结构分层 计算机网络体系结构分层 2.TCP/IP ...
- 36 张图详解应用层协议:网络世界的最强王者
上帝视角 应用层 我们前面介绍过 TCP/IP 模型的下三层,分别是网络接入层.网络层和传输层.它们都是为应用层服务的,传输应用层的各种数据,现在我们就来看看最高层的应用层. 应用层 在 TCP/IP ...
- 一篇文章带你详解 HTTP 协议(上)
文章目录,方便阅读: 一.概述 二.HTTP 工作过程 三.HTTP 协议基础 四.HTTP 协议报文结构 五.HTTP 报文首部之请求行.状态行 六.HTTP 报文首部之首部字段(重点分析) 七.H ...
- TCP/IP协议基本概括+ARP协议详解+DNS协议详解---Linux学习笔记
TCP/IP协议的体系结构: TCP/IP协议族四层模型和OSI七层模型 上层协议使用下层协议的服务,下层协议给上层协议提供一个接口. 四层模型中各个层次的作用和特点 上图说明: 最底层是数据链路层, ...
最新文章
- python单词大全-学Python必须背的42个常见单词
- ppt复制切片器_这6个新手必学的PPT技能,让你效率提升10倍!套模板都比别人快...
- android插件式换肤,Android学习之插件化换肤
- kinect:0x80080014
- Spring Data JPA教程第一部分:配置
- 如何用记事本编写运行java程序?
- json java 数据类型_程序员都应该了解的一种数据格式之 JSON
- syscall 系统调用陷入_系统调用深度剖析(上)
- 程序实现对数据排序并按出现次数进行排序 程序实现对数据排序并按出现次数进行排序(注:用面向对象的方式实现,用for循环进行排序,别用comparable接口实现){1,4,2,1,3,2,1,4}作为
- 2021年安全员-A证最新解析及安全员-A证考试总结
- 计算机专业论文推荐,计算机专业论文参考文献推荐
- c语言pow函数原型_C语言pow函数
- 【Java】P1957 口算练习题—(洛谷OJ)
- 三次曲线和五次曲线函数
- 文档多级列表_如何在Google文档中创建多级列表
- sql语句实现查询实例
- Win10怎么看内存条频率
- 电源学习(1):stm32单片机buck电路可调电源设计介绍
- python解数学方程_用Python如何解数学方程
- 《信息与编码》考试复习笔记6----第六章连续信源熵和信道容量(考点在连续信道容量)
热门文章
- 基于MATLAB Simulink的太阳能光伏MPPT控制蓄电池充电仿真模型
- 全国计算机二级考试操作题是原题吗,2017全国计算机二级office考试操作题
- 赵本山/宋丹丹之买房篇
- 批处理 批量s扫1433_批处理可以批量处理相同操作的图片
- java.lang.NoSuchFieldError: No static field xxxx of type I in class Lcom/app/live/R$id; or its supe
- springcloud必知功能使用教程
- 数据库:mysql基本增删查改
- CodeForces - 1006F Xor-Paths(双向搜索,到分界位置组合一起和最终结果比较+map容器)
- 煽情的儿子549=随笔
- 0x0000050蓝屏srvsys_分享蓝屏0x00000050提示srv.sys的解决方法