不懂Web基本原理怎么能学好爬虫。(五 、网络协议之HTTP)(爬虫、反爬虫、网络协议、HTTP、WebSocket )

目录

前言

1.HTTP 是什么       

2.HTTP 工作过程        

2.1 HTTP 协议格式       

2.1.1 抓包工具的使用

2.1.2 抓包工具原理       

 2.1.3 抓包结果分析

2.1.4 协议格式总结  ​编辑

3. HTTP 请求 (Request)

3.1 请求地址 URL       

3.2 认识方法         

 3.2.1 GET 方法       

3.2.2 POST 方法

3.2.3 其他方法

3.3 HTTP请求报文头属性

3.3.1Accept 

3.3.2cookie

3.3.3Referer

3.3.4Cache-Control

3.3.5 Host       

3.3.6Content-Length

3.3.7 Content-Type

3.3.8 User-Agent (简称 UA)        

3.4 请求 "正文" (body)

4.HTTP响应报文

4.1 响应行:

4.2 响应头:

4.3 响应体:

4.4 响应状态码 

4.5常见的HTTP响应报文头属性

4.5.1 Cache-Control

4.5.2 ETag 

4.5.3 Location 

4.6 cookie机制:

总结


前言

网络协议时链接客户端和服务器的桥梁,学习网络协议相关的知识,能让我们对网络通信过程以及通信所需条件有一个全面的认识,可以帮助我们提升爬虫技术。

常见的网络协议有HTTP协议、WebSocket协议、FTP协议、SSH协议和ViewSource协议等。我们重点学习在Web应用中使用最多的HTTP协议WebSocket协议


1.HTTP 是什么
       

HTTP (全称为 "超文本传输协议") 是⼀种应用非常广泛的应用层协议。

HTTP 诞生与1991年. 目前已经发展为最主流使用的一种应用层协议,我们平时打开一个网站, 就是通过 HTTP 协议来传输数据的.

        https 是在 http 基础之上做了一个加密解密的工作,当我们在浏览器中输入一个百度搜索的 "网址" (URL) 时, 浏览器就给百度的服务器发送了一个 HTTP 请 求, 百度的服务器返回了一个 HTTP 响应.
        这个响应结果被浏览器解析之后, 就展示成我们看到的页面内容. (这个过程中浏览器可能会给服务器发送多个 HTTP 请求, 服务器会对应返回多个响应, 这些响应里就包含了页面 HTML, CSS, JavaScript, 图片, 字体等信息).

2.HTTP 工作过程 
       

        当我们在浏览器中输入一个 "网址", 此时浏览器就会给对应的服务器发送一个 HTTP 请求. 对方服务器收到这个请求之后, 经过计算处理, 就会返回一个 HTTP 响应.

        事实上, 当我们访问一个网站的时候, 可能涉及不止一次的 HTTP 请求/响应  的交互过程. 可以通过 chrome 的开发者工具观察到这个详细的过程:

通过 F12 打开 chrome 的开发者工具, 切换到 网络 标签页. 然后刷新页面即可看到如下图效果. 每一条记录都是一次 HTTP 请求/响应

2.1 HTTP 协议格式
       

        HTTP 是一个文本格式的协议. 可以通过 Chrome 开发者工具分析 HTTP 请求/响应 的细节.

2.1.1 抓包工具的使用

