Загрузка файлов по частям с помощью Laravel и AJAX

Я пытаюсь создать скрипт для загрузки больших файлов, я отправляю данные через Ajax (это работает), но это не решило проблему больших файлов, в лучшем случае я могу загрузить только 100 МБ, а это не подходит для пользователь, поможете ли вы добавить Загрузка файлов по частям, спасибо

Это мой HTML:

<form id = "upload_form" method = "POST" enctype = "multipart/form-data">
 @csrf
 <input type = "file" name = "file" id = "file-7" class = "inputfile inputfile-6" />
<center>
   <a href = "#" id = "star_up" value = "hide/show">
      <input class = "btn btn-info btn-lg wow tada" id = "sell_house_submit" type = "submit" name = "upload_file" value = "@lang('lang.UPLOAD')">
   </a>
</center>
<div id = "prog" style = "display:none;">
    <progress id = "progressBar" class = "wow tada" style = "@if (isMobile())width:200px;@else width:750px;@endif height: 10px;" value = "0" max = "100">
    </progress>
    <h3 class = "av" id = "status" ></h3>
    <p id = "loaded_n_total" ></p>

Мой javascript:

$(document).ready(function(){

 $('#upload_form').on('submit', function(event){
   $.ajax({
   url:"{{ route('upload') }}",
   method:"POST",
   data: new FormData(this),
   xhr: function() {
        var myXhr = $.ajaxSettings.xhr();
        if (myXhr.upload){
            myXhr.upload.addEventListener('progress',progressHandler, false);
            myXhr.addEventListener("load", completeHandler, false);
            myXhr.addEventListener("error", errorHandler, false);
            myXhr.addEventListener("abort", abortHandler, false);
        }
        return myXhr;
    },
   dataType:'JSON',
   contentType: false,
   cache: false,
   processData: false,
   // IF SUCCESS
   success:function(data)
   {
      if (data.type_is == 'swal') {
        swal({
            title: data.title,
            html: data.html,
            showCloseButton: true,
            focusConfirm: false,
            type: data.status
        });
        jQuery('#progress_up').toggle('hide');
        document.getElementById('file-7').value = '';
        document.getElementById('name_file').innerHTML = '';
      } 
   }
  })
    event.preventDefault();
 });

});

Контроллер:

protected function upload(Request $request) {
  ini_set('max_execution_time', 3000);
  ini_set('memory_limit','256M');

  // UPLOAD FILE
  if (getValue('storage_type', 'disk') == 's3') {
     $path = Storage::disk('s3')->putFile('files', $request->file('file'));
     $storage = 's3';
  } else {
  $path = Storage::putFile('files', $request->file('file'));
  $storage = 'disk';
  }
  // RANDOM
  $link_id = Random();
  $delete_token = Random(50);
  $preview = Random(10);
  $ip = getip();

  $this->createFile($name, $path, $link_id, $delete_token, $ip, $preview, $size, $mime, $type, $storage);

  // FILE UPLOADED

  return response()->json([
     'title' => trans('lang.GREAT'),
     'html' => getFileInfoHTML($link_id, $delete_token, $name, $type, $preview),
     'type_is' => 'swal',
     'status' => 'success'
  ]);
}

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

Я думаю, что это код, который нужно использовать: jQuery-File-Upload? но я не знаю, как им пользоваться!

Saif Manwill 28.12.2018 18:35

Вы можете попробовать этот пакет: packagist.org/packages/pion/laravel-chunk-upload

Md.Sukel Ali 28.12.2018 18:40

Да, я знаю, а как насчет AJAX? как отправить данные с maxChunkSize?

Saif Manwill 28.12.2018 18:43

Поддержка pion / laravel-chunk-upload github.com/23/resumable.js для дескриптора ajax внешнего интерфейса.

Md.Sukel Ali 28.12.2018 18:48

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

Saif Manwill 28.12.2018 18:54

Могу ли я использовать пакет laravel-chunk-upload для загрузки нескольких файлов и фрагментов? @ Md.SukelAli

