captures in regex location

Vladimir Sopot jd at artdesign.ru
Fri Mar 6 01:22:30 MSK 2009


Хотелось бы, как раз, сохранить текущий порядок: проверка  
существования файла переписывает URI в "старый" формат, "когда  
компьютеры были большими" и адресация на сайте была несколько другая  
(при этом файла вообще может и не существовать). А тем, которые EN,  
уже однозначно подсовывается новый формат и посылается вдаль, туда,  
где о старом варианте ничего не знают.

А в чем вообще прелесть "новых технологий" и location ~* upic\.jpg$ {}  
(ну и location ~* "^(................)$" {})?


On Mar 6, 2009, at 12:32 AM, Igor Sysoev wrote:

> On Fri, Mar 06, 2009 at 12:15:28AM +0300, Vladimir Sopot wrote:
>
>>
>> On Mar 5, 2009, at 11:37 PM, Igor Sysoev wrote:
>>
>>> On Thu, Mar 05, 2009 at 11:30:14PM +0300, Vladimir Sopot wrote:
>>>
>>>> А-ха!
>>>>
>>>> В моем if-е подразумевался break, чтобы больше условий (типа  
>>>> проверки
>>>> географии и пр.) в этом server-е не выполнялось. Что должно быть
>>>> внутри нового location-а для того же функционала?
>>>
>>> Как выглядят if'ы ?
>>
>> Наверняка, что-то не так с last-break, но работает :)
>>
>>       if ($request_uri ~* upic.jpg) {
>>           break;
>>           }
>>
>> 	if (!-f $request_filename) {
>>            rewrite "^(................)$"   http://$2$3$4      last;
>>            return 404;
>>            }
>>
>>        if ($country = EN) {
>>            rewrite (.*)        http://somewhere.com$1 break;
>>            }
>
> location ~* upic\.jpg$ {
>    ...
> }
>
> location ~* "^(................)$" {
>
>    if ($country = EN) {
>        rewrite  ^        http://somewhere.com$request_uri?;
>    }
>
>    error_page  404  http://$2$3$4;
> }
>
> Только в этом случае "if ($country = EN)" будет выполняться до  
> проверки
> существования файла.
>
> А ещё можно сделать так:
>
> server_name ~^([bos])(\d)p\.site;
>
>    set   $root    /wwwroot/site/$2/$1/;
>    root  $root;
> }
>
> Но
>
>     if ($request_uri ~* upic.jpg) {
>           break;
>     }
>
> нужно однозначно менять на
>
>     location ~* upic\.jpg$ {
>         ...
>     }
>
>>>> On Mar 5, 2009, at 10:43 PM, Igor Sysoev wrote:
>>>>
>>>>> On Thu, Mar 05, 2009 at 10:34:51PM +0300, Vladimir Sopot wrote:
>>>>>
>>>>>> Mot*^&@W$ ;".%($ :^?:(;!
>>>>>>
>>>>>> Спасибо, действительно, надо обращать больше внимания на имена
>>>>>> файлов
>>>>>> и места сохранения аттачей.
>>>>>>
>>>>>> Но всплыл другой непонятный "фич" -
>>>>>>
>>>>>> server {
>>>>>>    server_name ~^([bos])(\d)p\.site;
>>>>>>    root    /wwwroot/site/$2/$1/;
>>>>>>    }
>>>>>>
>>>>>> работает отлично. Но как только внутри, после root ... появляется
>>>>>>
>>>>>> 	if ($request_uri ~* upic.jpg) {
>>>>>> 		# не важно что, хотя бы даже пустота
>>>>>> 		}
>>>>>>
>>>>>> всё снова ломается :(
>>>>>
>>>>> regex в if/rewrite меняют captures, даже если они не сработали.
>>>>> Несовпавший location regex не трогает captures. Поэтому нужно
>>>>> переходить
>>>>> на прогрессивные технологии:
>>>>>
>>>>> location ~* upic\.jpg {
>>>>> ...
>>>>> }
>>>>>
>>>>>> P.S. спасибо за ненужную "|" :)
>>>>>>
>>>>>> On Mar 5, 2009, at 6:56 PM, Igor Sysoev wrote:
>>>>>>
>>>>>>> On Thu, Mar 05, 2009 at 06:46:03PM +0300, Vladimir Sopot wrote:
>>>>>>>
>>>>>>>> В эту сторону я уже думал и на такой location - ругается, да.
>>>>>>>>
>>>>>>>> Но патч вроде ложится -
>>>>>>>>
>>>>>>>> nginx-0.7.39/src/http # patch -p2 <patch.location_captures
>>>>>>>
>>>>>>> Это первый патч, нужен patch.location_captures1
>>>>>>>
>>>>>>>> patching file ngx_http_core_module.c
>>>>>>>> patching file ngx_http_request.h
>>>>>>>> patching file ngx_http_script.c
>>>>>>>> patching file ngx_http_script.h
>>>>>>>> patching file modules/ngx_http_rewrite_module.c
>>>>>>>>
>>>>>>>> и objs/nginx получается другого размера, если без патча.
>>>>>>>>
>>>>>>>> On Mar 5, 2009, at 5:30 PM, Igor Sysoev wrote:
>>>>>>>>
>>>>>>>>> On Thu, Mar 05, 2009 at 05:22:43PM +0300, Vladimir Sopot  
>>>>>>>>> wrote:
>>>>>>>>>
>>>>>>>>>> Увы,
>>>>>>>>>>
>>>>>>>>>> 2009/03/05 16:54:16 [error] 18720#0: *5440 open() "/wwwroot/
>>>>>>>>>> site///e/
>>>>>>>>>> ea/0/12720.jpg" failed (2: No such file or directory),
>>>>>>>>>> client: 94.188.35.148, server: ~^(s)(\d)\.site, request:
>>>>>>>>>> "GET /e/
>>>>>>>>>> ea/
>>>>>>>>>> 0/12720.jpg HTTP/1.1", host: "s0.site", referrer:
>>>>>>>>>> "http://site/ea/12720.html"
>>>>>>>>>>
>>>>>>>>>> Тоесть сервер точно матчится, но вот $1-2 не  
>>>>>>>>>> устанавливаются :(
>>>>>>>>>>
>>>>>>>>>> Куда бы еще копнуть? Уж больно хочется и конфиг порезать и на
>>>>>>>>>> регекспах сэкономить :)
>>>>>>>>>
>>>>>>>>> А патч точно приложен ?
>>>>>>>>> Что показывает nginx, если в конфиг добавить такое:
>>>>>>>>>
>>>>>>>>> location ~ \.TXT$ {
>>>>>>>>> alias  /wwwroot/;
>>>>>>>>> }
>>>>>>>>>
>>>>>>>>> ?
>>>>>>>>>
>>>>>>>>>> # uname -a
>>>>>>>>>> Linux site 2.6.27.7-9-default #1 SMP 2008-12-04 18:10:04  
>>>>>>>>>> +0100
>>>>>>>>>> x86_64
>>>>>>>>>> x86_64 x86_64 GNU/Linux
>>>>>>>>>>
>>>>>>>>>> # ./configure \
>>>>>>>>>> --with-http_stub_status_module \
>>>>>>>>>> --without-mail_pop3_module \
>>>>>>>>>> --without-mail_imap_module \
>>>>>>>>>> --without-mail_smtp_module \
>>>>>>>>>> --without-http_access_module \
>>>>>>>>>> --without-http_autoindex_module \
>>>>>>>>>> --without-http_browser_module \
>>>>>>>>>> --without-http_charset_module \
>>>>>>>>>> --without-http_limit_zone_module \
>>>>>>>>>> --without-http_map_module \
>>>>>>>>>> --without-http_memcached_module \
>>>>>>>>>> --without-http_referer_module \
>>>>>>>>>> --without-http_ssi_module \
>>>>>>>>>> --without-http_userid_module \
>>>>>>>>>> --without-http_proxy_module \
>>>>>>>>>> --without-http_proxy_module
>>>>>>>>>> ...........
>>>>>>>>>> checking for PCRE library ... found
>>>>>>>>>> ...........
>>>>>>>>>> Configuration summary
>>>>>>>>>> + using system PCRE library
>>>>>>>>>> ...........
>>>>>>>>>> # pcre-config --version
>>>>>>>>>> 7.8
>>>>>>>>>>
>>>>>>>>>> On Mar 5, 2009, at 4:14 PM, Igor Sysoev wrote:
>>>>>>>>>>
>>>>>>>>>>> On Thu, Mar 05, 2009 at 03:46:55PM +0300, Vladimir Sopot
>>>>>>>>>>> wrote:
>>>>>>>>>>>
>>>>>>>>>>>> Помимо описанного сервера есть еще секции
>>>>>>>>>>>>
>>>>>>>>>>>> server {
>>>>>>>>>>>> server_name ~^([b|o])(\d)\.site;
>>>>>>>>>>>> 	.......
>>>>>>>>>>>> 	}
>>>>>>>>>>>>
>>>>>>>>>>>> server {
>>>>>>>>>>>> listen *:80 default bind sndbuf=64k;
>>>>>>>>>>>> server_name site
>>>>>>>>>>>> 	..........
>>>>>>>>>>>> 	}
>>>>>>>>>>>>
>>>>>>>>>>>> и добавление пустого сервера не исправило ситуацию.
>>>>>>>>>>>
>>>>>>>>>>> У меня для
>>>>>>>>>>>
>>>>>>>>>>> server {
>>>>>>>>>>> listen  8000;
>>>>>>>>>>> server_name ~^([b|o])(\d)z\.site;
>>>>>>>>>>>
>>>>>>>>>>> root    /wwwroot/site/$1/$2/;
>>>>>>>>>>> }
>>>>>>>>>>>
>>>>>>>>>>> в логах такая ошибка:
>>>>>>>>>>>
>>>>>>>>>>> [error] 58504#0: *1 open() "/wwwroot/site/b/1/dir/ 
>>>>>>>>>>> index.html"
>>>>>>>>>>> failed
>>>>>>>>>>> (2: No such file or directory), client: 127.0.0.1, server:
>>>>>>>>>>> ~^([b|
>>>>>>>>>>> o])
>>>>>>>>>>> (\d)z\.site, request: "GET /dir/index.html HTTP/1.0", host:
>>>>>>>>>>> "b1z.site"
>>>>>>>>>>>
>>>>>>>>>>> То есть, путь "/wwwroot/site/b/1/dir/index.html" формиурется
>>>>>>>>>>> правильно.
>>>>>>>>>>>
>>>>>>>>>>> Кстати, "|" в "([b|o])" - лишняя.
>>>>>>>>>>>
>>>>>>>>>>>> On Mar 5, 2009, at 2:43 PM, Igor Sysoev wrote:
>>>>>>>>>>>>
>>>>>>>>>>>>> On Thu, Mar 05, 2009 at 01:57:49PM +0300, Vladimir Sopot
>>>>>>>>>>>>> wrote:
>>>>>>>>>>>>>
>>>>>>>>>>>>>> Спасибо, но что-то оно не того
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> server {
>>>>>>>>>>>>>> server_name ~^([b|o])(\d)z\.site;
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> #        if ($host ~* (.)(\d)) {
>>>>>>>>>>>>>> set $store_type $1;
>>>>>>>>>>>>>> set $store_id $2;
>>>>>>>>>>>>>> #            }
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> root    /wwwroot/site/$store_id/$store_type/;
>>>>>>>>>>>>>> }
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> В таком виде не работает (404), если убрать комментарии -
>>>>>>>>>>>>>> все
>>>>>>>>>>>>>> становится на свои места. Забрать root внутрь location /
>>>>>>>>>>>>>> { }
>>>>>>>>>>>>>> тоже
>>>>>>>>>>>>>> ничего не дает. root  /wwwroot/site/$2/$1/ тоже не  
>>>>>>>>>>>>>> работает
>>>>>>>>>>>>>
>>>>>>>>>>>>> Скорее всего, regex вообще не исполняется, потому что  
>>>>>>>>>>>>> сервер
>>>>>>>>>>>>> один -
>>>>>>>>>>>>> проверять нечего. Нужно добавить пустой сервер, чтобы  
>>>>>>>>>>>>> nginx
>>>>>>>>>>>>> начал
>>>>>>>>>>>>> проверять
>>>>>>>>>>>>> server_name:
>>>>>>>>>>>>>
>>>>>>>>>>>>> server { server_name _; }
>>>>>>>>>>>>>
>>>>>>>>>>>>>> On Mar 5, 2009, at 1:17 PM, Igor Sysoev wrote:
>>>>>>>>>>>>>>
>>>>>>>>>>>>>>> On Thu, Mar 05, 2009 at 12:14:55PM +0200, Andrew  
>>>>>>>>>>>>>>> Sitnikov
>>>>>>>>>>>>>>> wrote:
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>>>>> А можно такое же ещё и для server_name?
>>>>>>>>>>>>>>>> IS> Новый патч с поддержкой server_name.
>>>>>>>>>>>>>>>> можно пример ?
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>> Наверное, как-то так:
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>> server {
>>>>>>>>>>>>>>> listen  8000;
>>>>>>>>>>>>>>> server_name  ~^(?:www\.)?(.+)$;
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>> location / {
>>>>>>>>>>>>>>> root   /path/to/$1;
>>>>>>>>>>>>>>> }
>>>>>>>>>>>>>>> }
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>>
>>>>>>>>>>>>>>> -- 
>>>>>>>>>>>>>>> Игорь Сысоев
>>>>>>>>>>>>>>> http://sysoev.ru
>>>>>>
>>>>>
>>>>> -- 
>>>>> Игорь Сысоев
>>>>> http://sysoev.ru
>>>>>
>>>>>
>>>>
>>>
>>> -- 
>>> Игорь Сысоев
>>> http://sysoev.ru
>>>
>>>
>>
>
> -- 
> Игорь Сысоев
> http://sysoev.ru
>
>






More information about the nginx-ru mailing list