📜 ⬆️ ⬇️

Using Nginx and php to check permissions before uploading files

Sometimes on the site there is a need to restrict access to certain files for various reasons (to distribute files only to authorized users, anti-face, and so on). To solve this problem, you can use different approaches:

  1. Distribute files using a script in php (replace php with something you like). With this approach, we pass the file name as a parameter to the script. The code checks all conditions under which it is possible to gain access to this file and decides whether to issue a 404 or the requested file. This approach is suitable for small files, however, as the size of the file being transferred increases, it will consume a lot of system resources, since the file will be read into memory and then given.
  2. Use some unobvious web server features.


Consider the second option.
So historically, I started using nginx for reverse proxying. Having rummaged in his documentation, I discovered that with the help of this server you can control file distribution by checking access rights just before the content is rendered.
So let's get started.
I have an apache for nginx, which processes requests for dynamic content, described something like this:
location / {
proxy_pass 127.0.0.1/;
}


At first we put our content in the selected directories. In my case, the site is located in / var / www , I uploaded the protected content in / var / www / protected . For this section, I added the following lines to the nginx configuration:
location /protected {
root /var/www ;
internal ;
}

')
Here root indicates where the site is located. The internal directive indicates that this area will be available only if there is an internal redirection of nginx to the protected directory. Thus, even knowing the direct address of the resource on the server, we will receive 404 in response to our request.
The first stage is completed, the content is not available for a direct link.
However, we need to show this content under certain conditions. For this we give the first location to the following form:
location / {
rewrite ^/download/(.*) /download.php?path=$1 last;

proxy_pass 127.0.0.1/;
}

Thus, all requests that try to pick up something from download will be redirected to the file download.php. In this file, the decision will be made about allowing / denying user access to the file. The source code of the download.php file can be as follows:
<?
$ path = $ _GET ["path"];
// some actions to verify access rights
header ("X-Accel-Redirect: / protected /". $ path);
?>

If the user is allowed access to this file, then we send this header, otherwise we send him 404. After determining the access rights, php is completed. Then nginx receives this header, performs an internal redirection, and starts giving the requested file to the user.

Summary:
This method, it seems to me, will consume much less system resources when uploading files for which the rights should be checked.

The basis for the article was half- finished : blog.kovyrin.net/2006/11/01/nginx-x-accel-redirect-php-rails/lang/en
Materials used: sysoev.ru/nginx/docs

PS This article does not claim to be complete and cannot be considered as an instruction for setting up an nginx server. It deliberately omits moments regarding compression, caching and similar things.

Source: https://habr.com/ru/post/37686/


All Articles