Php upload с ошибками

Php upload с ошибками

Опция MAX_FILE_SIZE не должна позволять передачу файлов, размер которых превышает лимит, установленный конфигурационной директивой upload_max_filesize в php.ini . Ограничение по умолчанию составляет 2 мегабайта.

В случае, если установлены ограничения памяти, вам может понадобиться увеличить значение опции memory_limit. Убедитесь в том, что значение memory_limit достаточно велико.

В случае, если опция max_execution_time установлена слишком маленьким значением, необходимое время работы скрипта может превышать это значение. Убедитесь в том, что значение max_execution_time достаточно велико.

Замечание: Директива max_execution_time касается исключительно времени, используемого непосредственно самим скриптом. Время, потраченное на внешние действия, такие как системные вызовы при помощи функции system() или sleep() , обращения к базе данных, а также время, потраченное на загрузку файла и другие действия, происходящие вне скрипта, не учитываются при определении максимально допустимого промежутка времени, отведённого для выполнения скрипта.

Директива max_input_time указывает максимально допустимое время в секундах для получения входящих данных, в том числе и загружаемых файлов. В случае, если вы имеете дело с несколькими или большими файлами, либо удалённые пользователи используют медленный канал, ограничение по умолчанию в 60 секунд может быть превышено.

Если директива post_max_size слишком мала, большие файлы не смогут быть загружены на сервер. Убедитесь, что значение директивы post_max_size достаточно велико.

Опция max_file_uploads контролирует максимальное количество загружаемых файлов в течение одного запроса. Если загружается большее количество файлов, чем указано в этом ограничении, то массив $_FILES прекратит дальнейшую обработку файлов по достижении этого ограничения. Например, если max_file_uploads установлено в 10 , то $_FILES никогда не будет содержать больше 10 элементов.

Читайте также:  Php crypt with salt

Если не проверять, с какими файлами вы работаете, пользователи могут получить доступ к конфиденциальной информации, расположенной в других директориях.

Поскольку разные системы по-разному работают с файловой структурой, нет никаких гарантий того, что файлы с экзотическими именами (например, которые содержат пробельные символы) будут обработаны корректно.

Разработчики не должны использовать одинаковые имена для обычных полей ввода (тег input ) и полей выбора файла в пределах одной и той же формы (например, используя имя для тега input наподобие foo[] ).

Источник

Массив $_FILES

В PHP-скрипте обработка загруженных через форму происходит через глобальный массив $_FILES , рассмотрим его содержимое:

Загрузка одного файла

Чтобы форма отправила файл, необходимо использовать только метод POST для отправки данных и добавить к тегу атрибут enctype=»multipart/form-data» , который определяет способ кодирования данных формы при их отправке на сервер.

Код скрипта index.php:

Результат:

Array( [name] => image.jpg [type] => image/jpeg [tmp_name] => /home/user/temp/phpjX2YXo [error] => 0 [size] => 119303 )

Описание значений массива $_FILES :

$_FILES[‘file-1’][‘name’] Оригинальное имя файла на компьютере клиента.
$_FILES[‘file-1’][‘type’] Mime-тип файла, в случае, если браузер предоставил такую информацию. Этот mime-тип не проверяется на стороне PHP, так что не полагайтесь на его значение без проверки.
$_FILES[‘file-1’][‘size’] Размер принятого файла в байтах .
$_FILES[‘file-1’][‘tmp_name’] Временное имя, с которым принятый файл был сохранен на сервере.
$_FILES[‘file-1’][‘error’] Код ошибки, которая может возникнуть при загрузке файла.

Загрузка несколько файлов

Для загрузки сразу нескольких файлов к нужно добавить атрибут multiple , а к имени поля – [] .

Код скрипта index.php

Результат:

Array( [name] => Array( [0] => image.jpg [1] => arhive.zip ) [type] => Array( [0] => image/jpeg [1] => application/zip ) [tmp_name] => Array( [0] => /home/user/temp/phpK3h32F [1] => /home/user/temp/phpBrGxus ) [error] => Array( [0] => 0 [1] => 0 ) [size] => Array( [0] => 119303 [1] => 6792 ) )

Как видно, структура массива разделена по свойствам, а не по файлам. Для удобства работы с циклом foreach массив $_FILES можно преобразовать:

 $l) < foreach($l as $i =>$v) < $files[$i][$k] = $v; >> $_FILES['file-2'] = $files; print_r($_FILES);

Результат:

Array( [0] => Array( [name] => image.jpg [type] => image/jpeg [tmp_name] => /home/user/temp/phpKgSQbo [error] => 0 [size] => 119303 ) [1] => Array( [name] => arhive.zip [type] => application/zip [tmp_name] => /home/user/temp/phpVht8LS [error] => 0 [size] => 6792 ) )

Максимальный размер загружаемого файла

