18个运维必知的Nginx代理缓存配置技巧(你都掌握了哪些呢)

我们都知道应用程序和网站的性能是他们成功的关键因素。但是,使您的应用程序或网站表现更好的过程并不总是很清楚。代码质量和基础架构当然至关重要,但在许多情况下,您可以通过专注于一些非常基本的应用程序的交付技术,对应用程序的最终用户体验进行大量改进。

其中一个例子是在应用程序栈中实现和优化缓存。在教程中介绍的技术可以帮助新手和高级用户使用 Nginx 中包含的内容缓存功能,从而获得更好的性能。

概览

内容缓存位于客户端和源服务器 (upstream) 之间,并保存它看到的所有内容的副本。如果客户端请求缓存已存储的内容,则它会直接返回内容而不连接源服务器。这提高了性能,因为内容缓存更靠近客户端,并且更有效地使用应用程序服务器,因为它们不必每次都从头开始生成页面。

Web 浏览器和应用程序服务器之间可能存在多个缓存:客户端的浏览器缓存,中间缓存,内容交付网络(CDN)以及位于应用程序服务器前面的负载平衡器或反向代理。即使在反向代理/负载均衡器级别,缓存也可以极大地提高性能。

这里举一个例子,比如我的站点使用 Next.js 服务器端口渲染,由于服务器性能比较差,当然 $5 的服务器,并不能期望好到那里去,能用就已经非常了不起,能进入这个局域网就好了,别期望太多。

每次打开页面将近花费 7 秒左右,当这其中包含网络延迟,但当我直接在服务器端(127.0.0.1) 发起请求时,时间接近 5 秒,然后再排除从数据库获取数据时间,服务器端渲染时间用了 4.5 秒,实在太慢,此时我能想到最快解决问题答案就是缓存,但在那里加入缓存,从每一步时间看来,在 Nginx 加入缓存最快解决问题

Nginx 通常作为应用程序堆栈中的反向代理或负载平衡器部署,并具有一整套缓存功能。下面我们将讨论如何使用 Nginx 配置基本缓存。

如何设置和配置基本缓存

只需要两个指令即可启用基本缓存:proxy_cache_path 和 proxy_cache。

proxy_cache_path 指令设置缓存的路径和配置,proxy_cache 用来指令激活它。

proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max_size=10g
         inactive=60m use_temp_path=off; 

server {
  # ...
  location / {
    proxy_cache my_cache;
    proxy_pass http://my_upstream;
  }
}

proxy_cache_path 指令的参数定义了以下设置:

缓存的本地磁盘目录称为 /path/to/cache/。

  • levels 在/path/to/cache/ 下设置一个两级目录层次结构。在单个目录中包含大量文件会降低文件访问速度,因此我们建议对大多数部署使用两级目录层次结构。如果 levels 未包含该参数,Nginx 会将所有文件放在同一目录中。
  • keys_zone 设置共享内存区域,用于存储缓存键和元数据,例如使用计时器。拥有内存中的密钥副本,Nginx 可以快速确定请求是否是一个 HIT 或 MISS 不必转到磁盘,从而大大加快了检查速度。1 MB 区域可以存储大约 8,000 个密钥的数据,因此示例中配置的 10 MB 区域可以存储大约 80,000 个密钥的数据。
  • max_size 设置缓存大小的上限(在本例中为 10 千兆字节)。它是可选的; 不指定值允许缓存增长以使用所有可用磁盘空间。当缓存大小达到限制时,一个称为缓存管理器的进程将删除最近最少使用的缓存,将大小恢复到限制之下的文件。
  • inactive 指定项目在未被访问的情况下可以保留在缓存中的时间长度。在此示例中,缓存管理器进程会自动从缓存中删除 60 分钟未请求的文件,无论其是否已过期。默认值为 10 分钟(10m)。非活动内容与过期内容不同。Nginx 不会自动删除缓存 header 定义为已过期内容(例如 Cache-Control:max-age=120)。过期(陈旧)内容仅在指定时间内未被访问时被删除。访问过期内容时,Nginx 会从原始服务器刷新它并重置 inactive 计时器。
  • Nginx 首先将发往高速缓存的文件写入临时存储区域,use_temp_path=off 指令指示 NGINX 将它们写入将被高速缓存的相同目录。我们建议您将此参数设置 off 为避免在文件系统之间进行不必要的数据复制。use_temp_path 在 Nginx 1.7.10 中引入。

