Tentando usar o Nginx try_files para emular o Apache MultiViews

2

Eu quero uma solicitação para http://example.com/foobar para retornar http://example.com/foobar.jpg . (Ou .gif, .html, qualquer que seja)

Isso é trivial para fazer com o Apache MultiViews, e parece que seria igualmente fácil no Nginx. Esta questão parece indicar que seria fácil, como try_files $uri $uri/ index.php; na localização bloco, mas isso não funciona.

try_files $uri $uri/ =404; não funciona, nem try_files $uri =404; ou try_files $uri.* =404; Mover entre o bloco location / { e o regexp que corresponde às imagens não tem efeito.

Crucialmente, try_files $uri.jpg =404; funciona , mas apenas para arquivos .jpg, e isso gera um erro de configuração se eu usar mais de uma regra try_files em um bloco de localização!

O bloco atual server { :

server {
        listen   80;
        server_name     example.org www.example.org;
        access_log  /var/log/nginx/vhosts.access.log;
        root   /srv/www/vhosts/example;
        location / {
                root   /srv/www/vhosts/example;
        }

        location ~* \.(?:ico|css|js|gif|jpe?g|es|png)$ {
                expires max;
                add_header Cache-Control public;
                try_files $uri =404;
        }
}

A versão do Nginx é 1.1.14.

    
por Samuel Bierwagen 07.04.2012 / 01:05

1 resposta

5

Você pode emular os MultiViews do Apache, passando os vários nomes de arquivos para tentar try_files .

A diretiva try_files do Nginx faz exatamente o que o nome sugere - tenta arquivos na ordem em que são especificados, e se não for encontrado, passará para o próximo arquivo. Normalmente, a última entrada é um fallback com garantia de funcionamento - um bloco de localização nomeado ou uma página de erro.

Os parâmetros comumente encontrados de try_files : $uri e $uri/ são realmente os caminhos passados para nginx - com e sem a barra final.

Então, se você for para example.com/path/to/myfile

$uri = /path/to/myfile
$uri/ = /path/to/myfile/

Com a diretiva try_files $uri $uri/ , o nginx tentará exatamente o que é passado ( $uri ) - e se esse arquivo existir, será veiculado, caso contrário, tentará encontrar um diretório correspondente ( $uri/ ) e servirá isso ( usando o índice que você especificou).

Como os arquivos que você está tentando veicular não correspondem realmente ao caminho em $uri , é necessário anexar a extensão a $uri para que funcione:

$uri.jpg corresponderá (do exemplo acima) myfile.jpg - daí porque somente os JPEGs funcionaram quando você o usou.

Como você pode especificar vários arquivos para experimentar em try_files , ter mais de uma diretiva try_files não faz sentido, e é por isso que não é permitido.

Em sua forma mais simples, portanto, apenas liste os arquivos desejados, na ordem em que você deseja testá-los (por exemplo,

try_files $uri.jpg $uri.gif $uri.png $uri.css $uri.js $uri/ =404

O segundo bloco de localização é interessante neste caso. Normalmente, o nginx processa apenas um bloco de localização - aquele que corresponde melhor. No entanto, no caso de rewrite ... last , o processamento será reiniciado e todos os blocos de localização disponíveis serão verificados. Isso é essencialmente o que try_files equivale a - verifique se existe e rewrite ... last , a diferença principal é a ausência dos argumentos aprovados, que são removidos por try_files , a menos que sejam explicitamente adicionados (por exemplo, com $uri?$args ).

    
por 07.04.2012 / 04:16

Tags