我报名参加金石计划1期挑战——瓜分10万奖池,这是我的第4篇文章,点击查看活动详情
前言
作为专业的“切图仔”,如果说有一种的知识在平常工作中很少使用,但面试时总会被问到,那 http 相关绝对算一个,概念繁杂,晦涩难懂,常常令“切图仔们”望而生畏。这不,我们“可爱的”面试官在 前面 吃了瘪,正准备在这方面让我们吃到苦头。张口说到:“别吵吵了,看我看我,我们来聊聊 http 那些事吧!”
HTTP 简介
Web 使用一种名为 HTTP(HyperText Transfer Protocol,超文本传输协议)的协议作为规范,完成从客户端到服务器等一系列运作流程。简单来讲,HTTP 是一个在计算机世界里专门在两点之间传输文字、图片、音频、视频等超文本数据的约定和规范。
HTTP 版本的变迁
HTTP/1.0
最早的 http 只是使用在一些较为简单的网页上和网络请求上,所以比较简单,每次请求都打开一个新的 TCP 链接,收到响应之后立即断开连接。
HTTP/1.1
- 相比 1.0 版本,引入了更多的缓存控制策略,比如:“Cache-control: max-age=xxx”;
- 允许范围请求,即在请求头中加入 Range 头部;
- 请求消息和响应消息都必须包含 Host 头部;
- 默认开启持久连接,在一个 TCP 连接上可以传送多个 HTTP 请求和响应,减少了建立和关闭连接的消耗和延迟。
HTTP/2.0
- 新的二进制格式;
- 多路复用(允许并发的发起多个请求,每个请求及该请求的响应不需要等待其他的请求或响应,避免了线头阻塞问题。这样某个请求任务耗时严重,不会影响到其它连接的正常执行,极大的提高传输性能);
- 头部压缩,比如 cookie 和 user agent 每次都会重复发送,http2.0 在通讯双方各自 cache 一份 header fields 表,既避免了重复 header 的传输,又减小了需要传输的大小;
- 服务端推送,比如一个请求是由你的主页发起的,服务器很可能会响应主页内容、logo 以及样式表,因为它知道客户端会用到这些东西;
HTTP 报文
请求报文
请求行(请求方法、协议版本)、请求首部(请求 URI、客户端信息等)和内容实体(用户信息和资源信息等,可为空)构成
响应报文
状态行(协议版本、状态码)、响应首部(服务器名称、资源标识等)和内容实体(服务端返回的资源信息)构成
两种请求
当浏览器发送 CORS 请求(跨域请求)时,会有两种请求方式:
-
简单请求;
无自定义请求头,Content-Type 只能为:text/plain、multipart/form-data、application/x-www-form-urlencoded
-
复杂请求;
PUT, Delete 方法的 ajax 请求、发送 JSON 格式的 ajax 请求(比如 post 数据)、带自定义头的 ajax 请求
状态码
常见的几个:
- 200 - 请求成功
- 304 - 资源未修改,通常与 http 协商缓存相关,服务端无返回
- 400 - 客户端请求的语法错误,服务器无法理解
- 404 - 请求的资源(网页等)不存在
- 500 - 服务器内部错误
- 502 - 网关或代理服务器错误
| 分类 | 描述 |
|---|---|
| 1** | 信息,服务器收到请求,需要请求者继续执行操作 |
| 2** | 成功,操作被成功接收并处理 |
| 3** | 重定向,需要进一步的操作以完成请求 |
| 4** | 客户端错误,请求包含语法错误或无法完成请求 |
| 5** | 服务器错误,服务器在处理请求的过程中发生了错误 |
HTTPS
HTTPS 基于 HTTP 协议,通过 SSL 或 TLS(可以看作 SSL3.0)提供加密处理数据、验证对方身份以及数据完整性保护
特点
- 内容加密:采用混合加密技术,中间者无法直接查看明文内容
- 验证身份:通过证书认证客户端访问的是自己的服务器
- 保护数据完整性:防止传输的内容被中间人冒充或者篡改
与 HTTP 的区别
- HTTPS 协议需要到 CA(证书颁发机构)申请证书,一般免费证书很少,需要交费
- HTTP 协议运行在 TCP 之上,所有传输的内容都是明文,HTTPS 运行在 SSL/TLS 之上,SSL/TLS 运行在 TCP 之上,所有传输的内容都经过加密的;
- HTTP 和 HTTPS 使用的是完全不同的连接方式,用的端口也不一样,前者是 80,后者是 443
- http 的连接很简单,是无状态的;HTTPS 协议是由 HTTP+SSL 协议构建的可进行加密传输、身份认证的网络协议,可以有效的防止运营商劫持,解决了防劫持的一个大问题,比 http 协议安全
HTTP 缓存
所谓缓存就是在访问过一次某个网站之后,这个站点的文字、图片等所有资源都被下载到本地了,下次再访问该网站时判断是否满足缓存条件,如果满足就不用再花费时间去等待资源的获取了。优点还是很明显的,比如:减少冗余的数据传输,降低了服务器压力,加快了页面加载时间。
强缓存
这里有两个关键字段:
-
Expire
设置缓存到期时间(绝对时间),但这样有一个问题:如果修改了客户端的本地时间,就会导致判断缓存失效。
-
Cache-control
既然设置绝对时间不保险,那就设置个相对时间。在 HTTP/1.1 中,增加了一个字段 Cache-Control ,它包含一个 max-age 属性,该字段表示资源缓存的最大有效时间,这就是一个相对时间。 这里又有几个常用属性:
- no-cache:客户端缓存内容,但是是否使用缓存则需要经过协商缓存来验证决定,常常会有同学把这个误认为是用不缓存 -_-;
- no-store:所有内容都不会被缓存,即不使用强制缓存,也不使用协商缓存;
- public:所有内容都将被缓存(客户端和代理服务器都可缓存);
- private:所有内容只有客户端可以缓存,Cache-Control 的默认取值;
- max-age=xxx (xxx is numeric):缓存内容将在 xxx 秒后失效;
如果同时设置 Expire 和 Cache-Control ,Cache-Control 的优先级别更高。
协商缓存(对比缓存)
这里同样有两个关键的字段:
-
Last-Modified,If-Modified-Since
浏览器第一次请求资源的时候,服务器返回的 header 上会带有一个 Last-Modified 字段,表示资源最后修改的时间。服务器收到这个请求后,将 If-Modified-Since 和当前的 Last-Modified 进行对比。如果相等,则说明资源未修改,返回 304,浏览器使用本地缓存。
-
Etag
Etag 一般是由文件内容 hash 生成的,也就是说它可以保证资源的唯一性,资源发生改变就会导致 Etag 发生改变。同样地,在浏览器第一次请求资源时,服务器会返回一个 Etag 标识。当再次请求该资源时, 会通过 If-no-match 字段将 Etag 发送回服务器,然后服务器进行比较,如果相等,则返回 304 表示未修改。
Last-Modified 和 Etag 是可以同时设置的,服务器会优先校验 Etag,如果 Etag 相等就会继续比对 Last-Modified,最后才会决定是否返回 304
小结
- 强制缓存如果生效,不会再和服务器发生交互,而对比缓存不管是否生效,都需要与服务端发生交互;
- 缓存规则可以同时存在,强制缓存优先级高于对比缓存,也就是说,当强制缓存规则生效时,直接使用缓存,不再执行对比缓存规则;
最后
至此,关于 http 部分的面试告一段落了,总的来讲我们主要介绍了 http 版本、http 报文、https、http 缓存这几大部分,也不知道面前的这面试官是怎么想的,看他面无表情的动了动嘴,说到:“先回去等通知吧,拜拜 👋🏻”
“我回答的有问题还是咋的?拜拜就拜拜,下一个更乖!”