面试官系列- 你真的了解 http 吗

[toc]css

个人 CSDN 博客:blog.csdn.net/gdutxiaoxu
个人掘金:juejin.im/user/58aa85…
github: github.com/gdutxiaoxu/
微信公众号:徐公码字(stormjun94)
知乎:www.zhihu.com/people/xuju…
html

往期文章

Android 面试必备 - http 与 https 协议git

Android 面试必备 - 计算机网络基本知识(TCP,UDP,Http,https)程序员

Android 面试必备 - 线程github

Android 面试必备 - JVM 及 类加载机制面试

Android 面试必备 - 系统、App、Activity 启动过程算法

Android_interview github 地址chrome

有兴趣的话能够关注个人公众号 徐公码字(stormjun94),第一时间会在上面更新数据库

image

前言

转眼间,2020 年已过去一大半了,2020 年很难,各企业裁人的消息蛮多的,降职,不发年终奖等等。2020 年确实是艰难的一年。然而生活老是要继续,时间不给你丧的机会!若是咱们能坚持下来,不断提升本身,说不定会有新的机会。api

面试中,网络(http, https, tcp, udp), jvm, 类加载机制等这些基础的知识点是高频出现的,每一个程序员都能说上好多。但不必定说到重点,以及理解背后的原理。

我在面试的过程当中也常常被问到,因而总结记录了下来。千万不要小瞧这些基础,有时候,你算法,项目经验都过了,可是基础答得不太好。结果可能会经过,但这确定会影响你的评级,这是特别吃亏的。因此,不如花点时间背一下,理解一下背后的原理。

举一个简单的例子, https 链接过程是怎样的,使用了了哪一种加密方https 的链接过程式,能够抓包吗,怎样防止抓包,你是否可以对答以下。

废话很少说,开始进入正文。

面试常见

一道经典的面试题

还记得这道经典的面试题目吗?从 URL 在浏览器被被输入到页面展示的过程当中发生了什么?

整体来讲分为如下几个过程:

  • DNS 解析:将域名解析成 IP 地址
  • TCP 链接:TCP 三次握手
  • 发送 HTTP 请求
  • 服务器处理请求并返回 HTTP 报文
  • 浏览器解析渲染页面
  • 断开链接:TCP 四次挥手

完整的能够看如下下面的图片

image

http 必备基础知识

HTTP 是一种 超文本传输协议(Hypertext Transfer Protocol),HTTP 是一个在计算机世界里专门在两点之间传输文字、图片、音频、视频等超文本数据的约定和规范

image

HTTP 主要内容分为三部分,超文本(Hypertext)、传输(Transfer)、协议(Protocol)。

  • 超文本就是不仅仅只是本文,它还能够传输图片、音频、视频,甚至点击文字或图片可以进行超连接的跳转。
  • 上面这些概念能够统称为数据,传输就是数据须要通过一系列的物理介质从一个端系统传送到另一个端系统的过程。一般咱们把传输数据包的一方称为请求方,把接到二进制数据包的一方称为应答方。
  • 而协议指的就是是网络中(包括互联网)传递、管理信息的一些规范。如同人与人之间相互交流是须要遵循必定的规矩同样,计算机之间的相互通讯须要共同遵照必定的规则,这些规则就称为协议,只不过是网络协议。

什么是无状态协议,HTTP 是无状态协议吗,怎么解决

无状态协议(Stateless Protocol) 就是指浏览器对于事务的处理没有记忆能力。举个例子来讲就是好比客户请求得到网页以后关闭浏览器,而后再次启动浏览器,登陆该网站,可是服务器并不知道客户关闭了一次浏览器。

HTTP 就是一种无状态的协议,他对用户的操做没有记忆能力。可能大多数用户不相信,他可能以为每次输入用户名和密码登录一个网站后,下次登录就再也不从新输入用户名和密码了。这其实不是 HTTP 作的事情,起做用的是一个叫作 小甜饼(Cookie) 的机制。它可以让浏览器具备记忆能力。 若是你的浏览器容许 cookie 的话,查看方式 chrome://settings/content/cookies

几种方法

HTTP1.0定义了三种请求方法: GET, POST 和 HEAD方法

HTTP1.1新增了五种请求方法:OPTIONS, PUT, DELETE, TRACE 和 CONNECT

  • GET: 一般用于请求服务器发送某些资源
  • HEAD: 请求资源的头部信息, 而且这些头部与 HTTP GET 方法请求时返回的一致. 该请求方法的一个使用场景是在下载一个大文件前先获取其大小再决定是否要下载, 以此能够节约带宽资源
  • OPTIONS: 用于获取目的资源所支持的通讯选项
  • POST: 发送数据给服务器,是非幂等
  • PUT: 跟POST方法很像,也是想服务器提交数据。可是,它们之间有不一样。PUT指定了资源在服务器上的位置,而POST不须要置顶资源在服务器的位置,是幂等
  • DELETE: 用于删除指定的资源
  • PATCH: 用于对资源进行部分修改
  • CONNECT: HTTP/1.1协议中预留给可以将链接改成管道方式的代理服务器
  • TRACE: 回显服务器收到的请求,主要用于测试或诊断

