How to Display existing files in Dropzone – Laravel 8

Dropzone is a Javascript library that allows uploading files by drag and drop.

To load existing files on dropzone need to send an AJAX request while Dropzone initialization.

In this tutorial, I show how you can display existing files in the Dropzone container in Laravel 8.

How to Display existing files in Dropzone - Laravel 8


Contents

  1. Download
  2. Controller
  3. Route
  4. View
  5. Output
  6. Conclusion

1. Download

  • Download Dropzone library from here
  • Extract the downloaded file in public/ folder.
  • Or you can use CDN –
<!-- CSS -->
<link rel="stylesheet" href="https://unpkg.com/dropzone@5/dist/min/dropzone.min.css" type="text/css" />

<!-- Script -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.6.0/jquery.min.js"></script>
<script src="https://unpkg.com/dropzone@5/dist/min/dropzone.min.js"></script>
  • Using jQuery library to send AJAX requests.

2. Controller

  • Create PageController Controller.
php artisan make:controller PageController
  • Open app/Http/Controllers/PageController.php file.
  • Create 3 methods –
    • index – Load index view.
    • uploadFile – Using this method to upload the selected file from Dropzone.

Define file validation. If file is validated successfully then upload the file and assign 1 to $data['success'] otherwise 0 to $data['success'].

Return $data Array in JSON format.

    • readFiles – Using this method to return files list to display in the Dropzone.

Specify reading location in $directory. Create $files_info Array to store files list.

In the $file_ext Array specify extensions (It is same as the defined extensions list in uploadFile() validation) that need to display on the Dropzone.

Loop on the folder to read files. If file extension exists in $file_ext Array and file size is <= 2 (It is same as the defined max file size in uploadFile() validation) then initialize $files_info Array with name, file size, and path.

Return $files_info Array in JSON format.

Completed Code

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Illuminate\Support\Facades\Validator;
use File;

class PageController extends Controller
{
   
    public function index(){
       return view('index');
    }

    // Upload file
    public function uploadFile(Request $request){

       $data = array();

       $validator = Validator::make($request->all(), [
          'file' => 'required|mimes:png,jpg,jpeg,pdf|max:2048'
       ]);

       if ($validator->fails()) {

          $data['success'] = 0;
          $data['error'] = $validator->errors()->first('file');// Error response

       }else{
          if($request->file('file')) {

             $file = $request->file('file');
             $filename = time().'_'.$file->getClientOriginalName();

             // File upload location
             $location = 'uploads';

             // Upload file
             $file->move($location,$filename);

             // Response
             $data['success'] = 1;
             $data['message'] = 'Uploaded Successfully!';

          }else{
             // Response
             $data['success'] = 0;
             $data['message'] = 'File not uploaded.'; 
          }
       }

       return response()->json($data);
    }

    // Read files 
    public function readFiles(){ 
       $directory = 'uploads'; 
       $files_info = []; 
       $file_ext = array('png','jpg','jpeg','pdf'); 
       
       // Read files
       foreach (File::allFiles(public_path($directory)) as $file) { 
          $extension = strtolower($file->getExtension()); 
      
          if(in_array($extension,$file_ext)){ // Check file extension 
             $filename = $file->getFilename(); 
             $size = $file->getSize(); // Bytes 
             $sizeinMB = round($size / (1000 * 1024), 2);// MB 
           
             if($sizeinMB <= 2){ // Check file size is <= 2 MB 
                 $files_info[] = array( 
                       "name" => $filename, 
                       "size" => $size, 
                       "path" => url($directory.'/'.$filename) 
                 ); 
             } 
          } 
       } 
       return response()->json($files_info); 
    }
}

3. Route

  • Open routes/web.php file.
  • Define 3 routes –
    • / – Load index view.
    • readFiles – Read all files from a folder for dropzone.
    • uploadFile – This is used for Dropzone file upload.

Completed Code

<?php 

use App\Http\Controllers\PageController; 
Route::get('/', [PageController::class, 'index']); 
Route::get('readFiles', [PageController::class, 'readFiles'])->name('readFiles');
Route::post('uploadFile', [PageController::class, 'uploadFile'])->name('uploadFile');

4. View

Create index.blade.php file in resources/views/ folder.

Store CSRF token in <meta > tag and include Dropzone and jQuery library.

Dropzone Container 

  • Create a <form action="{{route('uploadFile')}}" class='dropzone' >.

Script

  • Read CSRF token from <meta > tag and assign it to CSRF_TOKEN.
  • Set autoDiscover to false.
  • Initialize Dropzone on class='dropzone'.
  • I set maxFilesize to 2 and acceptedFiles to ".jpeg,.jpg,.png,.pdf".
  • Using init to fetch existing files list using AJAX. Send AJAX request to route("readFiles"), set dataType: ‘json’.
  • On successful callback loop on the response and assign { name: value.name, size: value.size } in mockFile.
  • Using sending event to send CSRF token.
  • Using success event to check return response.
  • If response.status == 0 means there is an error and if response.status == 2 means file is not uploaded. Display error message using alert().

Completed Code

<!DOCTYPE html>
<html>
<head>
   <title>How to Display existing files in Dropzone - Laravel 8</title>

   <!-- Meta -->
   <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
   <meta charset="utf-8">
   <meta name="csrf-token" content="{{ csrf_token() }}">

   <!-- CSS -->
   <link rel="stylesheet" href="https://unpkg.com/dropzone@5/dist/min/dropzone.min.css" type="text/css" />

   <!-- Script -->
   <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.6.0/jquery.min.js"></script>
   <script src="https://unpkg.com/dropzone@5/dist/min/dropzone.min.js"></script>

   <style type="text/css">
   .dz-preview .dz-image img{
       width: 100% !important;
       height: 100% !important;
       object-fit: cover;
    }
    </style>
</head>
<body>

   <div class='content'>
      <!-- Dropzone -->
      <form action="{{route('uploadFile')}}" class='dropzone' ></form> 
   </div>

   <!-- Script -->
   <script>
   var CSRF_TOKEN = document.querySelector('meta[name="csrf-token"]').getAttribute("content");

   Dropzone.autoDiscover = false;
   var myDropzone = new Dropzone(".dropzone",{ 
      maxFilesize: 2, // 2 mb
      acceptedFiles: ".jpeg,.jpg,.png,.pdf",
      init: function() { 
         myDropzone = this;

         $.ajax({
            url: '{{ route("readFiles") }}',
            type: 'get',
            dataType: 'json',
            success: function(response){

               $.each(response, function(key,value) {
                  var mockFile = { name: value.name, size: value.size };

                  myDropzone.emit("addedfile", mockFile);
                  myDropzone.emit("thumbnail", mockFile, value.path);
                  myDropzone.emit("complete", mockFile);

               });

            }
         });
      }
   });
   
   myDropzone.on("sending", function(file, xhr, formData) {
      formData.append("_token", CSRF_TOKEN);
   }); 
   
   myDropzone.on("success", function(file, response) {

      if(response.success == 0){ // Error
         alert(response.error);
      }

   });
   </script>

</body>
</html>

5. Output

View Output


6. Conclusion

If you are validating file then also use those values while reading folder files to display on the Dropzone.

If you found this tutorial helpful then don't forget to share.

Leave a Comment