如何让nginx try_files及时获取html资源

Amazon Linux EC2实例上使用nginx 1.8.1。 用作反向代理来支持在不同实例上运行Apache https。 一切工作正常,除了这个问题。

我想从nginx提供一个静态页面,以防止我想closuresApache服务器实例。 所以我这样做了:

  location / { try_files /site-down.html $uri @backend; } 

所以在我closures后端服务器之前,我在nginx服务器的根目录下创build了一个符号链接到一个静态html文件,如下所示:

 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>example.com</title> <style type="text/css"> body { background-image:url('/images/back-soon-background.jpg'); font-family: arial,verdana,sans-serif; text-align: center; } #msg { background-image: url('/images/back-soon-oval.png'); background-repeat: no-repeat; width: 600px; padding-top: 140px; padding-left: 50px; padding-right: 50px; padding-bottom: 150px; } </style> </head> <body> <div id="msg"> <h1>Sorry, the site is currently unavailable.</h1> <h2>We expect to be back within 2 hours.</h2> </div> </body> </html> 

问题是,当我这样做的时候,页面会立即显示为div的文本内容,而没有<head>部分中<style>指定的图像。 使用Chrome开发者工具“networking”标签,我可以看到图片url的请求,并获取200个状态代码。 但是,如果我点击这些请求,没有可用的预览,并且体长太短。 重新加载页面并不能马上帮忙。 但是,如果我让它坐在那里一会儿,最终出现与图像正确的输出。 如果我直接将浏览器指向/site-down.html ,页面将立即正确显示。

Chrome 52.0.2743.116 mFirefox 48.0.2行为方式都是一样的。 我是nginx新手,但是我无法想象为什么try_files中的第一个uri应该和文件存在的情况下直接运行的uri有所不同。 我错过了什么?

@迈克尔 – 汉普顿的评论为我提出了问题的答案。 我大概在6个星期前提出,如果他把这些信息作为答案发布,我会将其标记为接受。 但是既然他不这样做,我在这里构build一个答案来接受。 似乎遗憾的是离开这个没有答案。

我问的问题的答案只是我指定的nginxconfiguration强制所有请求首先尝试提供静态site-down.html页面。 而且由于图像被指定为同一站点的URL,所以这些图像请求也被/ location指令处理,所以try_files被应用并更改它们以服务site-down.html页面。

我不知道为什么这些图像在重新加载和等待之后最终显示出来,有些东西一定是超时的。

解决这个问题的最直接的方法就是将背景图像url更改为data url,并将图像内容本身embedded到base64string中。 通过这样做, site-down.html页面不会生成任何额外的资源请求,而且它的工作方式与我原先site-down.html一样。

但是他也指出,当我工作的时候,即使这个网站基本上是停下来的,也会给出200个状态代码。 我解释说,该网站是专门为交互式用户,而不是服务器,这是短期故意中断,而不是像后端服务器崩溃的错误。 所以我不认为这是一个大问题。 但事实是,给出一个有意义的状态码总是最好的。 所以我认为对我来说“正确的”解决scheme有两个不同的“可用的”nginxconfiguration文件,其中一个简单地使用site-down.html作为自定义错误页面对503响应进行硬编码。 然后,不要在根目录下创build/删除一个名为site-down.html的符号链接,而是依靠try_files来提供所需的行为,我应该只更改启用网站的目录中的符号链接,以select正确的configuration并执行sudo service nginx reload以平滑切换行为。

使用try_files的优点是,行为立即切换一个命令,缺点是状态码表明该网站工作正常,即使它不是。 切换configuration文件的好处是它提供了有意义的状态,而缺点是重新加载nginx的额外步骤是可以被遗忘的。 但是,最终交换机将通过脚本完成,脚本不会忘记重新加载configuration。

try_files按您指定的顺序尝试文件。 改变顺序是这样的

 try_files $uri @backend /site-down.html; 

我假设自页面正在服务,现在你有一切设置好。 如果您需要进一步的帮助,请给出一个答案并对答案发表评论。 确保包含日志(如果适用)。

使用error_page指令来处理您的后端closures时的情况。 这也将让你返回一个适当的HTTP响应代码。

例如:

 server { try_files $uri @backend; error_page 500 502 503 504 =503 /site-down.html; #.... 

在这种情况下,我们首先提供静态文件,然后转到后端。 如果后端返回列出的错误之一,那么nginx将提供一个HTTP 503响应/site-down.html

这种方法的好处是您不必手动添加或删除site-down.html文件。 你把它放在原处,如果后端实际上是 down的话,nginx会自动提供它。