HTTP缓存

2023-11-03

HTTP缓存

什么是HTTP缓存 ?

http缓存指的是: 当客户端向服务器请求资源时,会先抵达浏览器缓存,如果浏览器有“要请求资源”的副本,就可以直接从浏览器缓存中提取而不是从原始服务器中提取这个资源。
常见的http缓存只能缓存get请求响应的资源,对于其他类型的响应则无能为力,所以后续说的请求缓存都是指GET请求

为什么要使用HTTP缓存 ?

假设我们请求一次服务器,请求头大小1kb,响应头大小1kb,请求文件10kb。
1次请求流量:12kb
10次请求流量:120kb
N次请求:12*N…
这只是假想的一次请求,但事实上的请求不仅是请求文件,请求客户端也会更多,那么问题就很明显:

1.客户端每次都要请求服务器,浪费流量(比如手机端?)。
2.服务器每次都得提供查找,下载,请求用户基础如果较大,服务器存在较大压力。
3.客户端每次请求完都要进行页面渲染,用户体验较差。
那么我们是否可以将请求的文件存放起来使用,比如使用http缓存。

HTTP缓存头部字段

1.Cache-Control
请求/响应头,缓存控制字段,可以说是控制http缓存的最高指令,要不要缓存也是它说了算。
它有以下常用值
  1.1 no-store:所有内容都不缓存
  1.2 no-cache:缓存,但是浏览器使用缓存前,都会请求服务器判断缓存资源是否是最新,它是个比较高贵的存在,因为它只用不过期的缓存。
  1.3 max-age=x(单位秒) 请求缓存后的X秒不再发起请求,属于http1.1属性,与下方Expires(http1.0属性)类似,但优先级要比Expires高。
  1.4 s-maxage=x(单位秒) 代理服务器请求源站缓存后的X秒不再发起请求,只对CDN缓存有效(这个在后面会细说)
  1.5 public 客户端和代理服务器(CDN)都可缓存
  1.6 private 只有客户端可以缓存

2.Expires
响应头,代表资源过期时间,由服务器返回提供,GMT格式日期,是http1.0的属性,在与max-age(http1.1)共存的情况下,优先级要低。
3.Last-Modified
响应头,资源最新修改时间,由服务器告诉浏览器。
4.if-Modified-Since
请求头,资源最新修改时间,由浏览器告诉服务器(其实就是上次服务器给的Last-Modified,请求又还给服务器对比),和Last-Modified是一对,它两会进行对比。
5.Etag
响应头,资源标识,由服务器告诉浏览器。
6.if-None-Match
请求头,缓存资源标识,由浏览器告诉服务器(其实就是上次服务器给的Etag),和Etag是一对,它两会进行对比。

使用http缓存

1.让服务器与浏览器约定一个文件过期时间——Expires(GMT时间格式)。
日常请求对话
第一次请求的时候:
在这里插入图片描述

后续请求的时候:
浏览器会先对比当前时间是否已经大于Expires,也就是判断文件是否超过了约定的过期时间。
时间没过,不发起请求,直接使用本地缓存。
时间过期,发起请求,继续上述的浏览器与服务器的谈话日常。
问题:假设Expires已过期,浏览器再次请求服务器,但f.js相比上次并未做任何改变,那这次请求我们是否通过某种方式加以避免?
比如约定时间是一个月,约定时间到了我还没改。

2.让服务器与浏览器在约定文件过期时间的基础上,再加一个文件最新修改时间的对比——Last-Modified与if-Modified-Since
日常请求对话
第一次请求:
在这里插入图片描述

后续请求:
Expires未过期,浏览器机智的使用本地缓存,免得挨打。
Expires过期,服务器带上了文件最新修改时间if-Modified-Since(也就是上次请求服务器返回的Last-Modified),服务器将if-Modified-Since与Last-Modified做了个对比。
if-Modified-Since 与Last-Modified不相等,服务器查找了最新的a.js,同时再次返回Expires与全新的Last-Modified
if-Modified-Since 与Last-Modified相等,服务器返回了状态码304,文件没修改过,你还是用你的本地缓存。
在这里插入图片描述