Ray Coder 03.02.2021 13:04
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
3
6
6 739
1

Ответы 1

1. Установите pion / laravel-chunk-upload,

composer require pion/laravel-chunk-upload
\Pion\Laravel\ChunkUpload\Providers\ChunkUploadServiceProvider::class
php artisan vendor:publish --provider = "Pion\Laravel\ChunkUpload\Providers\ChunkUploadServiceProvider"

2. добавить маршрут

Route::post('/upload', 'UploadController@upload');

3. Добавьте представление и скрипты.

<script src = "https://cdnjs.cloudflare.com/ajax/libs/resumable.js/1.1.0/resumable.min.js"></script>

<script>
        var $ = window.$; // use the global jQuery instance

        var $fileUpload = $('#resumable-browse');
        var $fileUploadDrop = $('#resumable-drop');
        var $uploadList = $("#file-upload-list");

        if ($fileUpload.length > 0 && $fileUploadDrop.length > 0) {
            var resumable = new Resumable({
                // Use chunk size that is smaller than your maximum limit due a resumable issue
                // https://github.com/23/resumable.js/issues/51
                chunkSize: 1 * 1024 * 1024, // 1MB
                simultaneousUploads: 3,
                testChunks: false,
                throttleProgressCallbacks: 1,
                // Get the url from data-url tag
                target: $fileUpload.data('url'),
                // Append token to the request - required for web routes
                query:{_token : $('input[name=_token]').val()}
            });

        // Resumable.js isn't supported, fall back on a different method
            if (!resumable.support) {
                $('#resumable-error').show();
            } else {
                // Show a place for dropping/selecting files
                $fileUploadDrop.show();
                resumable.assignDrop($fileUpload[0]);
                resumable.assignBrowse($fileUploadDrop[0]);

                // Handle file add event
                resumable.on('fileAdded', function (file) {
                    // Show progress pabr
                    $uploadList.show();
                    // Show pause, hide resume
                    $('.resumable-progress .progress-resume-link').hide();
                    $('.resumable-progress .progress-pause-link').show();
                    // Add the file to the list
                    $uploadList.append('<li class = "resumable-file-' + file.uniqueIdentifier + '">Uploading <span class = "resumable-file-name"></span> <span class = "resumable-file-progress"></span>');
                    $('.resumable-file-' + file.uniqueIdentifier + ' .resumable-file-name').html(file.fileName);
                    // Actually start the upload
                    resumable.upload();
                });
                resumable.on('fileSuccess', function (file, message) {
                    // Reflect that the file upload has completed
                    $('.resumable-file-' + file.uniqueIdentifier + ' .resumable-file-progress').html('(completed)');
                });
                resumable.on('fileError', function (file, message) {
                    // Reflect that the file upload has resulted in error
                    $('.resumable-file-' + file.uniqueIdentifier + ' .resumable-file-progress').html('(file could not be uploaded: ' + message + ')');
                });
                resumable.on('fileProgress', function (file) {
                    // Handle progress for both the file and the overall upload
                    $('.resumable-file-' + file.uniqueIdentifier + ' .resumable-file-progress').html(Math.floor(file.progress() * 100) + '%');
                    $('.progress-bar').css({width: Math.floor(resumable.progress() * 100) + '%'});
                });
            }

        }


</script>


<div class = "text-center" >
    <div id = "resumable-error" style = "display: none">
        Resumable not supported
    </div>
    <div id = "resumable-drop" style = "display: none">
        <p><button id = "resumable-browse" data-url = "{{ url('upload') }}" >Upload</button> or drop here
        </p>
        <p></p>
    </div>
    <ul id = "file-upload-list" class = "list-unstyled"  style = "display: none">

    </ul>
    <br/>
</div>

4. В вашем UploadController,

