我正在对 nginx/1.14.1 服务器进行配置重构,该服务器充当 PHP-FPM 的反向代理。
现在配置的方式,我可以做到
# in a server {} section at a vhost there's
# set $base_domain domain.com;
# and then it includes another config file which has something like this:
if ($php_logs_path = '') {
set $php_logs_path /a/b/$base_domain/logs/$server_name.php_www_errors.log;
}
fastcgi_parma PHP_ADMIN_VALUE "error_log=$php_logs_path"
这工作正常并且日志文件出现在正确的路径:
/a/b/domain.com/logs/some-sub-domain.domain.com.php_www_errors.log
但是,我不太喜欢现在需要访问上百个虚拟主机来设置变量$base_domain
。我访问了nginx 文档,但我找不到只提供domain
没有子域的段的变量。
有没有一种使用自定义变量的简单方法可以做到这一点?
答案1
那么使用一些全局map
指令怎么样
map $server_name $base_domain {
~([^.]*)\.([^.]*)$ $1.$2;
}
map
块是在http
上下文中定义的,因此您可以在全局 nginx 配置中将其与 vhost 分开定义。
更新
正如 OP 指出的那样,此解决方案不适用于.co.uk
域名。我在写这个答案时想到了其他例子 - 例如,澳大利亚.com.au
、.net.au
乌克兰.com.ua
和.in.ua
许多其他国家。好吧,因为国家顶级域名总是两个字母,我们可以假设任何.xx.xx
和域名后缀很可能是某个国家/地区的双组分 TLD。由于从头到尾检查了块表达式.xxx.xx
列表,因此可以使用以下块捕获这些域:map
map
map $server_name $base_domain {
"~([^.]*)\.([a-z]{2,3})\.([a-z]{2})$" $1.$2.$3;
~([^.]*)\.([^.]*)$ $1.$2;
}
更新 2
刚刚发现,这些正则表达式中不需要多个捕获组:
map $server_name $base_domain {
"~([^.]*\.[a-z]{2,3}\.[a-z]{2})$" $1;
~([^.]*\.[^.]*)$ $1;
}
答案2
你为什么不直接重用$server_name
?此变量设置为第一的 server_name
在块中定义server
。只需确保第一个定义的名称是您想要的(并且它可能已经是了)。