Nginx 的 open_file_cache 相关配置可以缓存静态文件的元信息,在这些静态文件被频繁访问时可以显着提升性能。

被缓存的文件元信息包括:

  • fd,文件被打开一次后,fd保留使用
  • size
  • path
  • last modified time

这里有个配置示例:

open_file_cache max=64 inactive=30d;
open_file_cache_min_uses 8;
open_file_cache_valid 3m;

max=64 表示设置缓存文件的最大数目为 64, 超过此数字后 Nginx 将按照 LRU 原则丢弃冷数据。

inactive=30d 与 open_file_cache_min_uses 8 表示如果在 30 天内某文件被访问的次数低于 8 次,那就将它从缓存中删除。

open_file_cache_valid 3m 表示每 3 分钟检查一次缓存中的文件元信息是否是最新的,如果不是则更新之。

2 为什么只缓存文件元信息而不缓存文件内容?

这个问题的关键是 sendfile(2).

Nginx 在 serve 静态文件的时候用的是 sendfile(2), 当然前提是你配置了 sendfile on, sendfile(2) 直接在 kernel space 内传输数据,对比使用 read(2)/write(2) 省去了两次 kernel space 与 user space 之间的数据拷贝。而同时这些被频繁读取的静态文件的内容会被 OS 缓存到 kernel space。在这样的机制下,我们缓存中有文件的 fd 和 size,直接调用 sendfile(2) 就可以了。

如果要 Nginx 连内容一起缓存,那就需要每次文件变化都要用 read(2) 将数据从 kernel space 复制到 user space,然后放在 user space,每次应答请求的时候再从 user space 复制到 kernel space 然后写入 socket。比起前面的方式,这样的方式毫无优点。

3 在文件缓存更新周期内文件发生变化了会发生什么?

上面提到的配置中,30 天无访问丢弃,每 3 分钟做一次信息有效性监测,我们暂且把 3 分钟叫做缓存更新周期。那在这 3 分钟之内文件发生变化了会怎样呢?

3.1 文件被删除

由于 nginx 还持有原文件的 fd,所以你删除此文件后,文件并不会真正消失, client 还是能通过原路径访问此文件。即便你删除后又新建了一个同名文件,在当前缓存更新周期内能访问到的还是原文件的内容。

3.2 文件内容被修改

文件内容被修改可以分为两种情况:

文件大小不变或增大
由于 nginx 缓存了文件的 size 并且使用 这个缓存中 size 调用 sendfile(2),所以此种情况的后果是:

  • 从文件开始到原 size 字节中的变化可以被 client 看到。
  • 原 size 之后的内容不会被 sendfile(2) 发送,因此 client 看不到此部份内容。
文件大小减小
此种情况下,由于同样原因,nginx 在 HTTP Header 中告诉 client 文件大小还是原来的尺寸,而 sendfile(2) 只能发送真正的文件数据,长度小于 HTTP Header 中设置的大小,所以 client 会等待到自己超时或者 Nginx 在 epoll_wait 超时后关闭连接。

4 如何设置?

  • 如果你的静态文件内容变化频繁并且对时效性要求较高,一般应该把 open_file_cache_valid 设置的小一些,以便及时检测和更新。
  • 如果变化相当不频繁的话,那就可以设置大一点,在变化后用 reload nginx 的方式来强制更新缓存。
  • 对静态文件访问的 error 和 access log 不关心的话,可以关闭已提升效率。