<?php
namespace App\Http\Controllers;
use Storage;
use Illuminate\Http\Request;
use Illuminate\Http\UploadedFile;
use Pion\Laravel\ChunkUpload\Exceptions\UploadMissingFileException;
use Pion\Laravel\ChunkUpload\Handler\AbstractHandler;
use Pion\Laravel\ChunkUpload\Handler\HandlerFactory;
use Pion\Laravel\ChunkUpload\Receiver\FileReceiver;
class UploadController extends Controller
{
    /**
     * Handles the file upload
     *
     * @param Request $request
     *
     * @return \Illuminate\Http\JsonResponse
     *
     * @throws UploadMissingFileException
     * @throws \Pion\Laravel\ChunkUpload\Exceptions\UploadFailedException
     */
    public function upload(Request $request) {
        // create the file receiver
        $receiver = new FileReceiver("file", $request, HandlerFactory::classFromRequest($request));
        // check if the upload is success, throw exception or return response you need
        if ($receiver->isUploaded() === false) {
            throw new UploadMissingFileException();
        }
        // receive the file
        $save = $receiver->receive();
        // check if the upload has finished (in chunk mode it will send smaller files)
        if ($save->isFinished()) {
            // save the file and return any response you need, current example uses `move` function. If you are
            // not using move, you need to manually delete the file by unlink($save->getFile()->getPathname())
            return $this->saveFile($save->getFile());
        }
        // we are in chunk mode, lets send the current progress
        /** @var AbstractHandler $handler */
        $handler = $save->handler();
        return response()->json([
            "done" => $handler->getPercentageDone(),
            'status' => true
        ]);
    }
    /**
     * Saves the file to S3 server
     *
     * @param UploadedFile $file
     *
     * @return \Illuminate\Http\JsonResponse
     */
    protected function saveFileToS3($file)
    {
        $fileName = $this->createFilename($file);
        $disk = Storage::disk('s3');
        // It's better to use streaming Streaming (laravel 5.4+)
        $disk->putFileAs('photos', $file, $fileName);
        // for older laravel
        // $disk->put($fileName, file_get_contents($file), 'public');
        $mime = str_replace('/', '-', $file->getMimeType());
        // We need to delete the file when uploaded to s3
        unlink($file->getPathname());
        return response()->json([
            'path' => $disk->url($fileName),
            'name' => $fileName,
            'mime_type' =>$mime
        ]);
    }
    /**
     * Saves the file
     *
     * @param UploadedFile $file
     *
     * @return \Illuminate\Http\JsonResponse
     */
    protected function saveFile(UploadedFile $file)
    {
        $fileName = $this->createFilename($file);
        // Group files by mime type
        $mime = str_replace('/', '-', $file->getMimeType());
        // Group files by the date (week
        $dateFolder = date("Y-m-W");
        // Build the file path
        $filePath = "upload/{$mime}/{$dateFolder}/";
        $finalPath = storage_path("app/".$filePath);
        // move the file name
        $file->move($finalPath, $fileName);
        return response()->json([
            'path' => $filePath,
            'name' => $fileName,
            'mime_type' => $mime
        ]);
    }
    /**
     * Create unique filename for uploaded file
     * @param UploadedFile $file
     * @return string
     */
    protected function createFilename(UploadedFile $file)
    {
        $extension = $file->getClientOriginalExtension();
        $filename = str_replace(".".$extension, "", $file->getClientOriginalName()); // Filename without extension
        // Add timestamp hash to name of the file
        $filename .= "_" . md5(time()) . "." . $extension;
        return $filename;
    }
}

??? Спасибо !! Сейчас попробую!

Saif Manwill 28.12.2018 20:53

Но как насчет моих параметров AJAX? нравится прогресс?

Saif Manwill 28.12.2018 21:13

Есть действие под названием fileProgress (), которое будет обрабатывать ваш прогресс. Просто попробуйте этот код. все добавлено. Вы даже можете настроить размер блока.

Md.Sukel Ali 29.12.2018 05:17

можно ли его использовать для многократной и частичной загрузки?

Ray Coder 08.02.2021 05:39

использование метода saveFileToS3 не работает. Всегда оставайся 0%. когда полностью загрузите, то покажите (завершено). Как исправить эту проблему?

Maksud Masum 20.02.2021 04:52

Другие вопросы по теме