问题:浏览器端可以随意修改Expires,Expires不稳定,Last-Modified只能精确到秒,假设文件是在1s内发生变动,Last-Modified无法感知到变化,这种情况下浏览器永远拿不到最新的文件(假想极端情况)。
如果是在淘宝京东这种,每一毫秒都会发生变化,这种方式就很不可取

3.让服务器与浏览器在过期时间Expires+Last-Modified的基础上,再增加一个文件内容唯一对比标记——Etag与If-None-Match。哦对了,我们说Expires有可能被篡改,这里我们再加入一个max-age来加以代替(cache-control其中一个值)。
日常对话
第一次请求:
在这里插入图片描述

后续请求:
60S内,不发起请求,直接使用本地缓存。(max-age=60代表请求成功缓存后的60S内不再发起请求,与Expires相似,同时存在max-age优先级要比Expires高,区别后面具体说)
60S后,浏览器带上了if-Modified-Since 与If-None-Match(上次服务器返回来的Etag)发起请求,服务器对比If-None-Match与Etag(不对比if-Modified-Since与Last-Modified了,Etag优先级比Last-Modified高,毕竟更精准)
If-None-Match与Etag不相等,说明a.js内容被修改过,服务器返回最新a.js与全新的Etag与max-age=60与Last-Modified与Expires
If-None-Match与Etag相等,说明a.js文件内容无任何改变,返回304,告诉浏览器继续使用之前的本地缓存。
如下图,服务器Etag与If-None-Match相同,所以返回了状态码304,由于优先级问题,虽然也有if-Modified-Since与Last-Modified,但这里不会对两者做对比。
在这里插入图片描述

问题:我们已经可以精确的对比服务器文件与本地缓存文件差异,但其实上面方案的演变都存在一个较大缺陷, max-age或Expires不过期,浏览器无法主动感知服务器文件变化。

http缓存方案

1.md5/hash缓存
通过**不缓存html,**为静态文件添加MD5或者hash标识,解决浏览器无法跳过缓存过期时间主动感知文件变化的问题。

为什么这么做?实现原理是什么?

之前的浏览器小老弟与服务器老大哥之间的缓存都是建立在每次请求的文件都是在相同的目录以及相同的文件名,如果目录或者是文件名发生改变的时候就会重新请求,管那些什么失效时间乱七八糟的花里胡哨的东西,所以这个时候就出现了新的解决办法。 就是通过webpack来解决,每次打包的时候生成新的文件,嘿嘿,简单粗暴的解决了上面说的浏览器小老弟无法主动感知服务器文件发生改变的事情

module/js/a-hash1.js与module/js/a-hash2.js是两个完全不同的文件,假想浏览器第一次加载页面,请求并缓存了module/js/a-hash1.js,第二次加载,文件指向变成了module/js/a-hash2.js,浏览器会直接重新请求a-hash2.js,因为这就是两个完全不同的文件,哪里还有什么http缓存文件对比,所以通过这种做法,我们就可以从根本上解决过期时间没到浏览器无法主动请求服务器的问题。因此我们只需要在项目每次发布迭代将修改过的静态文件添加不同的MD5或hash标识就好啦。
注意,这里不推荐缓存html文件(或许有更好的做法,欢迎留言),这样每次html加载渲染都可以感知文件变化,反正文件没变还是使用本地缓存,文件名都变了说明修改过,重新请求缓存就好了。
怎么改?一个个手动去修改?那不得累死。webpack提供了webpack-md5-hash插件,可以帮助开发者在项目发布时自动修改文件标识。

2.CDN

cdn就是构建在网络之上的内容分发,依靠部署在各地的边缘服务器,通过不知道具体什么原理的中心平台的负载均衡,然后进行内容分发,调度等功能模块,使用户可以在就近的服务器获取图片等静态文件,
之前看到一个不错的例子,这里直接拿过来举例说说CDN。
假设多年前我们所在的城市只有一个火车站,每次春运,整个城市的人都得去这个火车站买票,人流量以及购票的需求可想而知有多大,为了缓解这个问题,城市的不同区,都出现了火车票代售点,这样每个区的人都可以就近买票了,火车站总站的压力就这样大大减轻了。
我们可以把每个区的售票点称之为CDN节点,也就是前面所说的代理服务器。简而言之,我们可以把CDN理解成浏览器与服务器之间的临时站点,它会替服务器处理一部分的浏览器请求,从而整理减轻总服务器的压力。

