Nginx缓存相关配置解析

文章目录

  • 前言
  • 配置示例
    • proxy_cache
    • proxy_cache_path
    • proxy_cache_key
    • proxy_cache_valid
    • proxy_cache_lock
    • proxy_cache_methods
    • proxy_cache_bypass
    • proxy_no_cache
    • proxy_cache_min_uses
    • add_header 可选项
  • 使用示例
    • 通过响应头判断是否走缓存
  • 缓存手动删除
  • 原博客


前言

客户端需要访问服务器的数据时,如果都直接向服务器发送请求,服务器接收过多的请求,压力会比较大,也比较耗时;而如果在nginx缓存一定的数据,使客户端向基于nginx的代理服务器发送请求,可以有效节省时间。

Nginx缓存机制的作用

  • 缓存能够提升性能,学会Nginx中如何使用缓存很重要。
  • Nginx作为静态资源服务器,静态资源变动频率小,缓存能够加速访问。
  • Nginx离用户最近,启用缓存能更好的提高性能,结合Redis可以组成类似二级缓存。

完整的官方配置文档

缓存放置内容过程:

  1. 当nginx从上游服务器读取响应时,首先将内容写入缓存目录结构之外的临时文件。
  2. 当nginx完成处理请求时,它会重命名临时文件并将其移动到缓存目录。如果用于代理的临时文件目录位于另一个文件系统上,则文件将被复制,因此建议将临时目录和缓存目录保留在同一个文件系统上。当需要显式清除文件时,从缓存目录结构中删除文件也是非常安全的。
  3. nginx有第三方扩展,可以远程控制缓存的内容,并计划在主发行版中集成此功能

在这里插入图片描述

缓存的资源也不是一成不变的,因此缓存也需要有更新的机制。
因此,对于Nginx的缓存主要围绕以下几点展开:

  • 缓存文件存放在哪儿
  • 缓存的有效期
  • 如何指定哪些请求走缓存,哪些请求不缓存
  • 如何删除缓存

配置示例

proxy_cache

proxy_cache:用于定义共享内存区域的名称。可以使用变量,默认值为off表示禁用缓存。此参数是proxy_cache_path 指令的基础。

该指令用来开启或关闭缓存,如果是开启则自定使用哪个缓存区来缓存

  • 开启 proxy_cache zone_name;
  • 关闭 proxy_cache off;

zone_name 为自定义名称。

配置位置:http、server、location里

proxy_cache_path

proxy_cache_path:定义缓存的存储路径。

配置位置 : 在 http中,server外

语法 :

proxy_cache_path path [levels=a:b:c] keys_zone=zone_name:zone_size [inactive=time] [max_size=sizes]
  • path : 可以是 /usr/local/proxy_cache ,为设置缓存文件的存放地址

  • levels :levels可以将字符串密文与缓存目录进行结合,指定缓存空间对应的目录,最多可以设置三层,每层取值为1或2;
    例如: levels=1:2 ,表示缓存空间有两层目录,一层是1个字母,二层是2个字母
    如果字符串密文为dsciwbdciow87y8hwdh29,那么levels=1:2最终的存储目录为:/usr/local/proxy_cache/9/h2
    该参数与 proxy_cache_key 指令有关,proxy_cache_key 的默认值为$scheme$proxy_host$request_uri,然后将获取到的值MD5加密,然后依次从末尾按照levels的设置取值来创建目录。

  • keys_zone :可以指定缓存区的名称与大小,名称就是上面proxy_cache定义的名称,例keys_zone=impar:300m 表示缓存区名称为impar,大小为300m.

  • inactive :指定缓存的数据多久未被访问会被删除的时间;inactive=2d,2d表示2天

  • max_size:设置最大的缓存空间,如果缓存空间存满,会根据LRU算法,删除最近最少使用的数据或覆盖目前缓存时间最长的数据,示例max_size=10g

proxy_cache:定义共享内存区域的名称。
proxy_cache_path:定义缓存的存储路径。

proxy_cache_key

该指令用来设置web缓存中的key值,nginx会根据key值的MD5进行哈希缓存

语法 :

proxy_cache_key string;

默认值 :

proxy_cache_key $scheme$proxy_host$request_uri;

配置位置:http、server、location里

proxy_cache_valid

该指令用来对不同返回状态码的URL设置不同的缓存时间

语法 :

proxy_cache_valid [code …] time;