http get 和 post 区别

Post通常用于更新或者添加资源信息 Get通常用于查询操做,并且应该是安全和幂等的
Post更加安全 Get会把请求的信息放到URL的后面
Post传输量通常无大小限制 Get不能大于2KB
Post执行效率低 Get执行效率略高

http put 和 post 区别

举一个简单的例子

POST:用于提交请求,能够更新或者建立资源,是非幂等的

举个例子,在咱们的支付系统中,一个api的功能是建立收款金额二维码,它和金额相关,每一个用户能够有多个二维码,若是连续调用则会建立新的二维码,这个时候就用POST

PUT: 用于向指定的URI传送更新资源,是幂等的

仍是那个例子,用户的帐户二维码只和用户关联,并且是一一对应的关系,此时这个api就能够用PUT,由于每次调用它,都将刷新用户帐户二维码

若是从 RESTful API 的角度来理解,PUT 方法是这么工做的:

把一个对象 V 绑定到地址 K 上;从此请求地址 K 时,就会返回对象 V。

若是地址 K 以前曾绑定过另外一个对象,好比 V0,那么 V0 会被 V 替换。

举一个简单的例子,假设个人博客后台支持 RESTful API,我能够经过下面的请求发布这篇文章:

PUT https://gdutxiao.github.io/2018/04/16/http-put-vs-post HTTP/1.1

{
    /* 文章内容正文 */
}
复制代码

能够看出,使用 PUT 方法时,客户端须要在 HTTP 请求中明确指定地址 K。

正如 Java 的例子同样,PUT 方法应当支持幂等性。若是是同一个对象 V,PUT 屡次与 PUT 一次返回的结果应该是相同的。客户端能够利用 PUT 的幂等性安全地重试请求,保证客户端的请求至少被服务端处理一次。

若是把上面发布文章的例子用 HTTP POST 方法重写,它可能会是下面这样:

POST https://gdutxiao.github.io/post-article HTTP/1.1

{
    /* 文章内容正文 */
}
复制代码

也就是说,地址 K 不是由客户端指定的,而是由服务端生成的。好比,服务端可能会根据日期和文章标题,为本文分配一个地址。

另外,与 PUT 方法不一样,POST 方法是不支持幂等性的。同一个请求被处理两次,应当生成两份对象。换句话说,客户端应该只发送一次 POST 请求,而客户端的请求至多会被服务端处理一次。

如今问题来了,若是真的遇到了网络故障,客户端应该如何重试 POST 请求呢?解决方法其实很简单,咱们能够在 POST 请求中隐藏一个惟一的 token,服务端在处理请求后把 token 存入数据库,若是这个 token 以前遇到过,服务端就知道这是重复的 POST 请求,能够再也不处理了。

http 版本

1.0 与 1.1

  • http1.0一次只能处理一个请求,不能同时收发数据
  • http1.1能够处理多个请求,能同时收发数据
  • http1.1增长可更多字段,如cache-control,keep-alive.

2.0

  • http 2.0采用二进制的格式传送数据,再也不使用文本格式传送数据
  • http2.0对消息头采用hpack压缩算法,http1.x的版本消息头带有大量的冗余消息
  • http2.0 采用多路复用,即用一个tcp链接处理全部的请求,真正意义上作到了并发请求,流还支持优先级和流量控制(HTTP/1.x 虽然经过 pipeline也能并发请求,可是多个请求之间的响应会被阻塞的,因此 pipeline 至今也没有被普及应用,而 HTTP/2 作到了真正的并发请求。同时,流还支持优先级和流量控制。)
  • http2.0支持server push,服务端能够主动把css,jsp文件主动推送到客户端,不须要客户端解析HTML,再发送请求,当客户端须要的时候,它已经在客户端了。

缺点

虽然 HTTP/2 解决了不少以前旧版本的问题,可是它仍是存在一个巨大的问题, 主要是底层支撑的 TCP 协议形成的 。HTTP/2的缺点主要有如下几点:

  • TCP 以及 TCP+TLS创建链接的延时

HTTP/2使用TCP协议来传输的,而若是使用HTTPS的话,还须要使用TLS协议进行安全传输,而使用TLS也须要一个握手过程, 这样就须要有两个握手延迟过程

①在创建TCP链接的时候,须要和服务器进行三次握手来确认链接成功,也就是说须要在消耗完1.5个RTT以后才能进行数据传输。

