理解 HTTP

环境:

  • Windows 10 家庭中文版

  • Google Chrome 108.0.5359.94 (正式版本) (64 位)

  • fiddler v5.0.20211.51073 for .NET 4.6.1 Built: 2021年12月15日

一. 概述

简述 HTTP/HTTPS

HTTP,全称为 HyperText Transfer Protocol,即 超文本传输协议。

HTTPS,全称为 Hypertext Transfer Protocol Secure,超文本传输安全协议。

因为这篇文章主要描述 HTTP 的工作模式,以及数据传输的格式,所以暂时忽略 HTTPS 的部分特性。

HTTP 是基于 TCP 协议的应用层传输协议,用于分布式、协作式和超媒体信息系统的应用层协议,是客户端和服务端进行数据传输的一种规则。

因为 HTTP 以明文的方式发送资源,不对数据进行加密,如果攻击者截取了 Web 浏览器和服务器之间的报文,可以直接读懂其中的信息,数据泄露的风险很大。为了增加数据的安全性而研发出了 HTTPS,HTTPS 对传输的内容进行了加密,HTTPS 还是使用 HTTP 进行通信,利用 SSL/TSL 来加密数据包。

HTTP 建立连接只需要执行 TCP 的三次握手即可进行数据传输,而 HTTPS 则需要在完成 TCP 的连接之后,还要完成 SSL/TSL 的确认。因此服务器处理 HTTP 请求的速度比处理 HTTPS 协议的速度快。

HTTP 是一种 无状态 (stateless) 协议,即不会对发送过的请求和相应的通信状态进行持久化处理。这样做的目的是为了保持HTTP协议的简单性,从而能够快速处理大量的事务, 提高效率。然而,在许多应用场景中,我们需要保持用户登录的状态或记录用户购物车中的商品。由于HTTP 是无状态协议,所以必须引入一些技术来记录管理状态,例如 Cookie 和 token。

URL

Uniform Resource Locator 统一资源定位符,通常叫做 URL。

Internet 上每一个网页都具有一个唯一的名称标识,WWW 为了管理众多的网络资源,定制了统一资源定位符,日常中,URL 就是 Web 地址,也就是网址;日常中见到的https://cn.bing.comhttps://www.baidu.com/这些都是 URL。

URL 通常由这些参数组成:

  • 传输协议 😕/ 服务器域名 [ : 端口号 ] / 服务器资源路径 / 请求参数

  • protocol 😕/ hostnam [:port] / path / parameters

https://cn.bing.com/search?q=山寨机哪家牛为例:

  • protocol(协议):指定传输时使用的协议,现在常见的是 HTTPS 协议,其它常用的协议有 HTTP、FTP。

  • hostname(主机名):如果在本地部署服务器,然后再在本地的浏览器访问,则 hostname 一般用 localhost 指代主机名;而网站的 hostname 一般都是网站从域名服务商那里申请的域名。

  • port(端口):一般服务器有很多端口,范围从 0 ~ 65535,HTTP 默认使用的是 80 端口,HTTPS 默认使用的是 443 端口,尝试使用https://cn.bing.com:443/search?q=山寨机哪家牛进行检索,可以看见默认端口是否存在不影响访问。

  • parameters(参数):访问服务器时附带的参数,可以为空。

会话 = 请求 + 响应

Session 会话,请求 Request,响应 Respond。

HTTP 的基本工作模式就是,计算机中的浏览器向服务器发送 Request,当服务器收到计算机的 Request 时,服务器会向计算机产生 Respond,向计算机传输某些资源。这个 请求 -- 响应 的模式就是 HTTP 基本的工作形式。

在计算机发送请求时,请求和响应的内容都称为报文,这些报文都遵循一定的格式,方便计算机之间的数据交流,以下内容会大致说明 HTTP 会话的格式。

二. HTTP 请求

在具体解释会话内容前,或许可以下载 fiddler 来查看一些真实的网页请求。

Fiddler 的一些操作可以看这篇文章 Fiddler 使用手册 - 文档待完善

HTTP 请求基本格式

Method(请求方法)  Request-URL  HTTP-version  CRLF(换行)
Request-header
        空行(CRLF)
Request-body

一个请求例子,此次用 fiddler 抓取 Chrome 访问 Baidu 的包

