Назад | Перейти на главную страницу

AWS, Nginx и Django: сервер по умолчанию для предотвращения фиктивных строк хоста

У нас есть установка сервера с AWS, которая должна удовлетворять следующим требованиям:

1: входящие запросы, исходящие от балансировщика нагрузки (в частности, проверки работоспособности и проверки задержки), должны быть разрешены для достижения веб-серверов.

2: Действительные запросы, содержащие правильные Host строкам должно быть разрешено достигать веб-сервера.

3: Все остальные запросы должны быть отклонены с нестандартным отклонением Nginx «444», что означает, что они будут проигнорированы.

Кроме того, на нашем веб-сайте есть несколько поддоменов, на каждом из которых выполняется один и тот же код для разных клиентов. Мы настроили Nginx для перенаправления всего http-трафика с этих поддоменов на https. Я назову эти субдомены «a.example.com», «b.example.com» и «c.example.com».

Мы заметили в наших журналах, что наш код Django возвращает много 500 ошибок из-за фальшивых строк Host, которые проходят мимо Nginx. Строка хоста, которую мы видим для каждого из этих запросов, - «* .example.com», которая соответствует любому из наших поддоменов и, следовательно, соответствует коду Django. Поскольку эта строка хоста нераспознана, Django возвращает ошибку 500.

Ниже приведен пример нашего файла, доступного для сайтов Nginx:

# Repeat this for each subdomain:
server {
    server_name a.example.com;
    listen 80;
    return 301 https://a.example.com$request_uri;
}

server {
    server_name a.example.com;
    listen 443;
    location / {
        set $my_host $host;
        if ($host ~ "\d+\.\d+\.\d+\.\d+") {
            set $my_host "elb.example.com";
        }
    }
}

Мы попытались отловить эту неверную строку хоста с помощью следующего определения сервера «черная дыра» в Nginx:

server {
    server_name *.example.com;
    listen 80 default_server;
    listen 443 default_server;
    return 444
}

Однако строка хоста "* .example.com" соответствует одному из определений сервера https и перенаправляется в код Django.

Что мне не хватает?

В вашей попытке конфигурации все, что вам нужно было изменить, это server_name переменная к чему-то, что не соответствует никакому другому блоку сервера, но будет действительным, например localhost, и это должен быть сервер, к которому запросы возвращаются, если они не соответствуют никакому другому имени хоста (поскольку вы отметили его как default_server - использование подстановочного имени хоста только усложняет задачу).

server {
    server_name localhost;
    listen 80 default_server;
    listen 443 default_server;
    return 444
}