以 Fiddler 为例. (下载地址: https://www.telerik.com/fiddler/),安装过程比较简单, 一路 next 即可。

左侧窗口显示了所有的 HTTP请求/响应, 可以选中某个请求查看详情.
右侧上方显示了 HTTP 请求的报文内容. (切换到 Raw 标签页可以看到详细的数据格式)
右侧下方显示了 HTTP 响应的报文内容. (切换到 Raw 标签页可以看到详细的数据格式)
请求和响应的详细数据, 可以通过右下角的 View in Notepad 通过记事本打开.
使用 ctrl + a 全选左侧的抓包结果, delete 键清除所有被选中的结果.
 

2.1.2 抓包工具原理
       

        Fiddler 相当于一个 "代理",浏览器访问 baidu.com 时, 就会把 HTTP 请求先发给 Fiddler, Fiddler 再把请求转发给 sogou 的服务器. 当 sogou 服务器返回数据时, Fiddler 拿到返回数据, 再把数据交给浏览器.

 2.1.3 抓包结果分析

HTTP请求抓包结果:

首行: [方法] + [url] + [版本]
Header: 请求的属性, 冒号分割的键值对;每组属性之间使用\n分隔;遇到空行表示Header部分结束 
Body: 空行后面的内容都是Body. Body允许为空字符串. 如果Body存在, 则在Header中会有一个Content-Length属性来标识Body的长度;


 HTTP响应:

 首行: [版本号] + [状态码] + [状态码解释]
Header: 请求的属性, 冒号分割的键值对;每组属性之间使用\n分隔;遇到空行表示Header部分结束
Body: 空行后面的内容都是Body. Body允许为空字符串. 如果Body存在, 则在Header中会有一个Content-Length属性来标识Body的长度; 如果服务器返回了一个html页面, 那么html页面内容就是在body中.


2.1.4 协议格式总结
 
 

为什么 HTTP 报文中要存在 "空行"?

因为 HTTP 协议并没有规定报头部分的键值对有多少个. 空行就相当于是 "报头的结束标记", 或者是 "报头和正文之间的分隔符".
HTTP 在传输层依赖 TCP 协议, TCP 是面向字节流的. 如果没有这个空行, 就会出现 "粘包问题". 

3. HTTP 请求 (Request)


3.1 请求地址 URL
       

        平时我们俗称的 "网址" 其实就是说的 URL (Uniform Resource Locator 统一资源定位符). 互联网上的每个文件都有一个唯一的URL,它包含的信息指出文件的位置以及浏览器应该怎么处理它. 

        URL 的详细规则由 因特网标准RFC1738 进行了约定(https://datatracker.ietf.org/doc/html/rfc1738).

URL中可以省略的部分:

  • 协议名: 可以省略, 省略后默认为 http://
  • ip 地址 / 域名: 在 HTML 中可以省略(比如 img, link, script, a 标签的 src 或者 href 属性). 省略后表示服务器的 ip / 域名与当前 HTML 所属的 ip / 域名一致.
  • 端口号: 可以省略. 省略后如果是 http 协议, 端口号自动设为 80; 如果是 https 协议, 端口号自动设为 443.
  • 带层次的文件路径: 可以省略. 省略后相当于 / . 有些服务器会在发现 / 路径的时候自动访问/index.html
  • 查询字符串: 可以省略
  • 片段标识: 可以省略

关于 URL encode

        像 / ? : 等这样的字符, 已经被url当做特殊意义理解了. 因此这些字符不能随意出现.比如, 某个参数中需要带有这些特殊字符, 就必须先对特殊字符进行转义.转义的规则如下: 将需要转码的字符转为16进制,然后从右到左,取4位(不足4位直接处理),每2位做一 位,前面加上%,编码成%XY格式

 "\\" 被转义成了 "%5C%5C"

urldecode就是urlencode的逆过程.

3.2 认识方法
         

这里的方法指的是请求的方法类型,它的分类有以下几个:

 3.2.1 GET 方法
       

         GET 是最常用的 HTTP 方法. 常用于获取服务器上的某个资源。在浏览器中直接输入 URL, 此时浏览器就会发送出一个 GET 请求. 
另外, HTML 中的 link, img, script 等标签, 也会触发 GET 请求.

GET 请求的特点:

  • 首行的第一部分为 GET
  • URL 的 query string 可以为空, 也可以不为空.
  • header 部分有若干个键值对结构.
  • body 部分为空.

3.2.2 POST 方法


        POST 方法也是一种常见的方法. 多用于提交用户输入的数据给服务器(例如登陆页面)通过 HTML 中的 form 标签可以构造 POST 请求, 或者使用 JavaScript 的 ajax 也可以构造 POST 请求.

POST 请求的特点:

  • 首行的第一部分为 POST
  • URL 的 query string 一般为空 (也可以不为空)
  • header 部分有若干个键值对结构.
  • body 部分一般不为空. body 内的数据格式通过 header 中的   Content-Type 指定. body 的长度由header 中的 Content-Length 指定.
     

谈谈 GET 和 POST 的区别 ?

  •  语义不同: GET 一般用于获取数据, POST 一般用于提交数据.
  • GET 的 body 一般为空, 需要传递的数据通过 query string 传递, POST 的 query string 一般为空, 需要传递的数据通过 body 传递
  • GET 请求一般是幂等的, POST 请求一般是不幂等的. (如果多次请求得到的结果一样, 就视为请求是幂等的).
  • GET 可以被缓存, POST 不能被缓存. (这一点也是承接幂等性).


补充说明: 

  • 关于语义: GET 完全可以用于提交数据, POST 也完全可以用于获取数据.
  • 关于幂等性: 标准建议 GET 实现为幂等的. 实际开发中 GET 也不必完全遵守这个规则(主流网站都有 "猜你喜欢" 功能, 会根据用户的历史行为实时更新现有的结果.
  • 关于安全性: 有些资料上说 "POST 比 GET 请安全". 这样的说法是不科学的. 是否安全取决于前端在传输密码等敏感信息时是否进行加密, 和 GET POST 无关.
  • 关于传输数据量: 有的资料上说 "GET 传输的数据量小, POST 传输数据量大". 这个也是不科学的, 标准没有规定 GET 的 URL 的长度, 也没有规定 POST 的 body 的长度. 传输数据量多少,完全取决于不同浏览器和不同服务器之间的实现区别.
  • 关于传输数据类型: 有的资料上说 "GET 只能传输文本数据, POST 可以传输二进制数据". 这个也是不科学的. GET 的 query string 虽然无法直接传输二进制数据, 但是可以针对二进制数据进行 url encode.


3.2.3 其他方法

  • PUT 与 POST 相似,只是具有幂等特性,一般用于更新
  • DELETE 删除服务器指定资源
  • OPTIONS 返回服务器所支持的请求方法
  • HEAD 类似于GET,只不过响应体不返回,只返回响应头
  • TRACE 回显服务器端收到的请求,测试的时候会用到这个
  • CONNECT 预留,暂无使用

这些方法的 HTTP 请求可以使用 ajax 来构造. (也可以通过一些第三方工具)

3.3 HTTP请求报文头属性

3.3.1Accept 

        请求报文可通过一个“Accept”报文头属性告诉服务端 客户端接受什么类型的响应。 如下报文头相当于告诉服务端,俺客户端能够接受的响应类型仅为纯文本数据啊,你丫别发其它什么图片啊,视频啊过来,那样我会歇菜的~~~

Accept:text/plain 

Accept属性的值可以为一个或多个MIME类型的值(描述消息内容类型的因特网标准, 消息能包含文本、图像、音频、视频以及其他应用程序专用的数据)

3.3.2cookie

Cookie 中存储了一个字符串, 这个数据可能是客户端(网页)自行通过 JS 写入的, 也可能来自于服务器(服务器在 HTTP 响应的 header 中通过 Set-Cookie 字段给浏览器返回数据)。往往可以通过这个字段实现 "身份标识" 的功能。(每个不同的域名下都可以有不同的 Cookie, 不同网站之间的Cookie 并不冲突.)

客户端的Cookie就是通过这个报文头属性传给服务端的!如下所示:

Cookie: $Version=1; Skin=new;jsessionid=5F4771183629C9834F8382E23 

服务端是怎么知道客户端的多个请求是隶属于一个Session呢?注意到后台的那个jsessionid = 5F4771183629C9834F8382E23木有?原来就是通过HTTP请求报文头的Cookie属性的jsessionid的值关联起来的!(当然也可以通过重写URL的方式将会话ID附带在每个URL的后面哦)。

3.3.3Referer

表示这个请求是从哪个URL过来的,假如你通过google搜索出一个商家的广告页面,你对这个广告页面感兴趣,鼠标一点发送一个请求报文到商家的网站,这个请求报文的Referer报文头属性值就是http://www.google.com。

3.3.4Cache-Control

对缓存进行控制,如一个请求希望响应返回的内容在客户端要被缓存一年,或不希望被缓存就可以通过这个报文头达到目的。

3.3.5 Host
       

表示服务器主机的地址和端口. 

3.3.6Content-Length

        表示 body 中的数据长度.

3.3.7 Content-Type

         表示请求的 body 中的数据格式.

Content-Type: text/html;charset=utf-8


3.3.8 User-Agent (简称 UA) 
       

表示浏览器/操作系统的属性. 形如:

User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.64 Safari/537.36 Edg/101.0.1210.47

3.4 请求 "正文" (body)


        正文中的内容格式和 header 中的 Content-Type 密切相关. 上面也罗列了三种常见的情况.

4.HTTP响应报文

HTTP的响应报文也由三部分组成(响应行+响应头+响应体

4.1 响应行:

①报文协议及版本; 
②状态码及状态描述;

4.2 响应头:

③响应报文头,也是由多个属性组成;

4.3 响应体:

④响应报文体,即我们真正要的“干货”

4.4 响应状态码 

        和请求报文相比,响应报文多了一个“响应状态码”,它以“清晰明确”的语言告诉客户端本次请求的处理结果。 
HTTP的响应状态码由5段组成:

  • 1xx:指示信息--表示请求已接收,继续处理
  • 2xx:成功--表示请求已被成功接收、理解、接受
  • 3xx:重定向--要完成请求必须进行更进一步的操作
  • 4xx:客户端错误--请求有语法错误或请求无法实现
  • 5xx:服务器端错误--服务器未能实现合法的请求

以下是几个常见的状态码: 

101 协议切换

        客户端要求服务器切换协议并且服务器已确认切换,如WebSocket协议起始阶段

200 OK

         这是一个最常见的状态码, 表示访问成功.

301 Moved Permanently 

        永久重定向. 当浏览器收到这种响应时, 后续的请求都会被自动改成新的地址. 301 也是通过 Location 字段来表示要重定向到的新地址.

302 Move temporarily 

        临时重定向 

临时重定向 就相当于手机号码中的 "呼叫转移" 功能.
比如我本来的手机号是 187-xxxx-1234, 后来换了个新号码 153-xxxx-5678, 那么不需要让我的朋友知道新号码,
只要我去办理一个呼叫转移业务, 其他人拨打 187-xxxx-1234 , 就会自动转移到 153-xxxx-5678 上.

304 Not Modified 

告诉客户端,你请求的这个资源至你上次取得后,并没有更改,你直接用你本地的缓存吧,我很忙哦,你能不能少来烦我啊

403 Forbidden 

        表示访问被拒绝. 有的页面通常需要用户具有一定的权限才能访问(登陆后才能访问). 如果用户没有登陆直接访问, 就容易见到 403. 

404 Not Found

        没有找到资源.

浏览器输入一个 URL, 目的就是为了访问对方服务器上的一个资源. 如果这个 URL 标识的资源不存在, 那么就会出现 404 .

405 Method Not Allowed 

        前面介绍了 HTTP 中所支持的方法, 有 GET, POST, PUT, DELETE 等. 但是对方的服务器不一定都支持所有的方法(或者不允许用户使用一些其他的方法). 此时就会出现 405.

500 Internal Server Error

        服务器出现内部错误. 一般是服务器的代码执行过程中遇到了一些特殊情况(服务器异常崩溃)会产生这个状态码. 

504 Gateway Timeout

        当服务器负载比较大的时候, 服务器处理单条请求的时候消耗的时间就会很长, 就可能会导致出现超时的情况. 

在登陆页面中经常会见到 302. 用于实现登陆成功后自动跳转到主页. 响应报文的 header 部分会包含一个 Location 字段, 表示要跳转到哪个页面. 

4.5常见的HTTP响应报文头属性

4.5.1 Cache-Control

 
响应输出到客户端后,服务端通过该报文头属告诉客户端如何控制响应内容的缓存

常见的取值有private、public、no-cache、max-age,no-store,默认为private。

  • private:             客户端可以缓存
  • public:              客户端和代理服务器都可缓存(前端的同学,可以认为public和private是一样的)
  • max-age=xxx:   缓存的内容将在 xxx 秒后失效
  • no-cache:          需要使用对比缓存来验证缓存数据
  • no-store:           所有内容都不会缓存

默认为private,缓存时间为31536000秒(365天)也就是说,在365天内再次请求这条数据,都会直接获取缓存数据库中的数据,直接使用。

4.5.2 ETag 
 

一个代表响应服务端资源(如页面)版本的报文头属性,如果某个服务端资源发生变化了,这个ETag就会相应发生变化。它是Cache-Control的有益补充,可以让客户端“更智能”地处理什么时候要从服务端取资源,什么时候可以直接从缓存中返回响应。

4.5.3 Location 
 

我们在JSP中让页面Redirect到一个某个A页面中,其实是让客户端再发一个请求到A页面,这个需要Redirect到的A页面的URL,其实就是通过响应报文头的Location属性告知客户端的,如下的报文头属性,将使客户端redirect到iteye的首页中:

Location: http://www.iteye.com  
 

4.5.4 Set-Cookie 
服务端可以设置客户端的Cookie,其原理就是通过这个响应报文头属性实现的

Set-Cookie: UserID=JohnDoe; Max-Age=3600; Version=1  
 

4.6 cookie机制:

客户端请求服务器,如果服务器需要记录该用户状态,就使用response向客户端浏览器颁发一个Cookie。客户端浏览器会把Cookie保存起来。当浏览器再请求该网站时,浏览器把请求的网址连同该Cookie一同提交给服务器。服务器检查该Cookie,以此来辨认用户状态。服务器还可以根据需要修改Cookie的内容。

Cookie的maxAge决定着Cookie的有效期,单位为秒(Second)。Cookie中通过getMaxAge()方法与setMaxAge(int maxAge)方法来读写maxAge属性。

如果maxAge属性为正数,则表示该Cookie会在maxAge秒之后自动失效。

如果maxAge为负数,则表示该Cookie仅在本浏览器窗口以及本窗口打开的子窗口内有效,关闭窗口后该Cookie即失效。

如果maxAge为0,则表示删除该Cookie。

Cookie并不提供修改、删除操作。如果要修改某个Cookie,只需要新建一个同名的Cookie,添加到response中覆盖原来的Cookie。

如果要删除某个Cookie,只需要新建一个同名的Cookie,并将maxAge设置为0,并添加到response中覆盖原来的Cookie。


总结

至此我们已经对HTTP已经有清晰的了解,下节我们对另一个常用的协议WebSocket进行学习。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值