Размер загружаемого файла можно ограничить, добавив в форму скрытое поле с максимальным размером файла :

В случае превышения размера файла в переменной $_FILES[‘file-1’][‘error’] будет ошибка с кодом « 2 ».

Коды ошибок загрузки файлов

В случаи, если при загрузке файла произошла ошибка, в переменной $_FILES[‘file’][‘error’] будет содержатся её код. Возможны следующие значения:

Код Константа Описание
0 UPLOAD_ERR_OK Ошибок не возникло, файл успешно загружен на сервер.
1 UPLOAD_ERR_INI_SIZE Размер файла превысил максимально допустимый размер, который задан директивой upload_max_filesize
2 UPLOAD_ERR_FORM_SIZE Размер загружаемого файла превысил значение MAX_FILE_SIZE, указанное в HTML-форме.
3 UPLOAD_ERR_PARTIAL Загружаемый файл был получен только частично.
4 UPLOAD_ERR_NO_FILE Файл не был загружен.
6 UPLOAD_ERR_NO_TMP_DIR Отсутствует временная папка.
7 UPLOAD_ERR_CANT_WRITE Не удалось записать файл на диск (возникает, когда на хостинге закончилось место).
8 UPLOAD_ERR_EXTENSION PHP-расширение остановило загрузку файла.

Настройки PHP

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

Посмотреть установленные значения можно с помощью функции phpinfo() , в разделе «Core».

Раздел «Core» в phpinfo

В php.ini:

; Разрешение на загрузку файлов file_uploads = On ; Максимальное время выполнения скрипта в секундах max_execution_time = 60 ; Максимальное потребление памяти одним скриптом memory_limit = 64M ; Максимально допустимый размер данных отправляемых методом POST post_max_size = 50M ; Папка для хранения файлов во время загрузки upload_tmp_dir = home/user/temp ; Максимальный размер загружаемого файла upload_max_filesize = 5M ; Максимально разрешённое количество одновременно загружаемых файлов max_file_uploads = 10

В .htaccess:

# Разрешение на загрузку файлов php_value file_uploads On # Максимальное время выполнения скрипта в секундах php_value max_execution_time 60 # Максимальное потребление памяти одним скриптом php_value memory_limit 64M # Максимально допустимый размер данных отправляемых методом POST php_value post_max_size 50M # Папка для хранения файлов во время загрузки php_value upload_tmp_dir home/user/temp # Максимальный размер загружаемого файла php_value upload_max_filesize 5M # Максимально разрешённое количество одновременно загружаемых файлов php_value max_file_uploads 10

Источник

Загрузка файлов на сервер PHP

Загрузка файлов на сервер PHP

В статье приведен пример формы и php-скрипта для безопасной загрузки файлов на сервер, возможные ошибки и рекомендации при работе с данной темой. HTML-форма отправит файл только методом POST и с атрибутом enctype=»multipart/form-data» .

Форма для загрузки сразу нескольких файлов

Файл upload.php

  • Поддерживает как одиночную загрузку файла так и множественную (multiple) без изменения кода.
  • Проверка на все возможные ошибки которые могут возникнуть при загрузке файлов.
  • Имена файлов переводятся в транслит и удаляются символы которые будут в дальнейшем мешать вывести их на сайте.
  • Есть возможность указать разрешенные и запрещенные для загрузки расширения файлов.