配置位置:http、server、location里
示例 :

#不指定响应码,则只对200、301和302进行缓存。
proxy_cache_valid 10m;

#对指定响应码进行缓存。
proxy_cache_valid 200 301 10m;

#对任何响应码进行缓存。
proxy_cache_valid any 10m;

前面我们在配置proxy_cache_path指令时,inactive参数可以指定一定时间内缓存未被访问就会被删除。而proxy_cache_valid指定的是缓存的过期时间,超过该时间缓存将会过期,但是不会被删除。
因此我们在配置的时候,一般inactive的值会大于proxy_cache_valid中的值,否则将会导致缓存还不过期就被删除了。

proxy_cache_valid 404 1m;
proxy_cache_valid 202 302 1m;
proxy_cache_valid any 1m;
  1. 该设置从上到下进行,如果在上面的步骤中被设置(如404,202,302),就不会更改,最后的any只能设置除404,202,302以外的状态。
  2. nginx缓存代理中常有情况:nginx尚未缓存某数据,但是客户端发出请求该数据的信息,nginx往往只能先回复404。但是稍后nginx从服务器请求到了该数据后,客户端再请求该数据那按照原理必然要返回该数据,而不是404。因此,之前请求对应的返回状态码应该有一个“限定有效的时间”。这就需要靠proxy_cache_valid来设置了。

proxy_cache_valid 不是唯一设置缓存时间的,还可以通过如下方式(优先级从上到下):

以秒为单位的“X-Accel-Expires”响应头来设置响应缓存时间 如果没有“X-Accel-Expires”,可以根据“Cache-Control”、“Expires”来设置响应缓存时间 否则使用proxy_cache_valid设置的缓存时间。
如果响应头包含Cache-Control:private/no-cache/no-store、Set-Cookie或者只有一个Vary响应头且其值为*,则响应内容将不会被缓存。可以使用proxy_ignore_headers来忽略这些响应头。

proxy_cache_lock

当多个客户端同时请求同一份内容时,如果开启proxy_cache_lock(默认off)则只有一个请求被发送至后端;其他请求将等待该内容返回;当第一个请求返回时,其他请求将从缓存中获取内容返回;当第一个请求超过了proxy_cache_lock_timeout超时时间(默认5s),则其他请求将同时请求到后端来获取响应,且响应不会被缓存;启用proxy_cache_lock可以应对雪崩效应。

proxy_cache_lock_age time;

默认值 :

proxy_cache_lock_age 5s;

配置位置:http、server、location里

proxy_cache_methods

该指令用户设置哪些http方法可以被缓存

proxy_cache_methods method

method可选方式为GET, HEAD, POST.
默认方式为GET, HEAD。

配置位置:http、server、location里

proxy_cache_bypass

该指令配置不走缓存响应的条件,如果条件命中,则不走缓存。可与proxy_no_cache配合使用。
如果参数中的值至少有一个值不为空且不为"0",则不走缓存响应。

# 以$arg开头的参数表示url中的对应的参数。
proxy_cache_bypass $cookie_nocache $arg_nocache$arg_comment;

proxy_no_cache

该指令配置不缓存响应的条件,如果条件命中,则不缓存。可与proxy_cache_bypass配合使用。

配置位置:http、server、location里

语法:proxy_no_cache string …;

如果参数中的值至少有一个值不为空且不为"0",则不缓存响应。

# 以$arg开头的参数表示url中的对应的参数。
proxy_no_cache $cookie_nocache $arg_nocache$arg_comment;

proxy_cache_min_uses

该指令设置某个请求达到指定次数后,才对其进行缓存。

配置位置:http、server、location里

语法:

proxy_cache_min_uses number;

默认值:proxy_cache_min_uses 1;

add_header 可选项

当前选项不是必须的,只是方便在测试的时候查看是否命中缓存

add_header nginx-cache $upstream_cache_status;

可添加的头示例 :

  1. add_header Access-Control-Allow-Methods
    明确了客户端所要访问的资源允许使用的方法或方法列表,可以是"GET,OPTIONS,POST,HEAD,PUT,DELETE"

  2. add_header Accept-Ranges
    此字段的值表示可用于定义范围的单位,可以是"bytes"

  3. add_header Access-Control-Allow-Origin "*"
    表示服务器可以接受所有的请求源(Origin),即接受所有跨域的请求。

  4. add_header Access-Control-Allow-Headers
    可支持的请求首部名字。请求头会列出所有支持的首部列表,用逗号隔开。
    示例:

  5. add_header Access-Control-Allow-Headers "*"
    注意以下这些特定的首部是一直允许的:Accept, Accept-Language, Content-Language, Content-Type,这些被称作simple headers,无需特意声明它们。

