Nginx client_max_body_size por bloco de localização (com padrão php frontcontroller)

Nginx client_max_body_size por bloco de localização (com padrão php frontcontroller)

Estou procurando uma solução paraeste problema. Entendo o motivo pelo qual a configuração dessa pergunta não funciona, mas tento chegar a uma solução onde possa fazê-la funcionar.

A ideia é permitir uploads de arquivos grandes apenas em determinados URLs. Posso usar um locationbloco para isso, mas o problema é: tenho um padrão frontcontroller em php:

location ~ \.php {
    # ...
    fastcgi_pass unix:/tmp/php5-fpm.sock;
}

Minha configuração total se parece com:

# ...

http {
    # ...

    client_max_body_size 512K;

    server {
        server_name example.com;
        root        /var/www/example.com/public;

        location / { 
            try_files $uri /index.php?$query_string;
        }

        location /admin/upload {
            client_max_body_size 256M;
        }

        location ~ \.php {
            # ...

            fastcgi_pass unix:/tmp/php5-fpm.sock;
        }
    }
}

Pelo que entendi, apenas um bloco de localização será aplicado. Portanto, se eu tiver um tamanho de solicitação padrão de 512K, 256M nunca será aplicado, pois todas as solicitações são correspondidas por meio do padrão frontcontroller ~ \.php.

Estou certo neste caso e, em caso afirmativo, o que pode ser configurado para que os visitantes não possam fazer upload de nada, exceto quando fizerem upload para admin/upload?

Responder1

Se /admin/uploado caminho for virtual, é possível fazê-lo funcionar da seguinte forma:

location / {
    try_files $uri /index.php?$args;
}

location /admin/upload {
    client_max_body_size 256M;

    include inc/php.conf;
    rewrite ^(.*)$ /index.php?$args break;
}

location ~ \.php$ {
    include inc/php.conf;
}

Não é o mais bonito também, mas funciona.

Responder2

Definir dois locais php?

location ~ ^/admin/upload/.+\.php$
{
    client_max_body_size 256M;
    include /etc/nginx/conf.d/php-fpm.conf;
}   
location ~ \.php
{
    include /etc/nginx/conf.d/php-fpm.conf;
}

Talvez não seja o mais bonito... Deve ser funcional.

Responder3

Usar vários locais é possível, mas é um pouco complicado.

Se você usar try_filesou rewritecomo explicado acima, então o client_max_body_sizeseria definido para client_max_body_sizeo contexto superior, e não para o bloco de localização que você esperaria.

Mova sua configuração PHP FastCGI para um arquivo que você possa incluir, como php-conf.conf.

Em seguida, use esta configuração:

    location / {
        # try to serve file directly, fallback to index.php
        try_files $uri /index.php$query_string;
    }

    location ~ ^/admin/upload$ {
        client_max_body_size 4m;
        include /etc/nginx/php-conf.conf;
        fastcgi_param SCRIPT_FILENAME $realpath_root/index.php;
    }

    location ~ ^/index\.php(/|$) {
        include /etc/nginx/php-conf.conf;
        internal;
    }

Observe que você precisa substituir SCRIPT_FILENAMEpara usar index.phpse tiver um nome de script diferente definido. Isso pode acontecer por causa de fastcgi_split_path_info ^(.+\.php)(/.*)$;.

informação relacionada