Nginx Open File Cache的更多相关文章

  1. Nginx - Configuration File Syntax

    Configuration Directives The Nginx configuration file can be described as a list of directives organ ...

  2. joomla 出现The file Cache Storage is not supported on this platform;

    错误提示:The file Cache Storage is not supported on this platform:在这个平台上不支持文件缓存存储 出现这样的原因很简单,有两个文件夹不可写,这 ...

  3. nginx返回file not found原因

    nginx返回file not found原因1 确实没有这个文件2 没有权限访问这个网站目录!!!

  4. [svc]tomcat目录结构/虚拟主机/nginx反向代理cache配置

    tomcat目录文件 /usr/local/tomcat/bin/catalina.sh stop sleep 3 /usr/local/tomcat/bin/catalina.sh start to ...

  5. Nginx缓存[proxy cache、memcache]

    nginx自带缓存 nginx自己有单独的进程来对磁盘上的缓存文件进行扫描,在内存中建立缓存索引.并且有管理进程来对缓存进行过期判断,更新等操作 定义:只能在http段中使用 proxy_cache_ ...

  6. nginx报file not found错误

    查看错误日志 [:q2013/10/20 18:41:40 [error] 27151#0: *106117 FastCGI sent in stderr: "Primary script ...

  7. Nginx proxy开启cache缓存

    proxy_temp_path /tmp/proxy_temp_dir; // 设置缓存位置 proxy_cache_path /tmp/proxy_cache_dir levels = : keys ...

  8. [日常] nginx与HTTP cache

    去年的事,随便记记 =============================================================2017年12月11日 记录: nginx缓存:ngx_h ...

  9. nginx报 File not found 错误

    原因可能非常多,但对于刚開始学习的人.大部分应该是/etc/nginx/conf.d/default.conf里面的php解析部分配置不正确. 解决的话就是把root定义.在server下加上,这样r ...

随机推荐

  1. DotNet三层架构

    [项目结构]DAL 数据访问层.BLL 业务逻辑.UI 表现层 Model 数据.Common 常用工具[引用关系]DAL --> Model CommonCommon --> 谁都不引用 ...

  2. Android App的破解技术有哪些?如何防止反编译?

     现在最流行的App破解技术大多是基于一定相关技术的基础:如一定阅读Java代码的能力.有一些Android基础.会使用eclipse的一些Android调试的相关工具以及了解一些smali的语法规范 ...

  3. iOS 获取 UITabViewController 和 UINavigationController 的图标位置

    这些图标是放在 UITabBar 和 UINavigationBar 里的.所以只要遍历它们的 subViews,找到类型是 UIButton 的就可以了. 所有想获取它们的相对位置很容易. 获取到相 ...

  4. Java50道经典习题-程序6 求最大公约数及最小公倍数

    题目:输入两个正整数m和n,求其最大公约数和最小公倍数.分析:用辗转相除法求最大公约数    两个数的最大公约数:设两个数分别为n和m,(n>=m);用定义一个变量i,使用for循环,将i的取值 ...

  5. ClamAV学习【5】—— cli_scanpe函数浏览

    这近2000行的代码,要是没有Source Insight,都不知道怎么看下去.跟着跟着来到了PE文件查杀的地方,发现前面都中规中矩地进行PE属性检查,中间一段开始扫描每个区块,然后和特征库的size ...

  6. GO学习笔记 - 用":="实现短声明变量!

    对于Delphi程序员,":="这个符号再熟悉不过了,表示对变量赋值!在GO语言中,同样表示赋值,但是和Delphi有些不同,不同就在于不需要var变量名称了!GO语言中的&quo ...

  7. Codechef:Fibonacci Number/FN(二次剩余+bsgs)

    题面 传送门 前置芝士 \(bsgs\),\(Cipolla\) 题解 因为题目保证\(p\bmod 10\)是完全平方数,也就是说\(p\bmod 5\)等于\(1\)或\(-1\),即\(5\)是 ...

  8. jquery源码解析:jQuery数据缓存机制详解1

    jQuery中有三种添加数据的方法,$().attr(),$().prop(),$().data().但是前面两种是用来在元素上添加属性值的,只适合少量的数据,比如:title,class,name等 ...

  9. Windows系统下如何在cmd命令窗口中切换Python2.7和Python3.6

    针对在同一系统下我们可能安装多个版本的Python,毕竟Python2.7与Python3.6还是有不同的需求,但是在用Cmd命令窗口是我们可能默认的系统变量环境是其中一个版本,当我们需要在cmd命令 ...

  10. Linux 服务器加入Windows AD

    背景信息: Windows AD Version: Windows Server 2012 R2 zh-cn 计算机全名:hlm12r2n1.hlm.com 域:hlm.com 域控管理员:stone ...