Я могу успешно загружать большие файлы (проверенные до 8 ГБ) через плагин BlueImp JQuery Uploader.
Мои настройки PHP:
upload_max_filesize 8192M post_max_size 8192M max_execution_time 200 max_input_time 200 memory_limit 8192M
Проблема, с которой я сталкиваюсь, заключается в том, что когда большие файлы (2 гб или больше) заканчивают загрузку, индикатор выполнения зависает на 100% и занимает значительное время, чтобы «закончить». Я не уверен, что происходит с последующей обработкой, за исключением того, что вместе они объединяют файлы.
Я попытался настроить размер куска в файле UploadHandler.php, и, похоже, он немного улучшился при увеличении (например, от 10 до 500 мб кусков), но задержка все еще существует. По-видимому, улучшения при отключении загружаемых фрагментов вообще (0), и я не уверен в возможных последствиях этого.
В файле 2gb задержка составляет около 20 секунд, но в файле 4gb это составляет около 2 минут. Файл 7gb занимает около 3-4 минут, а иногда и время. Это приводит к тому, что пользователь ждет, не осознавая, что происходит, когда индикатор прогресса завершился на 100% к этому моменту.
Кто-нибудь имеет представление о том, что это может быть, или как его устранять? Я подозревал, что файл в / tmp может быть скопирован, а не перемещен, но, насколько я могу судить, в php-файле нет никаких признаков этого.
Увеличение количества процессоров и оперативной памяти на моем сервере. VM немного улучшает ситуацию, хотя команда «сверху» во время этого процесса показывает, что процессор и оперативная память не выглядят широко исчерпанными (0-2% по сравнению с 90-100% во время фактическая загрузка).
Спасибо заранее.
Я не очень много знаю об этом, я ищу в google, и я нашел некоторые, я думаю, это может помочь вам.
Обычно событие «onError» запускается при возникновении исключения на сервере или клиенте. В упомянутой ситуации нет никаких исключений, пока сам сервер не отключится.
Одна из возможностей – следить за статусом загрузки и устанавливать тайм-аут JavaScript или счетчик при загрузке события, которое отменит загрузку по истечении установленного срока.
Все статусы загрузки и коды ошибок показаны здесь – http://help.infragistics.com/NetAdvantage/jQuery/2013.1/CLR4.0?page=igUpload_Using_Client_Side_Events.html
Вы можете отслеживать их с помощью аргумента fileStatus при загрузке события.
Ссылка, которая поможет вам
Что это может быть :
jQuery FileUpload регистрирует событие прогресса запроса. Это событие, когда браузер отправляет данные на сервер, а не событие подтверждения с сервера. Между отправкой браузера и сервером, подтверждающим прием, происходит задержка. См. Может ли функция onprogress быть добавлена в jQuery.ajax () с помощью xhrFields? для двух событий. Однако я не мог решить это для меня и использовал обход, поэтому я не могу полностью подтвердить это предположение.
Как решить проблему :
Используйте инструменты отладки браузера и установите точку останова здесь, в коде, чтобы получить представление о доступных переменных: https://github.com/blueimp/jQuery-File-Upload/blob/master/js/jquery.fileupload.js# L372
После того, как вы уверены, что хотите видеть, лучше всего напечатать информацию с помощью console.log и проверить вывод консоли вашего браузера.
Рабочие места :
Если вам интересно только, закончились ли все загрузки и покажут пользователю, что что-то все еще происходит, вы можете проверить события остановки / завершения, а также файлupload («active»), см. Здесь: Finish of Multiple файл загружен
После многого устранения неполадок и отладки этой проблемы я нашел то, что, по моему мнению, стал причиной, и улучшил обходное решение / решение. Это немного «взломанный» (я любитель!), Поэтому я открыт для любых предложений по улучшению этого, хотя, похоже, он работает для меня.
Файлы, загруженные с клиента, фактически загружаются в это временное местоположение на сервере: / tmp / systemd-private- random-number -httpd.service- random-number / tmp / sess_ php-session-ID
После завершения загрузки на стороне клиента индикатор выполнения пользовательского интерфейса достигает 100% и остается таким, пока сервер обрабатывает файлы.
Обработка на стороне сервера включает в себя перемещение (копирование, а затем удаление) файла из вышерасположенного / tmp-местоположения в соответствующее местоположение синим. (Предполагая, что «user_dirs» включен / истинно в параметрах blueimp, по умолчанию используется следующее: / var / www / html / server / php / files / php-session-id /).
Этот процесс копирования может занимать значительное количество времени, особенно в файлах размером более 2 ГБ или около того. По завершении обработки сервера blueimp запускает обратный вызов «fileuploaddone», а пользовательский интерфейс обновляется до состояния завершения.
Моя цель состояла в том, чтобы предоставить некоторые интерактивные пользовательские интерфейсы на этом этапе (вместо того, чтобы висит на 90%, как и у другого обходного пути). Моя среда способна к очень крупным загрузкам (10gb +), поэтому я не счел приемлемым не предоставлять отзывов пользователям о том, что может быть несколько минут обработки файлов (с учетом того, что пользователь решил, что сайт разбился, и закрытие браузера и т. Д. .).
Мое обходное решение:
Первая проблема, с которой я столкнулся, заключалась в том, что, похоже, нет обратного вызова blueimp для того момента, когда загрузка файлов завершена на стороне клиента, и начинается обработка сервера. Поэтому я работал над этим, создав функцию (в main.js), чтобы отобразить мой пользовательский «обработчик div» после того, как data.loaded соответствует data.total:
$('#fileupload').bind('fileuploadprogressall', function (e, data) { console.log(data); if (data.loaded == data.total) { setTimeout(function(){ $("#processwarn").fadeTo(300, 1); },3000); }})
Мой пользовательский div, который находится ниже информации о баре прогресса, – это другая страница php, обновленная каждые несколько секунд (с помощью ajax.load) и вычисляет общий размер файлов всех файлов в текущей папке загрузки сеанса (общий размер каталога не как представляется, дают точные результаты):
// Calculate size of files being processed $filePath = "/var/www/html/server/php/files/*php-session-id*/"; $total = 0; $d = new RecursiveIteratorIterator( new RecursiveDirectoryIterator($filePath), RecursiveIteratorIterator::SELF_FIRST ); foreach($d as $file){ $total += $file->getSize(); } // Convert to readable format if ($total >= 1073741824) { $total = number_format($total / 1073741824, 2) . ' GB'; } elseif ($total >= 1048576) { $total = number_format($total / 1048576, 2) . ' MB'; } elseif ($total >= 1024) { $total = number_format($total / 1024, 2) . ' KB'; } elseif ($total > 1) { $total = $total . ' bytes'; } elseif ($total == 1) { $total = $total . ' byte'; } else { $total = '0 bytes'; } // Display spinner gif and size of file currently being processed echo "<img src=\"img/spinner.gif\" height=\"20px\" width=\"20px\"> Please wait, processing files: $total";
Результат выглядит примерно так:
Изменить: (после некоторой дополнительной работы) – вместо этого добавляется индикатор выполнения bootstrap:
Дополнительная точка заметила из тестирования:
При включенной функции chunking (например, 1gb (maxChunkSize: 1000000000)) проблема почти исчезает, так как время обработки резко уменьшается для пользователя, так как обработка «копирования» происходит в точке chunking (каждый 1gb в этом примере ). Когда происходит окончательная обработка, сервер должен только «перезаписать» / скопировать последние оставшиеся 1gb.
Из-за этого я также испытал более быстрое общее время загрузки. Оглядываясь назад, это может быть проще или эффективнее для многих.