nginx 上游代理的后备
Posted
技术标签:
【中文标题】nginx 上游代理的后备【英文标题】:fallback for an nginx upstream proxy 【发布时间】:2012-11-03 01:04:07 【问题描述】:我在图像服务器集群前面有一个 nginx 实例:
upstream img-farm-1
server 10.0.1.1;
server 10.0.1.2;
server 10.0.1.3;
server 10.0.1.4;
# etc
location ~ ^/static:
rewrite /static:(.*) /$1 break;
proxy_pass http://img-farm-1;
limit_except GET
allow all;
这个集群正在被一个即将上线的新集群所取代,有一段时间,我想从旧集群提供图像,但如果图像是新的或已从新集群迁移,则回退到新集群旧的到新的。迁移完成后,我可以回到原来的设置。
所以我认为我可以做到
upstream img-farm-2
server 10.0.2.1;
server 10.0.2.2;
server 10.0.2.3;
server 10.0.2.4;
server 10.0.2.5;
# etc
location ~ ^/static:
access_log /var/log/nginx/static.access.log;
rewrite /static:(.*) /$1 break;
proxy_pass http://img-farm-1;
error_page 404 = @fallback-2;
location @fallback-2
access_log /var/log/nginx/static-2.access.log;
proxy_pass http://img-farm-2;
但这不起作用。我在 static.access.log
中看到 404,但 error_page 404
指令没有被执行,因为没有任何内容被写入 static-2.access.log
。
我很确定我不能使用try_files
,因为,呃,没有任何本地文件,一切都被代理了。
以前有人做过这样的事情吗?我错过了什么?
【问题讨论】:
【参考方案1】:这应该可以工作
upstream img-farm-2
server 10.0.2.1;
server 10.0.2.2;
server 10.0.2.3;
server 10.0.2.4;
server 10.0.2.5;
# etc
location ~ ^/static:
access_log /var/log/nginx/static.access.log;
rewrite /static:(.*) /$1 break;
proxy_pass http://img-farm-1;
proxy_intercept_errors on;
error_page 404 = @fallback-2;
location @fallback-2
access_log /var/log/nginx/static-2.access.log;
proxy_pass http://img-farm-2;
【讨论】:
【参考方案2】:我有类似的情况,但如果我的第一台服务器停机(状态)502,我想退回到另一台服务器。我让它工作(nginx/1.17.8
)而不需要 proxy_intercept_errors`。
此外,对于任何使用带有 URI 的 proxy_pass
(本例中为 /
)的人,您需要使用稍微不同的配置,否则您会收到错误消息(见下文)。
location /texts/
proxy_pass http://127.0.0.1:8084/;
proxy_set_header X-Forwarded-For $remote_addr;
error_page 502 = @fallback;
location @fallback
# This will pass failed requests to /texts/foo above to
# http://someotherserver:8080/texts/foo
proxy_pass http://someotherserver:8080$request_uri;
无论出于何种原因,Nginx 都不允许在此处使用斜线:
location @fallback
proxy_pass http://someotherserver:8080/;
并且会抛出:
nginx:[emerg]“proxy_pass”不能在正则表达式给出的位置、命名位置、“if”语句或“limit_except”块中包含URI部分
不幸的是,没有/
,您不能(AFAIK)proxy_pass 子目录。没有带有$1
的正则表达式也不起作用,因为它不支持空格。
【讨论】:
【参考方案3】:我傻了。所需要的只是proxy_intercept_errors on;
在第一个位置
【讨论】:
干得好!正是我需要的。以上是关于nginx 上游代理的后备的主要内容,如果未能解决你的问题,请参考以下文章
TCP 代理到 postgres 数据库作为 nginx 中的上游服务器