②进行TLS链接,TLS有两个版本——TLS1.2和TLS1.3,每一个版本创建链接所花的时间不一样,大体是须要1~2个RTT。

总之,在传输数据以前,咱们须要花掉 3~4 个 RTT。

  • TCP的队头阻塞并无完全解决

上文咱们提到在HTTP/2中,多个请求是跑在一个TCP管道中的。但当出现了丢包时,HTTP/2 的表现反倒不如 HTTP/1 了。由于TCP为了保证可靠传输,有个特别的“丢包重传”机制,丢失的包必需要等待从新传输确认,HTTP/2出现丢包时,整个 TCP 都要开始等待重传,那么就会阻塞该TCP链接中的全部请求(以下图)。而对于 HTTP/1.1 来讲,能够开启多个 TCP 链接,出现这种状况反到只会影响其中一个链接,剩余的 TCP 链接还能够正常传输数据。

image

Http 3.0

Google 在推SPDY的时候就已经意识到了这些问题,因而就另起炉灶搞了一个基于 UDP 协议的“QUIC”协议,让HTTP跑在QUIC上而不是TCP上。 而这个“HTTP over QUIC”就是HTTP协议的下一个大版本,HTTP/3。它在HTTP/2的基础上又实现了质的飞跃,真正“完美”地解决了“队头阻塞”问题。

image

QUIC 虽然基于 UDP,可是在本来的基础上新增了不少功能,接下来咱们重点介绍几个QUIC新功能。不过HTTP/3目前还处于草案阶段,正式发布前可能会有变更,因此本文尽可能不涉及那些不稳定的细节。

QUIC新功能

上面咱们提到QUIC基于UDP,而UDP是“无链接”的,根本就不须要“握手”和“挥手”,因此就比TCP来得快。此外QUIC也实现了可靠传输,保证数据必定可以抵达目的地。它还引入了相似HTTP/2的“流”和“多路复用”,单个“流"是有序的,可能会由于丢包而阻塞,但其余“流”不会受到影响。具体来讲QUIC协议有如下特色:

  • 实现了相似TCP的流量控制、传输可靠性的功能。

虽然UDP不提供可靠性的传输,但QUIC在UDP的基础之上增长了一层来保证数据可靠性传输。它提供了数据包重传、拥塞控制以及其余一些TCP中存在的特性。

  • 实现了快速握手功能。

因为QUIC是基于UDP的,因此QUIC能够实现使用0-RTT或者1-RTT来创建链接,这意味着QUIC能够用最快的速度来发送和接收数据,这样能够大大提高首次打开页面的速度。 0RTT 建连能够说是 QUIC 相比 HTTP2 最大的性能优点

  • 集成了TLS加密功能。

目前QUIC使用的是TLS1.3,相较于早期版本TLS1.3有更多的优势,其中最重要的一点是减小了握手所花费的RTT个数。

  • 多路复用,完全解决TCP中队头阻塞的问题

和TCP不一样,QUIC实现了在同一物理链接上能够有多个独立的逻辑数据流(以下图)。实现了数据流的单独传输,就解决了TCP中队头阻塞的问题。

image

关于 http 3.0 的,若是想了解更多,能够查看这一篇文章。解密HTTP/2与HTTP/3 的新特性

总结

  • HTTP/1.1有两个主要的缺点:安全不足和性能不高。
  • HTTP/2彻底兼容HTTP/1,是“更安全的HTTP、更快的HTTPS",头部压缩、多路复用等技术能够充分利用带宽,下降延迟,从而大幅度提升上网体验;
  • QUIC 基于 UDP 实现,是 HTTP/3 中的底层支撑协议,该协议基于 UDP,又取了 TCP 中的精华,实现了即快又可靠的协议

http 状态码

Http 状态码 含义
200 请求成功
206 支持断点下载(range = byte = 0 -1024)
301 永远移动
302 临时移动
303 See Other 查看其它地址。与301相似。使用GET和POST请求查看
304 无更新
400 Bad request,服务器没法识别
403 禁止访问
404 not found
405 Method Not Allowed 客户端请求中的方法被禁止
500 Internal Server Error 服务器内部错误,没法完成请求

关于更详细的能够查看

http 状态码

题外话

下一篇预告,将会推出 面试官系列 - https 真的安全吗,能够抓包吗,如何防止抓包。

有兴趣的话能够关注个人公众号 徐公码字(stormjun94)

image

目前从事于 Android 开发,除了分享 Android开发相关知识,还有职场心得,面试经验,学习心得,人生感悟等等。但愿经过该公众号,让你看到程序猿不同的一面,咱们不仅会敲代码,咱们还会。。。。。。,期待你的参与

相关文章
相关标签/搜索