我们可以把CDN的价值归纳为:
1.CDN通过分流的形式,大大减轻源站的访问压力。
2.就像住的区比较偏远,每次买票要去城市中心,而这个区后来有了分站,火车票就可以就近购买一样。CDN也解决了跨地区访问问题,根本上为访问提供了加速。

2.2 什么是CDN缓存
CDN边缘节点缓存数据,当浏览器请求,CDN将代替源站判断并处理此处请求。
日常请求对话
第一次请求:
在这里插入图片描述

后续请求:
在这里插入图片描述

情况1:CDN节点自己缓存的文件未过期,于是返回了304给浏览器,打回了这次请求。
情况2:CDN节点发现自己缓存的文件过期了,为了保险起见,自己发起请求给了服务器(源站),成功拿回了最新数据,然后再交给与了浏览器。
其实说到这,CDN缓存的问题也跟前面的http缓存一样,CDN缓存时间不过期,浏览器始终被拦截,无法拿到最新的文件。
但是我们回归http缓存问题本质,缓存本身针对于更新频率不高的静态文件,其次,CDN缓存提供了分流以及访问加速其它优势条件。
CDN类似一个平台,是可以通过登录,手动更新CDN缓存的,变相解决了浏览器缓存无法手动控制的问题。

由于我没有用过cdn,但是大概可以猜到cdn可能会遇到一些坑就是源文件修改之后,cdn上的文件未更新的问题,大致有两种解决办法就是给静态文件增加版本号,或者是使用cdn提供商的强制刷新

那么两种http缓存方案就说到这里了,接下来谈谈http缓存其它的一些问题和概念。
浏览器地址栏回车,新开窗口,F5刷新,CTRL+F5刷新等浏览器操作对HTTP缓存的影响
对浏览器的不同行为对缓存的影响做一个总结。
**1.浏览器地址栏回车,或者点击跳转按钮,前进,后退,新开窗口,**这些行为,会让Expires,max-age生效,也就是说,这几种操作下,浏览器会判断过期时间,再考虑要不要发起请求,当然Last-Modified和Etag也有效。
2.F5刷新浏览器,或者使用浏览器导航栏的刷新按钮,这几种,会忽略掉Expires,max-age的限制,强行发起请求,Last-Modified和Etag在这种情况下也有效。
3.CTRL+F5是强制请求,所有缓存文件都不使用,全部重新请求下载,因此Expires,max-age,Last-Modified和Etag全部失效。
在这里插入图片描述

在利用fiddler抓包看不同网站缓存时,发现了一个有趣的问题,大部分网站的cache-control都设置的为no-cache。
我在前面说了,no-cache不是不缓存,要缓存,但是浏览器在协商性缓存情况下,都会无条件像服务器发起请求,判断自己的缓存是不是最新,如果是就接着用,不是就请求最新的文件,缓存起来用,以此循环。
那么有必要设置过期时间Expires与max-age吗?有!
当我们第一次浏览一个页面,关闭后,第二次再打开还是属于新开窗口行为,如果设置了缓存时间,新开窗口会走强缓存,可以避免反复的文件下载,加快页面渲染,提升用户体验性。
(其实一开始我是觉得Expires与max-age是不需要设置的,直到我使用pageSpeed对公司网站做了个性能评分,发现还是推荐使用缓存时间,结合上面的话,其实是有道理的)

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