最后,该 proxy_cache 指令激活与父 location 块的 URL 匹配的所有内容的缓存(在示例中为/)。您还可以在 server 块中包含 proxy_cache 指令; 它适用于没有自己的 location 指令的服务器的所有块。

当上游服务器关闭()时提供缓存内容

Nginx 内容缓存的一个强大功能是,Nginx 可以配置为在无法从原始服务器获取新内容时从缓存中提供已缓存的内容。如果缓存资源的所有源服务器都已关闭或暂时占用,则会发生这种情况。

Nginx 不是将错误传递给客户端,而是从缓存中提供文件的陈旧版本。这为 Nginx 代理的服务器提供了额外的容错能力,并确保在服务器故障或流量高峰时的正常运行时间。要启用此功能,请包含 proxy_cache_use_stale 指令:

location / {
  # ...
  proxy_cache_use_stale error timeout http_500 http_502 http_503 http_504;
}

使用此示例配置,如果 Nginx 从原始服务器收到一个 error,timeout 或任何指定的 5xx 错误,并且在其缓存中具有所请求文件的过时版本,则它会传递过时文件,而不是将错误转发到客户端。

如何提高缓存性能

Nginx 具有丰富的可选设置,可用于微调缓存的性能。这是一个激活其中一些的例子:

proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max_size=10g
         inactive=60m use_temp_path=off; 

server {
  # ...
  location / {
    proxy_cache my_cache;
    proxy_cache_revalidate on;
    proxy_cache_min_uses 3;
    proxy_cache_use_stale error timeout updating http_500 http_502
               http_503 http_504;
    proxy_cache_background_update on;
    proxy_cache_lock on; 

    proxy_pass http://my_upstream;
  }
}

这些指令配置以下行为:

  • proxy_cache_revalidate 指示 Nginx 在使用 GET 条件请求时,从源服务器刷新内容。如果客户端请求缓存但是由缓存控制头定义的过期的内容,则 Nginx将 If-Modified-Since 字段包含在 GET 请求的标头中将它发送到源服务器。因为服务器只有在 Nginx 最初缓存它时自附加到文件的标题 Last-Modified 中记录的时间以来修改了整个项目。
  • proxy_cache_min_uses 设置客户端在 Nginx 缓存之前必须请求多少次才被缓存。如果缓存不断填满,这将非常有用,因为它可确保只将最常访问的项添加到缓存中。默认 proxy_cache_min_uses 设置为 1。
  • 指令 updating 参数 proxy_cache_use_stale 与启用 proxy_cache_background_update 指令相结合,指示当客户端请求已过期或正在从原始服务器更新的项目时,Nginx 会传递过时的内容。所有更新都将在后台完成。在完全下载更新的文件之前,将为所有请求返回陈旧文件。
  • 与 proxy_cache_lock 启用,如果多个客户端请求的文件不在缓存(MISS),只有第一个这些请求是通过原始服务器的。其余请求等待满足该请求,然后从缓存中提取文件。如果 proxy_cache_lock 未启用,会导致缓存未命中的所有请求都将直接发送到源服务器。

跨多个硬盘拆分缓存

如果您有多个硬盘驱动器,可以使用 Nginx 在它们之间拆分缓存。以下示例根据请求 URI 将客户端均匀分布在两个硬盘驱动器上:

proxy_cache_path /path/to/hdd1 levels=1:2 keys_zone=my_cache_hdd1:10m
         max_size=10g inactive=60m use_temp_path=off;
proxy_cache_path /path/to/hdd2 levels=1:2 keys_zone=my_cache_hdd2:10m
         max_size=10g inactive=60m use_temp_path=off; 

split_clients $request_uri $my_cache {
       50%     “my_cache_hdd1”;
       50%     “my_cache_hdd2”;
} 

