Защита загружаемых файлов в PHP

У меня есть сайт с логинами и сеансами пользователей. Я хотел бы разрешить своим пользователям загружать файлы на веб-сервер, но они доступны только для их входа в систему.

Я понимаю, что если я загружу в какой-то общедоступный веб-каталог, файл будет по-прежнему доступен через:

http://www.mydomain.com/files/thefile.pdf

Однако я думаю, что могу хранить файлы в каталогах чуть выше моего общедоступного корня HTML (скажем, /mnt/content/web/html).

Итак, я мог бы создать каталог с именем (/mnt/content/web/uniqueidfortheuser) и хранить там свои файлы, а затем ссылаться на файлы через PHP с синтаксисом:

(../уникальный идентификатор пользователя/файл.pdf).

Мой вопрос - это достаточно безопасно или я что-то упускаю из виду? Имя уникального идентификатора пользователя будет храниться в базе данных и неизвестно пользователям, и им потребуется действующий сеанс, чтобы получить доступ к своему уникальному имени своей папки. И я не думаю, что они смогут вызывать какие-либо файлы в папке из Интернета.


person 916 Networks    schedule 23.12.2012    source источник


Ответы (1)


Еще лучше — когда пользователь загружает файл, укажите user_ID для файла. Затем, когда вы попытаетесь получить файл, убедитесь, что он принадлежит пользователю.

Так что даже если они угадают другой файл - это не имеет значения!

Вам нужно использовать readfile:

    function user_files($file_name = "")
    {
        // Check user is logged in
        if ($user->logged_in())
        {
           // Check file_name is valid and only contains valid chars
           if ((preg_match('^[A-Za-z0-9]{1,32}+[.]{1}[A-Za-z]{3,4}$^', $file_name)) 
           {
               // Now check file belongs to user - PSUEDOCODE
               if ($filename == $user->records)
               {
                   header('Content-Type: '.get_mime_by_extension(YOUR_PATH.$file_name)));
                   readfile(YOUR_PATH.$file_name);
               } else {
                   echo 'You do not have access to this file';
                }
           }
        }
    }

Есть некоторые проблемы с обходом каталога и т. д., поэтому вам нужно сначала проверить $file_name, как я использовал preg_match

person Laurence    schedule 23.12.2012
comment
Вау, классный ответ. Я попробую это сейчас. Благодаря тонну! - person 916 Networks; 23.12.2012