HTTP缓存 的相关文章

  • http之GET请求的传递参数的方式

    第一种 直接在URL后面加参数 localhost 21811 Handler1 ashx id 1 name abc 如下图 第二种 用超链接的方法传递参数 当点击超链接的时候 首先会跳转 localhost 21811 Handler1
  • TCP/IP协议,HTTP协议--面试必备

    经常面试被问到什么是http协议 什么是TCP协议 而且每次都弄不清楚 是时候记录一下了 一 什么是http协议 如果读者对计算机网络的体系结构比较了解的话应该清楚 IP协议位于网络层 TCP UDP协议位于传输层 HTTP位于应用层 如下
  • 浅谈Http长连接和Keep-Alive以及Tcp的Keepalive

    Keep Alive模式 我们知道Http协议采用 请求 应答 模式 当使用普通模式 即非Keep Alive模式时 每个请求 应答 客户端和服务器都要新建一个连接 完成之后立即断开连接 当使用Keep Alive模式时 Keep Aliv
  • WebSocket的原理与优缺点

    一 websocket与http WebSocket是HTML5中的协议 支持持久连接 而Http协议不支持持久连接 首先HTMl5指的是一系列新的API 或者说新规范 新技术 WebSocket是HTML5中新协议 新API 跟HTTP协
  • HTTP缓存

    HTTP缓存 什么是HTTP缓存 http缓存指的是 当客户端向服务器请求资源时 会先抵达浏览器缓存 如果浏览器有 要请求资源 的副本 就可以直接从浏览器缓存中提取而不是从原始服务器中提取这个资源 常见的http缓存只能缓存get请求响应的
  • iOS开发网络-HTTP协议

    一 URL 1 基本介绍 URL的全称是Uniform Resource Locator 统一资源定位符 通过1个URL 能找到互联网上唯一的1个资源 URL就是资源的地址 位置 互联网上的每个资源都有一个唯一的URL 2 URL中常见的协
  • .NET页面之间传值的几种方式总结

    1 QueryString 当页面上的form以get方式向页面发送请求数据时 web server将请求数据放入一名为QEURY STRING的环境变量中 QeueryString方法从这个变量中取出相应的值 先建立两个WebForm 分
  • http和缓存有关的状态码

    200 OK from cache 是浏览器没有跟服务器确认 直接用了浏览器缓存 而 304 Not Modified 是浏览器和服务器多确认了一次缓存有效性 再用的缓存 200 from cache 是速度最快的 因为不需要访问远程服务器
  • HTTP协议、http服务器的实现-1

    1 HTTP协议简介 在Web应用中 服务器把网页传给浏览器 实际上就是把网页的HTML代码发送给浏览器 让浏览器显示出来 而浏览器和服务器之间的传输协议是HTTP 所以 HTML 超文本标记语言 HyperText Markup Lang
  • Web和HTTP

    目录 HTTP概况 Web术语 HTTP基本 HTTP是无状态协议 HTTP连接方式 非持续连接HTTP 例子 花费时间 持续连接的HTTP 非持续的缺点 HTTP报文格式 请求报文 HTTP请求报文的通用格式 及GET POST HEAD
  • 05-网络的四层协议和七层协议

    TCP IP网络分层模型 TCP IP的设计创造性的提出了分层的概念 把复杂的网络通信划分出多个层次 再为每一个层次分配不同的职责 层次内只专心做好自己的事情 用分而治之的思想把一个大麻烦拆分成了数个小麻烦 从而解决了网络的难题 TCP I
  • file协议与Http协议,HTTP请求与AJAX请求

    一 什么是file协议 file协议主要用于访问本地计算机中的文件 好比通过Windows的资源管理器中打开文件或者通过右键单击 打开 一样 基本格式 file 文件路径 file C Users CLi AppData Local Tem
  • http1 & http2 发展与特性

    Http http协议已经被广泛应用在web应用中 常用于一下几种场景 聊天 全双工 客户端和服务器实时通信 推送 服务器主动向客户端通信 应答 传统模式 客户端发起请求 服务器响应 长连接 TCP Http协议本身就是基于请求 应答模式的
  • 用JAVA中的URL获取网页相关信息

    ava中有一个URL类 可以获取指定url的内容 import java io BufferedReader import java io InputStreamReader import java net URL public class
  • 【HTTP协议】超详细的HTTP协议详解

    基本介绍 HTTP是一个属于应用层的面向对象的协议 由于其简捷 快速的方式 适用于分布式超媒体信息系统 它于1990年提出 经过几年的使用与发展 得到不断地完善和扩展 目前在WWW中使用的是HTTP 1 0的第六版 HTTP 1 1的规范化
  • HTTP的升级之路

    HTTP的升级之路 HTTP简介 HTTP HyperText Transfer Protocol 超文本传输协议 是一种用于分布式 协作式和超媒体信息系统的应用层协议 1 HTTP是万维网的数据通信的基础设计HTTP最初的目的是为了提供一
  • 关于HTTP协议,一篇就够了

    HTTP简介 HTTP协议是Hyper Text Transfer Protocol 超文本传输协议 的缩写 是用于从万维网 WWW World Wide Web 服务器传输超文本到本地浏览器的传送协议 HTTP是一个基于TCP IP通信协
  • 断点续传和多线程下载

    断点续传和多线程下载 HTTP是通过在Header里两个参数实现的 客户端发请求时对应的是Range 服务器端响应时对应的是Content Range Range 客户端发请求的范围 Content Range 服务端返回当前请求范围和文件
  • 【应用层2】Http协议

    一 简介 Http 即超文本传输协议 一种建立在 TCP 上的无状态连接 属于应用层协议 http传输的内容都是明文的 不安全的 Http 协议用于客户端与服务器端之间的通信 它规定了客户端与服务端之间的通信格式 包括请求和响应的格式 Ht
  • Http协议详解

    引入 超文本传输协议 HTTP HyperText Transfer Protocol 是互联网上应用最为广泛的一种网络协议 所有的WWW文件都必须遵守这个标准 设计HTTP最初的目的是为了提供一种发布和接收HTML页面的方法 1960年美