使用示例

使用内置$upstream_cache_status变量可以查看缓存命中状态。状态值分别为MISS、BYPASS、EXPIRED、STALE、UPDATING、REVALIDATED、HIT。

在响应中添加Nginx-Cache头,显示缓存命中状态.

配置服务端前置Nginx :

http {
	# 缓存在10分钟之内未被访问即删除
	proxy_cache_path /home/stone/proxy_cache levels=1:2 keys_zone=my_cache:10M inactive=10m max_size=10G;
	server {
		listen       80;
		server_name  localhost;

        location /cache {
            proxy_cache my_cache;
            proxy_cache_key $uri$is_args$args;
            # 缓存的有效期会10s
            proxy_cache_valid any 10s;
            proxy_cache_min_uses 1;
            # 添加缓存命中状态,$upstream_cache_status
            add_header Nginx-Cache $upstream_cache_status;
            proxy_pass http://127.0.0.1:81;
        }
	}



}

同时在html文件夹下创建cache文件,并放入test.html文件。

代码块 :

	server {
		listen       81;
		server_name  localhost;

        location /cache {
            root html;
        }
	}

访问http://127.0.0.1:80/cache/test.html

第一次访问:缓存状态为MISS,即未命中。

在这里插入图片描述

第二次访问:缓存状态为HIT,即已命中缓存。

在这里插入图片描述

查看缓存文件夹,已经按照levels参数指定的规则生成目录结构,并缓存文件。
在这里插入图片描述

第三次访问:缓存状态为EXPIRED,缓存已过期,因为我们设置的10s过期。

在这里插入图片描述

通过响应头判断是否走缓存

首次访问 http://localhost:7000/cache/

在这里插入图片描述

服务器返回如下几个缓存控制头部:

  • Last-Modified:表示文档的最后修改时间,当去服务器验证时会拿这个时间去;
    Expires:http/1.0规范定义,表示文档在浏览器中的过期时间,当缓存的内容超过这个时间则需要重新去服务器获取最新的内容;
  • Cache-Control:http/1.1规范定义,表示浏览器缓存控制,例:Cache-Control: public, max-age=31536000,max-age=3153600表示文档可以在浏览器中缓存一年。
  • ETag:发送到服务端进行内容变更验证的,而Catch-Control是用于控制缓存时间的(浏览器、代理层等)。此处我们使用了弱实体W\”6124c”,弱实体(”6124c”)只要内容语义没变即可,比如内容的gzip版和非gzip版可以使用弱实体验证;而强实体指字节必须完全一致(gzip和非gzip情况是不一样的),因此建议首先选择使用弱实体。

nginx在生成etag时使用的算法是Last-Modified + Content-Length计算的。根据规范定义Cache-Control优先级高于Expires,实际使用时可以两个都用,或仅使用Cache-Control就可以了。一般情况下Expires=当前系统时间(Date) + 缓存时间(Cache-Control: max-age)。

再次访问 http://localhost:7000/cache/ 时,发现浏览器请求头部有变化:

在这里插入图片描述

在这里插入图片描述

  • Modified-Since请求头,其值是上次请求响应中的Last-Modified,即浏览器会拿这个时间去服务端验证内容是否发生了变更。

  • If-None-Match请求头,其值是上次请求响应中的ETag,即浏览器会拿这个时间去服务端验证内容是否发生了变更。

Last-Modified与ETag同时使用时,浏览器在验证时会同时发送If-Modified-Since和If-None-Match,按照http/1.1规范,如果同时使用If-Modified-Since和If-None-Match则服务端必须两个都验证通过后才能返回304;且nginx就是这样做的。因此实际使用时应该根据实际情况选择。

当我们按下cmd-F5强制刷新后:浏览器在请求时不会带上If-Modified-Since,并带上Cache-Control:no-cache和Pragma:no-cache,这是为了告诉服务端说我请给我一份最新的内容。

通过响应状态码判断是否走缓存

304 Not Modified
304表示服务器返回文档没有过期

200 (from cache) 表示浏览器直接使用缓存数据