server {
  # ...
  location / {
    proxy_cache $my_cache;
    proxy_pass http://my_upstream;
  }
}

这两个 proxy_cache_path 指令在两个不同的硬盘驱动器上定义了两个缓存(my_cache_hdd1 和 my_cache_hdd2)。

split_clients 配置块指定从一半的请求(结果50%)被缓存在 my_cache_hdd1 与另一半中 my_cache_hdd2。基于 $request_uri 变量的哈希(请求URI)确定每个请求使用哪个缓存,结果是对给定URI的请求总是缓存在同一缓存中。

请注意,此方法不能替代 RAID 硬盘设置。如果存在硬盘驱动器故障,则可能导致系统出现不可预测的行为,包括用户看到针对故障硬盘驱动器的请求的 500 响应代码。适当的 RAID 硬盘设置可以处理硬盘故障。

如何对 Nginx Cache 进行检测

可以在响应头中加入 $upstream_cache_status 变量以进行检测

add_header X-Cache-Status $upstream_cache_status;

此示例 X-Cache-Status 在响应客户端时添加 HTTP 标头。以下是可能的值 $upstream_cache_status:

  • MISS - 在缓存中找不到响应,因此从原始服务器获取响应。然后缓存响应。
  • BYPASS - 响应是从原始服务器获取的,而不是从缓存中提供的,因为请求与 proxy_cache_bypass 指令匹配
  • EXPIRED - 缓存中的条目已过期。响应包含来自原始服务器的新内容。
  • STALE- 内容过时,因为源服务器未正确响应但 proxy_cache_use_stale 已配置。
  • UPDATING- 内容过时,因为条目当前正在更新以响应先前的请求,并且 proxy_cache_use_stale updating 已配置。
  • REVALIDATED- proxy_cache_revalidate 指令已启用,Nginx 验证当前缓存的内容是否仍然有效通过(If-Modified-Since或If-None-Match)。
  • HIT - 响应直接来自有效的缓存

Nginx 如何确定是否要缓存响应

默认情况下,Nginx 尊重 Cache-Control 源服务器的标头。它不缓存响应 Cache-Control 设置为 Private,No-Cache 或 No-Store 或 Set-Cookie 在响应头。Nginx 只缓存 GET 和 HEAD 客户端请求。您可以按照以下答案中的说明覆盖这些默认值。

如果 proxy_buffering 设置为 off,Nginx 不会缓存响应。on 默认的。

Nginx 是否可以忽略 Cache-Control

使用 proxy_ignore_headers 指令可以忽略 Cache-Control

location /images/ {
  proxy_cache my_cache;
  proxy_ignore_headers Cache-Control;
  proxy_cache_valid any 30m;
  # ...
}

Nginx 忽略 /images/ Cache-Control 下所有内容的标题。该指令强制缓存数据到期,如果忽略标头则需要。Nginx 不会缓存没有过期的文件。

Nginx 是否可以忽略 Set-Cookie

使用 proxy_ignore_headers 指令即可。

Nginx 如何缓存 POST 请求

使用 proxy_cache_methods 指令:

proxy_cache_methods GET HEAD POST;

此示例启用了POST请求的缓存。

Nginx 如何缓存动态内容
只要 Cache-Control 标头允许。即使在很短的时间内缓存动态内容也可以减少原始服务器和数据库的负载,从而缩短第一个字节的时间,因为不必为每个请求重新生成页面。

如何不使用 Nginx 缓存

proxy_cache_bypass 指令

location / {
  proxy_cache_bypass $cookie_nocache $arg_nocache;
  # ...
}

该指令定义了 Nginx 立即从源服务器请求内容的请求类型,而不是首先尝试在缓存中找到它。这有时被称为通过缓存 “打孔”。

Nginx 使用什么缓存密钥

Nginx 生成的密钥的默认形式类似于以下 Nginx 变量的 MD5 哈希:$scheme$proxy_host$request_uri; 使用的实际算法稍微复杂一些。

proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max_size=10g
         inactive=60m use_temp_path=off; 

server {
  # ...
  location / {
    proxy_cache my_cache;
    proxy_pass http://my_upstream;
  }
}