随机推荐

  • 解决Establishing SSL connection without server‘s identity verification is not recommended.

    每次从数据库中进行查询或者其他操作控制台都会出现以下警告 虽说不是error 但是很显眼 Establishing SSL connection without server s identity verification is not r
  • 03-分布式文件系统HDFS

    目录 一 HDFS简介 1 什么是HDFS 2 优缺点 2 1 优点 2 2 缺点 二 HDFS原理 1 系统架构 1 1 角色分工 1 2 设计思想 2 数据存储 2 1 文件存储 2 2 元数据存储 3 读写操作 3 1 写操作 3 2
  • 智慧城市篇

    智慧城市篇 数字孪生智慧排水管网管理平台https mp weixin qq com s ZDgmKqHRztYk2ehBDbi3AA 2022年3月1日 住房和城乡建设部印发了 十四五 住房和城乡建设科技发展规划 提出关于实现城市基础设施
  • Mybatis中的resultType和resultMap

    一 概述 MyBatis中在查询进行select映射的时候 返回类型可以用resultType 也可以用resultMap resultType是直接表示返回类型的 而resultMap则是对外部ResultMap的引用 但是resultT
  • android组件悬浮,Andorid 任意界面悬浮窗,实现悬浮窗如此简单

    特性 1 支持拖动 提供自动贴边等动画 2 内部自动进行权限申请操作 3 可自由指定要显示悬浮窗的界面 4 应用退到后台时 悬浮窗会自动隐藏 5 位置不可变的悬浮窗无需权限申请 6 位置及宽高可设置百分比值 轻松适配各分辨率 7 链式调用
  • [Python / PyTorch] debug backward()

    问题描述 在自定义Loss的中 其backward 函数不支持在PyCharm中进行断点调试 因此需要以其他方式进行断点调试 解决方案 参考 Is there a way to debug the backward method of Fu
  • SQLI-Labs(3)8-14关【布尔盲注和时间盲注】

    目录 第八关 第九关 第十关 第十一关 第十二关 第十三关 第十四关 第八关 我们用测试语句来测试是否为注入点 从上图中得知存在注入点 那么接下来就是爆列 一共有三列 接下来用union select 和报错注入都试一下发现没有回显点 那么
  • thinkPHP使用PHPExcel实现导入导出

    目录 一 使用composer安装PHPExcel 二 使用PHPExcel 1 导入Excel文件 2 导出数据 3 导出方法使用demo 效果图 一 使用composer安装PHPExcel 安装命令 composer require
  • 常见的PLC通讯协议有哪些?

    PLC 可编程逻辑控制器 通讯方式有多种 以下是一些常见的通讯方式 串口通信 使用串行接口 如RS232 RS485等 进行通信 常用于与外部设备进行简单的数据传输 以太网通信 通过以太网接口进行通信 可以实现较高的数据传输速率和远程连接
  • 键值数据库PebblesDB读后感

    键值数据库PebblesDB读后感 在LevelDB RocksDB这种分层思路上 PebblesDB提出了一种减少写放大的思路 下面学习并总结 所述以论文为基础 也有个人 观点 客观论述请看原文 虽然LSM的写放大最近被研究很多 但是就写
  • 关于log4j

    log4j 在强调可重用组件开发的今天 除了自己从头到尾开发一个可重用的日志操作类外 Apache为我们提供了一个强有力的日志操作包 Log4j 官方站点 http logging apache org log4j Log4j是Apache
  • linux拒绝更改密码,【Linux】解决SSH服务拒绝密码

    xShell连接Linux服务器提示密码错误 1 检查虚拟机SSH服务是否开启 service sshd status 如果没有开启 请执行service sshd start启动该服务 或者通过service sshd restart重启
  • web3.0 nft 是什么? nft的意义是什么?

    英国一名12岁的男孩本雅明 他在暑假期间画了一系列的画作 并在网上以数字藏品的形式进行出售 不到9小时就全部售完 赚取的虚拟货币价值相当于250万人民币 这些画算不上很高端的艺术佳作 而是由密密麻麻的像素组成各种形状各异的鲸鱼 每条鲸鱼都有
  • Vulhub漏洞靶场搭建和使用

    今天继续给大家介绍渗透测试相关知识 本文主要内容是Vulhub漏洞靶场搭建和使用 免责声明 本文所介绍的内容仅做学习交流使用 严禁利用文中技术进行非法行为 否则造成一切严重后果自负 再次强调 严禁对未授权设备进行渗透测试 一 Vulhub漏
  • 视频播放器测试点

    视频播放器测试点 在负责XX项目组的测试中 接触了好多的关于播放器的测试 基于这些 再结合我测试过程中遇到的问题整理的测试点分别从以下几个方面进行 功能测试 视频资源可以正常获取 不管是服务器返回还是后台添加等 视频的封面图 页面UI等正常
  • 【转载】关于在keil5的time environment没有StdPeriph Drivers(标准库)但是又想使用库函数的解决办法

    关于在keil5的time environment没有StdPeriph Drivers 标准库 但是又想使用库函数的解决办法 本人刚刚接触keil5 遇到了一些问题 希望我的方法能帮到大家 作者本人使用的是芯片是stm32f407VET6
  • SpringBoot配置动态定时任务

    1 配置ScheduledTask 主要是实现SchedulingConfigurer 动态传入cron package com hzl boot config import lombok Data import org springfra
  • Spring Cloud OAuth2(一) 搭建授权服务

    本文内容主要为spring cloud 授权服务的搭建 采用jwt认证 GitHub 地址 https github com fp2952 spring cloud base tree master auth center auth cen
  • [USACO13DEC]Optimal Milking G【线段树维护最大独立集】

    题目链接 P3097 USACO13DEC Optimal Milking G 很明显的是这道题有4e4个点 直接跑最大独立集的话 那么测评机承受不起啊 所以 这里要维护一个区间dp的形式 每个区间有左右两个端点 我们现在要合并两个区间的话
  • HTTP缓存

    HTTP缓存 什么是HTTP缓存 http缓存指的是 当客户端向服务器请求资源时 会先抵达浏览器缓存 如果浏览器有 要请求资源 的副本 就可以直接从浏览器缓存中提取而不是从原始服务器中提取这个资源 常见的http缓存只能缓存get请求响应的