Nginx“默认”服务器?

Rob*_*son 39 nginx

我有一个带有许多启用的服务器块的 Nginx。每个服务器响应 1 个规范域,并且可以将 1 个或多个转发到该规范 URL。我至少有一台服务器(还没有检查所有服务器),如果我输入一个指向这个框的不存在的域,Nginx 会显示一个它选择的站点(总是同一个站点,但不是一个我在后面)。

我已经浏览了我总是登陆的站点的配置文件,但没有看到任何明显的东西可以将其识别为任何类型的默认站点,但它就在那里,当我胖手指一个 URL 时总是显示出来。

关于我应该寻找什么来追踪这个问题的任何想法?

Fle*_*der 47

为什么 nginx 会这样做?

这样做的原因是简单的。非常旧或损坏的客户端不会Host在其请求中发送HTTP 标头字段,并且如果您使用基于名称的服务器块(Apache 术语中基于名称的虚拟主机),nginx 无法确定您配置的哪个服务器是客户端所指的. 对于支持此基于名称的系统的任何其他 Web 服务器,同样的问题也是如此。如果您为每个域使用基于 IP 的系统(这也意味着您有多个网络接口),则不会出现此问题。

有关此主题的更多信息?nginx 如何处理请求


哪个是第一个?

如果没有default在任何listen指令上设置标志,nginx 将选择最先出现的服务器:

server {
  server_name server1.com;
}

server {
  server_name server2.com;
}
Run Code Online (Sandbox Code Playgroud)

server1.com 将是默认的。

如果您自动包含来自sites-enabled(默认配置)的符号链接,则目录中第一个出现的文件将是您的第一个服务器。


我能做些什么来防止这种情况?

好问题,你应该阻止它。没有理由支持这些旧客户端,也绝对没有理由支持损坏的客户端。通过创建默认捕获所有服务器配置,可以轻松解决该问题。以下示例来自我的一个项目,针对 nginx 的当前开发版本(1.5.2 - 但也适用于旧版本):

# /etc/nginx/sites-enabled/_.conf

# Default server for clients who do not send correct Host header.
# The underline in the file name makes sure that this file comes first in the dir.
server {
  server_name _;
  listen *:80 default_server deferred;
  return 444;
}
Run Code Online (Sandbox Code Playgroud)

配置被修剪,更多nginx配置的东西

  • 设置时请注意缓存的 301 重定向(在浏览器中)。我在 Chrome 中吓坏了,不明白为什么我的“return 444;”不起作用,直到我在隐身窗口中打开开发工具并意识到一切正常。 (5认同)

Sha*_*den 38

添加default_server到您要作为默认值的listen指令中server

  • 嗯,就是这样。我真的不想要一个默认值,但我似乎有一个。如果我输入的内容与某些内容不完全匹配,我宁愿让 nginx 抛出它抛出的任何错误。 (2认同)
  • 让我换个方式问这个问题。当调用不匹配的域时,是什么让 Nginx 加载站点 X?为什么是站点 X 而不是站点 Y?为什么它不只是抛出错误? (2认同)