对于此示例配置,缓存密钥 http://www.example.org/my_image.jpg 计算为 md5(“http://my_upstream:80/my_image.jpg”)。

请注意,proxy_host 变量用于散列值而不是实际主机名(www.example.com)。proxy_host 定义为 proxy_pass 指令中指定的代理服务器的名称和端口。

要更改用作密钥基础的变量,请使用该 proxy_cache_key 指令。

使用 Cookie 作为我的缓存密钥的一部分

缓存键可以配置为任意值,例如:

proxy_cache_key $proxy_host$request_uri$cookie_jessionid;

此示例将 JSESSIONID cookie 的值合并到缓存键中。具有相同 URI 但 JSESSIONID 值不同的项目将作为唯一项目单独缓存。

Nginx 使用 ETag 标头

在 Nginx 1.7.3 及更高版本中,ETag 标头完全支持 If-None-Match。

Nginx 如何处理字节范围请求

如果文件在高速缓存中是最新的,则 Nginx 遵循字节范围请求并仅向项目客户端提供项目的指定字节。如果文件未缓存,或者文件过时,Nginx 会从原始服务器下载整个文件。

如果请求是针对单个字节范围的,则 Nginx 会在下载流中遇到该范围后立即将该范围发送到客户端。如果请求在同一文件中指定了多个字节范围,则 Nginx 会在下载完成时将整个文件传送到客户端。

下载完成后,Nginx 会将整个资源移动到缓存中,以便从缓存中立即满足所有未来的字节范围请求,无论是单个范围还是多个范围。

请注意,upstream 服务器必须支持 Nginx 的字节范围请求,以支持对该 upstream 服务器的字节范围请求。

Nginx 如何处理 Pragma 标头

在 Pragma:no-cache 报头由客户加入到绕过所有中间缓存,直接进入到源服务器的请求的内容。Pragma 默认情况下,Nginx 不支持标头,但您可以使用以下 proxy_cache_bypass 指令配置该功能:

location /images/ {
  proxy_cache my_cache;
  proxy_cache_bypass $http_pragma;
  # ...
}

Nginx 是否支持标头 stale-while-revalidate 和 stale-if-error 以及扩展的 Cache-Control

Nginx 1.11.10 及更高版本中支持。这些扩展做了什么:

如果当前正在更新 stale-while-revalidate,Cache-Control HTTP 标头的扩展允许使用陈旧的缓存响应。HTTP 标头的 stale-if-error 扩展 Cache-Control 允许在发生错误时使用陈旧的缓存响应。这些头具有比较低优先级, proxy_cache_use_stale 指令如上所述。

Nginx 是否支持 Vary 标头

Nginx 1.7.7 以及更高版本中是支持 Vary 标头的 。

结论