// Название $input_name = 'file'; // Разрешенные расширения файлов. $allow = array(); // Запрещенные расширения файлов. $deny = array( 'phtml', 'php', 'php3', 'php4', 'php5', 'php6', 'php7', 'phps', 'cgi', 'pl', 'asp', 'aspx', 'shtml', 'shtm', 'htaccess', 'htpasswd', 'ini', 'log', 'sh', 'js', 'html', 'htm', 'css', 'sql', 'spl', 'scgi', 'fcgi' ); // Директория куда будут загружаться файлы. $path = __DIR__ . '/uploads/'; if (isset($_FILES[$input_name])) < // Проверим директорию для загрузки. if (!is_dir($path)) < mkdir($path, 0777, true); >// Преобразуем массив $_FILES в удобный вид для перебора в foreach. $files = array(); $diff = count($_FILES[$input_name]) - count($_FILES[$input_name], COUNT_RECURSIVE); if ($diff == 0) < $files = array($_FILES[$input_name]); >else < foreach($_FILES[$input_name] as $k =>$l) < foreach($l as $i =>$v) < $files[$i][$k] = $v; >> > foreach ($files as $file) < $error = $success = ''; // Проверим на ошибки загрузки. if (!empty($file['error']) || empty($file['tmp_name'])) < switch (@$file['error']) < case 1: case 2: $error = 'Превышен размер загружаемого файла.'; break; case 3: $error = 'Файл был получен только частично.'; break; case 4: $error = 'Файл не был загружен.'; break; case 6: $error = 'Файл не загружен - отсутствует временная директория.'; break; case 7: $error = 'Не удалось записать файл на диск.'; break; case 8: $error = 'PHP-расширение остановило загрузку файла.'; break; case 9: $error = 'Файл не был загружен - директория не существует.'; break; case 10: $error = 'Превышен максимально допустимый размер файла.'; break; case 11: $error = 'Данный тип файла запрещен.'; break; case 12: $error = 'Ошибка при копировании файла.'; break; default: $error = 'Файл не был загружен - неизвестная ошибка.'; break; >> elseif ($file['tmp_name'] == 'none' || !is_uploaded_file($file['tmp_name'])) < $error = 'Не удалось загрузить файл.'; >else < // Оставляем в имени файла только буквы, цифры и некоторые символы. $pattern = "[^a-zа-яё0-9,~!@#%^-_\$\?\(\)\\[\]\.]"; $name = mb_eregi_replace($pattern, '-', $file['name']); $name = mb_ereg_replace('[-]+', '-', $name); // Т.к. есть проблема с кириллицей в названиях файлов (файлы становятся недоступны). // Сделаем их транслит: $converter = array( 'а' => 'a', 'б' => 'b', 'в' => 'v', 'г' => 'g', 'д' => 'd', 'е' => 'e', 'ё' => 'e', 'ж' => 'zh', 'з' => 'z', 'и' => 'i', 'й' => 'y', 'к' => 'k', 'л' => 'l', 'м' => 'm', 'н' => 'n', 'о' => 'o', 'п' => 'p', 'р' => 'r', 'с' => 's', 'т' => 't', 'у' => 'u', 'ф' => 'f', 'х' => 'h', 'ц' => 'c', 'ч' => 'ch', 'ш' => 'sh', 'щ' => 'sch', 'ь' => '', 'ы' => 'y', 'ъ' => '', 'э' => 'e', 'ю' => 'yu', 'я' => 'ya', 'А' => 'A', 'Б' => 'B', 'В' => 'V', 'Г' => 'G', 'Д' => 'D', 'Е' => 'E', 'Ё' => 'E', 'Ж' => 'Zh', 'З' => 'Z', 'И' => 'I', 'Й' => 'Y', 'К' => 'K', 'Л' => 'L', 'М' => 'M', 'Н' => 'N', 'О' => 'O', 'П' => 'P', 'Р' => 'R', 'С' => 'S', 'Т' => 'T', 'У' => 'U', 'Ф' => 'F', 'Х' => 'H', 'Ц' => 'C', 'Ч' => 'Ch', 'Ш' => 'Sh', 'Щ' => 'Sch', 'Ь' => '', 'Ы' => 'Y', 'Ъ' => '', 'Э' => 'E', 'Ю' => 'Yu', 'Я' => 'Ya', ); $name = strtr($name, $converter); $parts = pathinfo($name); if (empty($name) || empty($parts['extension'])) < $error = 'Недопустимое тип файла'; >elseif (!empty($allow) && !in_array(strtolower($parts['extension']), $allow)) < $error = 'Недопустимый тип файла'; >elseif (!empty($deny) && in_array(strtolower($parts['extension']), $deny)) < $error = 'Недопустимый тип файла'; >else < // Чтобы не затереть файл с таким же названием, добавим префикс. $i = 0; $prefix = ''; while (is_file($path . $parts['filename'] . $prefix . '.' . $parts['extension'])) < $prefix = '(' . ++$i . ')'; >$name = $parts['filename'] . $prefix . '.' . $parts['extension']; // Перемещаем файл в директорию. if (move_uploaded_file($file['tmp_name'], $path . $name)) < // Далее можно сохранить название файла в БД и т.п. $success = 'Файл «' . $name . '» успешно загружен.'; >else < $error = 'Не удалось загрузить файл.'; >> > // Выводим сообщение о результате загрузки. if (!empty($success)) < echo '

' . $success . '

'; > else < echo '

' . $error . '

'; > > >

Возможные проблемы

  • На unix хостингах php функция move_uploaded_file() не будут перемещать файлы в директорию если у нее права меньше 777.
  • Загрузка файлов может быть отключена в настройках PHP директивой file_uploads .
  • Не загружаются файлы большого размера, причина в ограничениях хостинга.
    Посмотрите в phpinfo() значения директив:
    • upload_max_filesize – максимальный размер закачиваемого файла.
    • max_file_uploads – максимальное количество одновременно закачиваемых файлов.
    • post_max_size – максимально допустимый размер данных, отправляемых методом POST, его значение должно быть больше upload_max_filesize .
    • memory_limit – значение должно быть больше чем post_max_size .

    Не забудьте в директории куда помещаются загруженные файлы запретить выполнение PHP.

    Источник

Оцените статью