Last-Modified/Modified-Since 用于验证文档内容是否变更 max-age/Expires 定义文档缓存时间,如在有效期内会返回 200(from cache)

原文博客

缓存手动删除

如果服务端的文件发生变化,那么也需要将文件同步到Nginx的缓存中去,因此我们需要对缓存进行删除。

  • 删除对应缓存目录:这种方式看上去简单粗暴,但是想要删除指定的缓存,则犹如大海捞针。

    • rm -rf /home/stone/proxy_cache
  • ngx_cache_purge:第三方模块,通过请求删除指定的缓存文件。

ngx_cache_purge :

可以借助第三方模块ngx_cache_purge来实现对指定缓存的删除。

下载地址

语法:

proxy_cache_purge keys_zone key;
  • keys_zone:该参数为proxy_cache指令指定的值。
  • key:该参数为proxy_cache_key指定的值。

配置位置:location里

示例 :

server {
	listen       80;
	server_name  localhost;

	location /cache {
		proxy_cache my_cache;
		# 设置proxy_cache_key
		proxy_cache_key $uri$is_args$args;
		proxy_cache_valid 200 302 10s;
		# 添加缓存命中状态
		add_header Nginx-Cache $upstream_cache_status;
		proxy_pass http://127.0.0.1:81;
	}

	# 删除指定缓存
	location ~/purge(/.*) {
		proxy_cache_purge my_cache $1$is_args$args;
	}
}

原博客

案例博客原文

案例学习原文

知乎案例博客

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/399134.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

10、内网安全-横向移动域控提权NetLogonADCSPACKDC永恒之蓝

用途:个人学习笔记,有所借鉴,欢迎指正! 背景: 主要针对内网主机中的 域控提权漏洞,包含漏洞探针和漏洞复现利用。 1、横向移动-系统漏洞-CVE-2017-0146(ms17-010,永恒之蓝&#xff0…

如何添加或编辑自定义WordPress侧边栏

WordPress侧边栏是许多WordPress网站上的固定装置。它为您的内容提供了一个垂直空间,您可以在其中帮助读者导航、增加电子邮件列表或社交关注、展示广告等。 因为它是许多WordPress网站不可或缺的一部分,所以我们认为侧边栏值得拥有自己的大型指南。在这…

SpringBootWeb学习笔记——12万字详细总结!

0. 写在前面 注:这套笔记是根据黑马程序员B站2023-3-21的视频学习的成果,其中省略了前端基础部分、Maven部分和数据库基础部分,详情可见目录。 注注:目前文章内结尾处多幅图片加载不出来,因为图片还存在本地没被传上来,过段时间再改~ 所有的Spring项目都基于Spring Fra…

3、windows环境下vscode开发c/c++环境配置(二)

前言:上一篇文章写了windows环境下,配置vscode的c/c开发环境,这一篇讲vscode开发c/c的配置文件,包括c_cpp_propertues.json,task.json及launch.json。 一、总体流程 通过c/c插件我们就可以来编写c/c程序了&#xff0c…

网贷大数据查询多了对征信有影响吗?

网贷大数据在日常的金融借贷中起到很重要的风控作用,不少银行已经将大数据检测作为重要的风控环节。很多人在申贷之前都会提前了解自己的大数据信用情况,那网贷大数据查询多了对征信有影响吗?本文带你一起去看看。 首先要说结论:那就是查询网…

面试经典150题——同构字符串

"Dream big and dare to fail." - Norman Vaughan 1. 题目描述 2. 题目分析与解析 2.1 思路一 看见这个题目的第一反应就是使用一个hash表,用来存储映射关系,具体思路如下: 首先二者要是同构的长度肯定是得相同的,但…

Android 多线程并发优化实现

和你一起终身学习,这里是程序员Android 经典好文推荐,通过阅读本文,您将收获以下知识点: 一、Thread 使用二、Android Thread三.线程优先级 一、Thread 使用 在讲解多线程之前,我们先来讲解Thread使用几个需要注意的点&#xff1a…

Unity UGUI的DrawCall优化

Unity UGUI是一种强大的用户界面设计工具,它可以帮助开发者快速创建各种界面元素,从按钮和文本到滑块和面板等。然而,在使用UGUI时,一个常见的性能瓶颈就是DrawCall过多导致的性能下降。在本文中,我们将深入探讨UGUI的…

集成使用 GitHub Copilot 提升 IDEA 开发效率

集成使用 GitHub Copilot 提升 IDEA 开发效率 在现代软件开发中,集成开发环境(IDE)如IntelliJ IDEA已经成为开发人员不可或缺的工具。它们提供了代码编辑、调试、版本控制等一系列功能,极大地提高了开发效率。而GitHub Copilot作…

C# Winfrom实例:武汉智能安检闸机数据接收和解析

项目介绍:本实例主要是接收安检闸机的数据解析并显示到界面上,只做功能实现,不做界面美化 硬件:闸机一个、网线一根、电脑主机开发环境:vs2017 系统:win10涵盖知识点:tcp通讯、文件写入、多线程…

《软件方法(下)》8.2.5.2 属性是否直接描述类(202402更新)(2)

导致出现违反本要点的错误的原因有: (1)缺少抽象能力 缺少抽象能力的建模人员经常会把手上素材的信息,一一对应地映射为类和属性,导致本来属于多个类的信息被合并在一个类中。 如图8-63,建模人员对照着一…

ETL、ELT区别以及如何正确运用

一、 浅谈ETL、ELT ETL与ELT的概念 ETL (Extract, Transform, Load) 是一种数据集成过程,通常用于将数据从一个或多个源系统抽取出来,经过清洗、转换等处理后,加载到目标数据存储中。这种方法适用于需要对数据进行加工和整合后再加载到目标…

Django学习笔记-HTML实现MySQL的图片上传

1.django项目编写index.html代码 创建form表单,路由指向upload,请求方式post,enctype设置"multipart/form-data", post请求添加{% csrf_token %},编写两个input,上传和提交 2.添加upload路由 3.views中创建upload 1).获取上传的文件,没有上传则返回"没有指定…