至此,您应该很好地理解 Nginx 代理缓存的工作原理以及如何正确配置 Nginx 代理缓存。如果您有任何问题或反馈,请随时发表评论。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • 如何在nginx中配置缓存静态文件

    这篇教程说明你应该怎样配置 nginx.设置 HTTP 头部过期时间,用 Cache-Control 中的 max-age 标记为静态文件(比如图片. CSS 和 Javascript 文件)设置一个时间,这样用户的浏览器就会缓存这些文件.这样能节省带宽,并且在访问你的网站时会显得更快些(如果用户第二次访问你的网站,将会使用浏览器缓存中的静态文件). 1.准备事项 我想你需要一个正常工作的 nginx 软件,就像这篇教程里展示的:在Ubuntu 16.04 LTS 上安装 Nginx,PHP 7

  • Nginx服务器中强制使用缓存的配置及缓存优先级的讲解

    nginx代理做好了,缓存也配置好了,但是发现css.js.jpg这些静态文件统统都cached成功.但是偏偏页面文件依旧到源服务器取. 1. nginx不缓存原因 默认情况下,nginx是否缓存是由nginx缓存服务器与源服务器共同决定的, 缓存服务器需要严格遵守源服务器响应的header来决定是否缓存以及缓存的时常.header主要有如下: Cache-control:no-cache.no-store 如果出现这两值,nginx缓存服务器是绝对不会缓存的 Expires:1980-01-0

  • Nginx内容缓存以及常见参数配置详析

    使用场景: 项目的页面需要加载很多数据,也不是经常变化的,不涉及个性化定制,为每次请求去动态生成数据,性能比不上根据请求路由和参数缓存一下结果,使用 Nginx 缓存将大幅度提升请求速度. 基础 只需要配置 proxy_cache_path 和 proxy_cache 就可以开启内容缓存,前者用来设置缓存的路径和配置,后者用来启用缓存. http { ... proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max

  • Nginx服务器作反向代理时的缓存配置要点解析

    这里给出示例,并详解. http { [...] [...] proxy_cache_path /data/nginx/cache/one levels=1:2 keys_zone=one:10m max_size=10g; proxy_cache_key "$host$request_uri"; server { server_name www.jb51.net jb51.net; root /home/www.jb51.net/web; index index.php index.

  • Nginx服务器上搭建图片缓存服务的基本配置解析

    最近准备用nginx搭建了一个图片服务器,看中的就是nginx超强的静态文件处理能力. 由于图片量比较大,和web服务器(也是nginx)分开运行,虽然web服务器调用图片没用问题,但毕竟是远程调用,肯定没有本地文件系统那么快,因此仍然有优化的空间. proxy_store 使用前的nginx配置 location ~* ^.+\.(js|ico|gif|jpg|jpeg|png|html|htm)$ { log_not_found off; access_log off; expires 7d

  • Nginx缓存文件与动态文件自动均衡的配置脚本

    nginx Nginx (engine x) 是一个高性能的HTTP和反向代理服务,也是一个IMAP/POP3/SMTP服务.Nginx是由伊戈尔·赛索耶夫为俄罗斯访问量第二的Rambler.ru站点(俄文:Рамблер)开发的,第一个公开版本0.1.0发布于2004年10月4日. Nginx是一款轻量级的Web 服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器,并在一个BSD-like 协议下发行.其特点是占有内存少,并发能力强,事实上nginx的并发能力确实在同类型的网页服

  • 18个运维必知的Nginx代理缓存配置技巧(你都掌握了哪些呢)

    我们都知道应用程序和网站的性能是他们成功的关键因素.但是,使您的应用程序或网站表现更好的过程并不总是很清楚.代码质量和基础架构当然至关重要,但在许多情况下,您可以通过专注于一些非常基本的应用程序的交付技术,对应用程序的最终用户体验进行大量改进. 其中一个例子是在应用程序栈中实现和优化缓存.在教程中介绍的技术可以帮助新手和高级用户使用 Nginx 中包含的内容缓存功能,从而获得更好的性能. 概览 内容缓存位于客户端和源服务器 (upstream) 之间,并保存它看到的所有内容的副本.如果客户端请求

  • nginx proxy_cache 缓存配置详解

    前言: 由于本人工作原因,涉及到网络直播领域,其中视频的回放下载,涉及到了一些视频下载方面的技术.针对于一个完整视频的下载,目前市面上的主流做法是,先将整个视频流切片,存储到文件服务器中,在用户需要观看回放视频时.通过一个视频回源服务器,去文件服务器中逐个请求切片,返回给用户播放. 今天着重探讨的是关于回源服务器缓存的配置以及合理的缓存策略. 通过给回源服务器配置缓存的案例,详细讲解一整套缓存配置机制,并且可沿用到其他任何缓存配置场景中. 今天的讲解分为四点: 回源服务器的工作是啥为啥 需要给回

  • 通过Nginx代理转发配置实现跨域的方法(API代理转发)

    前言 在WEB开发中,我们经常涉及到跨域的请求,解决跨域问题的方式有很多,比如有window.name.iframe.JSONP.CORS等等,就不详细展开了,涉及到 协议.端口 不一样的跨域请求方式是采用代理,这里我们重点聊聊Nginx代理的方式. 场景 本地启动了一个前后端分离的WEB应用,端口为:3000,可以通过http://127.0.0.1:3000访问前端页面,页面中有些Ajax请求的地址为http://127.0.0.1:3000/api/getList,一般情况下肯定是404或

  • 前端开发必知的15个jQuery小技巧

    下面这些简单的小技巧能够帮助你玩转jQuery. 1.返回顶部按钮 通过使用jQuery中的animate 和scrollTop 方法,不用插件就可以创建一个滚动到顶部的简单动画: // Back to top $('.top').click(function (e) { e.preventDefault(); $('html, body').animate({scrollTop: 0}, 800); }); <!-- Create an anchor tag --> <a class=

  • 如何利用nginx做代理缓存浅析

    用到缓存就是为了减少后端的压力,提高网站并发.在网站设计中,为了更好的去中心化,我们会尽量将请求集中到前端,在前端就能处理掉. 常用的缓存类型有客户端缓存.代理缓存.服务端缓存等. 客户端缓存[缓存存到本地,如数据存到用户的浏览器缓存中,从本地读取]代理缓存[缓存存到代理或中间件上,如从服务端获取到的数据放置在nginx上,访问时直接读取nginx的缓存]服务端缓存[缓存存到服务端,经常使用redis和memchache,比如key-value格式的数据] 代理缓存简略示意:  nginx代理缓

  • 基于Nginx的Mencached缓存配置详解

    简介 memcached是一套分布式的高速缓存系统,memcached缺乏认证以及安全管制,这代表应该将memcached服务器放置在防火墙后.memcached的API使用三十二比特的循环冗余校验(CRC-32)计算键值后,将数据分散在不同的机器上.当表格满了以后,接下来新增的数据会以LRU机制替换掉.由于memcached通常只是当作缓存系统使用,所以使用memcached的应用程序在写回较慢的系统时(像是后端的数据库)需要额外的代码更新memcached内的数据 特征 memcached作

  • Python运维自动化之nginx配置文件对比操作示例

    本文实例讲述了Python运维自动化之nginx配置文件对比操作.分享给大家供大家参考,具体如下: 文件差异对比diff.py #!/usr/bin/env python # import difflib import sys try: textfile1=sys.argv[1] textfile2=sys.argv[2] except exception,e: print "Error:"+str(2) print "Usge: difflib.py file1 file2

  • 运维人员处理服务器故障的方法总结

    我们团队为上一家公司承担运维.优化和扩展工作的时候,我们碰到了各种不同规模的性能很差的系统和基础设备(大型系统居多,比如CNN或者世界银行的系统).要是再赶上修复时间紧.奇葩的技术平台.缺少信息和文档,基本上这过程都会惨痛到让我们留下深刻的记忆. 遇到服务器故障,问题出现的原因很少可以一下就想到.我们基本上都会从以下步骤入手: 一.尽可能搞清楚问题的前因后果 不要一下子就扎到服务器前面,你需要先搞明白对这台服务器有多少已知的情况,还有故障的具体情况.不然你很可能就是在无的放矢. 必须搞清楚的问题

  • 关于Android中drawable必知的一些规则

    前言 一入 Android 深似海,相信很多 Android 开发者深有体会,Android 系统版本的碎片化,Android 硬件设备的多样性,第三方 Rom 的不确定因素.现在想开发一个合格的商业化 App 真的不容易,先不说别的,应用的兼容性就是一项技术和耐心的双重考验,想完美适配各种情况可以说是不可能的,往往都是在人力和适配率之间寻找平衡,今天要说的 drawable 就是需要适配的一个重要角色. 配置限定符 对于不同的屏幕密度.不同的设备方向,不同的语言和区域,都会涉及到备选 draw

  • Linux下PHP+Apache的26个必知的安全设置

    PHP是一种开源服务器端脚本语言,应用很广泛.Apache web服务器提供了这种便利:通过HTTP或HTTPS协议,访问文件和内容.配置不当的服务器端脚本语言会带来各种各样的问题.所以,使用php时要小心.以下是Linux下PHP+Apache的26个PHP程序员必知的安全方面的设置 为PHP安全提示而提供的示例环境 文件根目录(DocumentRoot):/var/www/html 默认的Web服务器:Apache(可以使用Lighttpd或Nginx来取代Apache) 默认的PHP配置文

随机推荐