allow/deny and return

Maxim Dounin mdounin at mdounin.ru
Tue Oct 15 16:57:49 UTC 2013


Hello!

On Tue, Oct 15, 2013 at 07:14:22PM +0300, Gena Makhomed wrote:

> On 15.10.2013 16:45, Maxim Dounin wrote:
> 
> >>>>В такой конфигурации:
> >>>>
> >>>>location /closed {
> >>>>   allow 10.1.1.1;
> >>>>   deny all;
> >>>>   return 200 "secret\n";
> >>>>}
> >>>>
> >>>>allow/deny ни на что не влияют.
> ...
> >>я прочитал http://nginx.org/en/docs/http/ngx_http_rewrite_module.html
> >>но так и не смог понять, почему allow и deny тут не будут работать.
> 
> >Потому что директивы модуля rewrite - это фактически часть выбора
> >конфигурации.  И именно от выбранной конфигурации зависит, что
> >можно, а что - нельзя.
> 
> вот дословно что сейчас написано в документации:
> 
> The ngx_http_rewrite_module module is used to change URIs using regular
> expressions, return redirects, and conditionally select configurations.
> 
> "conditionally select configurations" - это только evil директива "if".
> остальные директивы, кроме rewrite, являются unconditional. разве нет?

Все директивы модуля rewrite - это в той или иной степени выбор 
конфигурации, даже если они unconditional.  E.g., банальный set:

    set $file ".htpasswd";
    auth_basic_user_file /path/to/$file;

так или иначе определяет конфигурацию, которая будет в дальнейшем 
использоваться для обработки запроса.  Выполнять сначала 
access-проверки, и только потом директивы модуля rewrite - ни разу 
не вариант.

Не говоря уже о том, что директивы модуля rewrite - нельзя 
рассматривать отдельно друг от друга.  Это инструкции, которые 
компилируются и выполняются вместе, о чём подробно рассказано в 
той самой документации модуля rewrite, со ссылки на которую я и 
начал.

> >>это все похоже на BUG, потому что пользователи обычно подразумевают,
> >>что сначала работает access module и только потом - rewrite_module.
> >>
> >>по крайней мере, в UNIX и даже в WINDOWS все работает именно так:
> >>если доступа к файлу нет, никаких операций с ним сделать нельзя.
> 
> >В Антоном конфиге нет файла.  Есть инструкция "при выборе
> >конфигурации для обработки запросов вернуть ответ с кодом 200".
> 
> файла нет. но есть location /closed и есть директивы задания доступа
> кому allow, а кому deny. то что return срабатывает раньше deny - это
> будет совершенно неожиданно для более чем 99% пользователей nginx...

С якобы багом разобрались - отлично.  Возвращаемся к исходному 
разговору - если есть идеи, как _хорошо_ объяснить пользователям, 
почему так - you are welcome. 

> >(И да, я таки считаю, что возможность задавать тело ответа была
> >добавлена в диркетиву return зря, не её это работа.  Надо было
> >сделать отдельный модуль a la empty gif, подобных вопросов было бы
> >меньше.  Но таки этот фарш уже поздно проворачивать назад.)
> 
> почему поздно? и сейчас можно сделать отдельный модуль return, который
> будет срабатывать как content handler возвращая код статуса и урл/текст
> 
> return code [text];
> return code URL;
> return URL;
> 
> а из модуля rewrite директиву return тогда можно будет вообще убрать.
> в этом случае - вообще ничего не изменится, кроме того, что директивы
> из access module отработают раньше, чем return, как это и должно быть.

Потому что семантика директивы return - в общем случае другая.  В 
частности, сломается вот такой вполне типичный конфиг:

    if ($evil) {
        return 403;
    }

    rewrite ^/something/(.*) /something/else/$1;

Аналогичный конфиг, кстати, рассматривается в подробностях тут:

http://nginx.org/en/docs/http/ngx_http_rewrite_module.html#internals

-- 
Maxim Dounin
http://nginx.org/en/donation.html



Подробная информация о списке рассылки nginx-ru