• 【前端】彻底搞懂HTTP协议


    一、http协议基础

    概念

    HTTP协议(HyperText Transfer Protocol,超文本传输协议)是用于从WWW服务器传输超文本到本地浏览器的传输协议。

    当你在浏览器的地址框中输入一个URL(www.baidu.com)或是单击一个超级链接时,URL就确定了要浏览的地址。浏览器通过超文本传输协议(HTTP),将Web服务器上站点的网页代码提取出来,并翻译成漂亮的网页。

    我们需要获取到服务器上的资源或者请求服务器的接口,都要发送请求(不一定必须是http请求)。

    请求报文(Request)

    客户端发送一个HTTP请求到服务器的请求消息包括以下格式:请求行(request line)、请求头部(header)、空行和请求数据四个部分组成。

    GET /hello.txt HTTP/1.1
    User-Agent: curl/7.16.3 libcurl/7.16.3 OpenSSL/0.9.7l zlib/1.2.3
    Host: www.example.com
    Accept-Language: en, mi
    
    • 1
    • 2
    • 3
    • 4

    常用请求方法:
    在这里插入图片描述

    响应报文(Response)

    HTTP响应也由四个部分组成,分别是:状态行、消息报头、空行和响应正文。
    在这里插入图片描述

    二、http缓存

    在浏览器加载资源的时候,首先会根据请求头的expires和cache-control判断是否命中强缓存策略,判断是否向远程服务器请求资源还是去本地获取缓存资源。

    http强缓存

    在浏览器中,强缓存分为Expires(http1.0规范)、cache-control(http1.1规范)两种。

    Expires

    Expires是http1.0的规范,用于表示资源的过期时间的请求头字段,值是一个绝对时间(到期时间),是由服务器端返回的。

    在浏览器第一个请求资源时,服务器端的响应头会附上Expires这个响应字段,当浏览器在下一次请求这个资源时会根据上次的expires字段是否使用缓存资源(当请求时间小于服务端返回的到期时间,直接使用缓存数据)
    注意:

    expires是根据本地时间来判断的,假设客户端和服务器时间不同,会导致缓存命中误差
    
    • 1

    cache-control

    Expires有个缺点,当客户端本地时间和服务器时间不一致时会产生误差,浏览器会直接向服务器请求新的资源,为了解决这个问题,在http1.1规范中,提出了cache-control字段,且这个字段优先级高于上面提到的Expires,值是相对时间

    cache-control中有常见的几个响应属性值:
    在这里插入图片描述
    例如下面是一张图片的响应:
    在这里插入图片描述

    http协商缓存

    强缓存都是由本地浏览器确定是否使用缓存,当浏览器没有命中强缓存时就会向浏览器发送请求,验证协商缓存是否命中,如果缓存命中则返回304状态码,否则返回新的资源数据。

    同样,协商缓存的标识也是在响应报文的HTTP头和请求结果一起返回给浏览器的,控制协商缓存的字段分别有:

    • Last-Modified / If-Modified-Since
    • Etag / If-None-Match

    其中Etag/If-None-Match优先级比Last-Modified/If-Modified-Since高。
    在这里插入图片描述

    Last-Modified / If-Modified-Since

    Last-Modified是服务器响应请求时,返回该资源文件在服务器最后被修改的时间

    If-Modified-Since则是客户端再次发起该请求时,携带上次请求返回的Last-Modified值,通过此字段告诉服务器该资源上次请求返回的最后被修改时间。服务器收到该请求,发现请求头含有If-Modified-Since字段,则会根据If-Modified-Since的字段值与该资源在服务器的最后被修改时间做对比

    • 若服务器的资源最后修改时间大于If-Modified-Since的字段值,则重新返回资源,状态码为200;
    • 否则返回304,代表资源无更新,可以继续使用缓存文件。

    Etag / If-None-Match

    Etag是服务器响应请求时,返回当前资源文件的一个唯一标识(由服务器生成)。

    If-None-Match是客户端再次发起请求时,携带上次请求返回的唯一标识Etag值,服务端收到该请求后,发现该请求含有If-None-Match,则会根据If-None-Match的字段值与该资源在服务器的Etag值做对比:

    • 一致则返回304,代表资源无更新,继续使用缓存文件。
    • 否则重新返回资源,状态码为200。

    所以协商缓存结果:

    • 协商缓存生效,返回304,服务器告诉浏览器资源未更新,则直接浏览器缓存中访问资源。
    • 协商缓存失效,返回200和请求结果,这个结果是从服务器返回的新的结果。

    缓存流程

    了解了强缓存和协商缓存,那么我们可以大概描述一下一次完整的请求流程:

    1. 当浏览器发起一个资源请求时(例如一张图片),浏览器会先判断本地是否有缓存记录,如果没有会向浏览器请求新的资源,并记录服务器返回的last-modified。
    2. 如果有缓存记录,先判断强缓存是否存在(cache-control优先于expires),如果强缓存的时间没有过期则返回本地缓存资源(状态码为200)。
    3. 如果强缓存失效了,客户端会发起请求进行协商缓存策略,首先服务器判断Etag标识符,如果客户端传来标识符和当前服务器上的标识符是一致的,则返回状态码 304 not modified(不会返回资源内容)。
    4. 如果没有Etag字段,服务器会对比客户端传过来的if-modified-match和服务器上资源的最后修改时间,如果这两个值是一致的,此时响应头不会带有last-modified字段(因为资源没有变化,last-modified的值也不会有变化),客户端304状态码之后读取本地缓存。如果If-Modified-Since的字段值与该资源在服务器的最后被修改时间不一样,那么返回新资源,状态码为200。
    5. 如果Etag和服务器端上的不一致,重新获取新的资源。

    简化:

    强缓存->(cache-control > expires) [强缓存失败] -> 协商缓存 -> (Etag > last-modified) -> [协商缓存失败] -> 重新获取资源
    
    • 1
  • 相关阅读:
    StringBuffer和StringBuilder的区别与联系
    零成本搭建个人博客搭建篇
    mybatis plus generator 3.5.1 从了解到自定义定制VO、PO、DTO
    ALBERT实战:基于ALBERT预训练模型实现答案预测分类
    【网络安全】——sql注入之奇淫巧技bypass(持续更新中)
    关于使用 SAP UI5 代码设置应用 theme 的技巧
    设计模式定义
    Vue3全网最细介绍使用
    sql 限制返回的行数、从表中随机返回n行数据、将NULL转换为实际值
    Area Listener 区域监听器
  • 原文地址:https://blog.csdn.net/ZHANGYANG_1109/article/details/126664760