GET https://www.baidu.com/s?ie=utf-8&wd=疫情 HTTP/1.1
Host: www.baidu.com
Connection: keep-alive
sec-ch-ua: "Not?A_Brand";v="8", "Chromium";v="108", "Google Chrome";v="108"
is_xhr: 1
Ps-Dataurlconfigqid: 0x8190872f0020dd2a
sec-ch-ua-mobile: ?0
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36
Accept: */*
X-Requested-With: XMLHttpRequest
is_referer: https://www.baidu.com/
sec-ch-ua-platform: "Windows"
Sec-Fetch-Site: same-origin
Sec-Fetch-Mode: cors
Sec-Fetch-Dest: empty
Referer: https://www.baidu.com/s?ie=utf-8&f=8&rsv_bp=1&rsv_idx=1&tn=baidu&wd=d&fenlei=256&rsv_pq=0x8190872f0020dd2a&rsv_t=d849xBsDFgXaDrKJXB18AwAh0vk0BE1j3cmcFd8yAaJRN%2Fdb1D2zc1orZp22&rqlang=en&rsv_enter=0&rsv_dl=tb&rsv_sug3=2&rsv_sug1=1&rsv_sug7=100&rsv_btype=i&prefixsug=d&rsp=0&inputT=1707&rsv_sug4=2385
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9
Cookie: RT="z=1&dm=baidu.com&si=78uixhravtc&ss=lb7lsaxu&sl=1&tt=16a&bcn=https%3A%2F%2Ffclog.baidu.com%2Flog%2Fweirwood%3Ftype%3Dperf&ld=1yp&ul=5sbc&hd=5sbw"; __bid_n=184d709c30615416bc4207; BIDUPSID=2A2C49BF8C1A707C4DF1E2E1C7546603; PSTM=1670102268; BAIDUID=2A2C49BF8C1A707CA276298523242153:FG=1; BD_HOME=1; H_PS_PSSID=37858_36553_37831_37766_37759_26350_37786_37882; BAIDUID_BFESS=2A2C49BF8C1A707CA276298523242153:FG=1; BD_UPN=12314753; BA_HECTOR=25a50h8l8125a40024ah2krf1honf7t1g; ZFY=VYKk6r:BMNqX8pZbBfbusowMmgfHSDH:AeOq79Nh9EAt4:C; delPer=0; BD_CK_SAM=1; PSINO=7; H_PS_645EC=b4fafeBvn1U4bBSdtmrAJObJA%2FSAWJhWpzfrHV4MOszNYvZPpgA7Vx3EuEA

(这里原本是请求体,但 get 请求一般没有请求体,这里放一句话 占位)
  • 首先,第一行的内容是GET [https://www.baidu.com/s?ie=utf-8&wd=疫情](https://www.baidu.com/s?ie=utf-8&wd=%E7%96%AB%E6%83%85) HTTP/1.1,GET 是请求的方式,请求方式有 get(请求获取数据)、post(请求提交数据)、put(请求服务器更新资源)、delete(请求服务器删除资源)、options(查询服务器性能或需求)等;关于请求类型更多的信息可以看看这篇博客 HTTP八种请求方法 - HTTP | MDN。然后后面是使用的协议以及协议的版本,HTTP 协议现在基本都用的是 1.1 版本。

  • 接下来直到空行之前的信息都属于请求头(Request-header),这部分的内容都是由一些键值对组成,一般是对响应体的要求或客户端自身的一些信息。Host 表示访问的域名;Connection 表示连接之后的状态是保持连接还是断开连接;还有很多,具体可以看看这份博客 http请求头响应头大全 - 傻瓜不傻108 - 博客园。另外在请求头的最后是带有 Cookie 的,至于 Cookie 和 Token 的区别,可以看看这个博客 Session、Cookie、Token 【浅谈三者之间的那点事】 - 腾讯云开发者社区-腾讯云

  • 空行,空行是必须的,区分请求头与请求体。

  • 最后是请求体,但这一部分在上面的例子中是空白的,因为例子中的请求是 Get 请求,一般不带有请求体,可以尝试在浏览器中登录某个网站,然后用 fiddler 抓取相应的 post 请求,就可以看到请求体中存在你提交的账号密码等信息。

三. HTTP 响应

HTTP 响应基本格式

HTTP-Version Status-Code(状态码) Reason-Phrase(说明状态码的简单描述)
Respond-Header(响应头)

Respond-Body(响应体)

一个响应例子,对应上面 Baidu 搜索的请求,以下是抓取的 响应

HTTP/1.1 200 OK
Bdpagetype: 3
Bdqid: 0xc8cb1544002ae262
Connection: keep-alive
Content-Type: text/html
Date: Sun, 04 Dec 2022 09:03:56 GMT
Is_status: 1
Server: BWS/1.1
Set-Cookie: delPer=0; path=/; domain=.baidu.com
Set-Cookie: BD_CK_SAM=1;path=/
Set-Cookie: PSINO=7; domain=.baidu.com; path=/
Set-Cookie: BDSVRTM=287; path=/
Set-Cookie: H_PS_PSSID=37858_36553_37831_37766_37759_26350_37786_37882; path=/; domain=.baidu.com; Secure; SameSite=None
Strict-Transport-Security: max-age=172800
Traceid: 1670144636043918823414468681609662620258
Vary: Accept-Encoding
X-Frame-Options: sameorigin
X-Ua-Compatible: IE=Edge,chrome=1
Content-Length: 95

<div><div id="__status">0</div><div id="__redirect">0</div><div id="__switchtime">0</div></div>
  • 响应的第一行叫做响应行,包含响应的基本信息,有使用的协议以及协议的版面本,响应的状态码,和对状态码的简单说明。状态码为 200 表示正常返回,还有经典的 404,更多的状态码描述可以查看这个文档 HTTP 响应状态码 - HTTP | MDN

  • 响应头的内容和请求头的内容形式一样,也是以键值对的形式表示。

  • 空行,空行是必须的,用于区分响应头和响应体。

  • 响应体,请求通过后,服务器响应返回的信息,这个例子中,因为 Get 请求没有在请求头中明确使用 Accept 属性描述想要接收的数据类型,所以 Baidu 以默认的 HTML 形式返回数据。(这里的请求体有点长,被我删掉了大部分)

参考

这篇文章可以初步了解 HTTP 协议,如果想要更深入地学习 HTTP 协议,需要弄清楚每个请求的类型、每个响应的状态码、Cookie 等,建议阅读完这篇文章之后如果想深入学习 HTTP,可以仔细阅读这篇文档HTTP | MDN

posted @ 2022-12-04 18:33  故魇  阅读(96)  评论(0编辑  收藏  举报