打码半年,开源一款自定义大屏设计软件!

hi,大家好,我是Tduck马马。 最近我们开源了一款大屏软件-TReport,与大家分享。 TReport是一款基于Vue3技术栈的数据可视化系统,支持静态、动态api等数据源;可用于数据可视化分析、报表分析、海报设计使用。 提供自定…

Stable Diffusion 绘画入门教程(webui)-图生图

通过之前的文章相信大家对文生图已经不陌生了,那么图生图是干啥的呢? 简单理解就是根据我们给出的图片做为参考进行生成图片。 一、能干啥 这里举两个例子 1、二次元头像 真人转二次元,或者二次元转真人都行, 下图为真人转二次…

.net6 webapi log4net完整配置使用流程

前置&#xff1a;为项目安装如下两个依赖 1.创建文件夹cfgFile 2.创建log4net.Config <?xml version"1.0" encoding"utf-8" ?> <log4net><appender name"ConsoleAppender" type"log4net.Appender.ConsoleAppender"…

使用备份工具xtrabackup进行差异备份详细讲解

差异备份 基于第一天进行差异备份 删除之前修改的数据备份 [rootservice ~]# rm -rf /data/backup/* [rootservice ~]# ls /data/backup 完整备份 [rootservice ~]# xtrabackup --defaults-file/etc/my.cnf --backup --target-dir/data/backup/base/ -uroot -pWyxbuke00. -H…

Collection集合体系(ArrayList,LinekdList,HashSet,LinkedHashSet,TreeSet,Collections)

目录 一.Collection 二.List集合 三.ArrayList集合 四.LinkedList集合 五.Set集合 六.hashSet集合 七.LinkedHashSet集合 八.TreeSet集合 九.集合工具类Collections 集合体系概述 单列集合&#xff1a;Collection代表单列集合&#xff0c;每个元素&#…

大白话说说Docker容器默认网络模型工作原理

Docker的默认网络模型 —— 桥接模式&#xff08;Bridge&#xff09; 当你不做任何特殊设置时&#xff0c;Docker会使用一种叫做“桥接模式”的网络设置。这就像是给你的容器小房子安装了一个虚拟的桥接网络。这座桥连接着容器和你的电脑&#xff08;宿主机&#xff09;&#…

Jmeter之内置函数__property和__P的区别

1. __property函数 作用 读取 Jmeter 属性 语法格式 ${__property(key,var,default)} 参数讲解 小栗子 ${__property(key)} 读取 key 属性如果找不到 key 属性&#xff0c;则返回 key&#xff08;属性名&#xff09; ${__property(key,,default)} 读取 key 属性如果找不到 k…