Dropzone multiple file upload uploads 2 files at a time - dropzone.js

I have the following code
HTML
<form action="{{ route('documents.store') }}" method="POST" class="kt-form kt-form--label-right">
#csrf
<div class="kt-portlet__body">
<div class="form-group">
<div class="dropzone dropzone-default dropzone-success" id="documents_upload" style="padding: 0;">
<div class="dropzone-msg dz-message needsclick">
<h3 class="dropzone-msg-title">Drop files here</h3>
</div>
</div>
</div>
</div>
</form>
Javascript
<script type="text/javascript">
$(document).ready(function() {
$('#documents_upload').dropzone({
url: "{{ route('documents.store') }}", // Set the url for your upload script location
paramName: "documents", // The name that will be used to transfer the file
maxFiles: 50,
maxFilesize: 4, // MB
addRemoveLinks: true,
acceptedFiles: "application/msword, application/vnd.ms-excel, application/pdf, image/*, application/vnd.openxmlformats-officedocument.wordprocessingml.document, application/vnd.openxmlformats-officedocument.spreadsheetml.sheet, image/*",
uploadMultiple: true,
headers: {
'X-CSRF-TOKEN': "{{ csrf_token() }}"
},
queuecomplete: function() {
// notify about successful upload
// window.location.replace("{{ route('client.documents.index') }}");
}
});
});
</script>
The problem
It seems like this uploads the documents on chunks, 2 at a time. So if I want to upload 8 files it makes 4 requests, each containing 2 files. I want to upload all at once, is there any easy way I can do this ? This method causes many problems, because the user may upload a large amount of documents and when half of them are ready, he can leave/refresh the page, etc. and he will have to search which documents have been uploaded and which have not.

You need to tell the dropzone to do a parallel upload in the options of your dropzone, by the quantity you want.
<script type="text/javascript">
$(document).ready(function() {
$('#documents_upload').dropzone({
url: "{{ route('documents.store') }}", // Set the url for your upload script location
paramName: "documents", // The name that will be used to transfer the file
maxFiles: 50,
maxFilesize: 4, // MB
addRemoveLinks: true,
acceptedFiles: "application/msword, application/vnd.ms-excel, application/pdf, image/*, application/vnd.openxmlformats-officedocument.wordprocessingml.document, application/vnd.openxmlformats-officedocument.spreadsheetml.sheet, image/*",
parallelUploads:10,
uploadMultiple: true,
headers: {
'X-CSRF-TOKEN': "{{ csrf_token() }}"
},
queuecomplete: function() {
// notify about successful upload
// window.location.replace("{{ route('client.documents.index') }}");
}
});
});
Let me know if it worked!!

Related

Filepond integration with livewire dosen't shows progressBar in percentage like 1% to 100%

I have integrated Filepond in my project, am getting a problem when I upload a file it doesn't show its progress from 1 % to 100% but other things work well and the image view also with no problem. Filepond working fine only issue is that when we upload file in livewire component it doesn't show upload progress in percentage. And I am also using same in my controller which is working fine and also showing a progress in percentage.
Initialization with Alpinjs code:
<div class="col-md-12 pb-3 filepond-box">
#if($label)
<x-form.label name="{{ $name }}" label="{{$label}}" class="col-form-label"></x-form.label>
#endif
<div
class="col-md-12"
wire:ignore
x-data
x-init="
() => {
const pond = FilePond.create($refs.filepond)
pond.setOptions({
filePosterMaxHeight:256,
maxFileSize:'10MB',
allowMultiple:true,
server: {
headers: {
'X-CSRF-TOKEN': '{{ csrf_token() }}',
},
#isset($_instance)
process:(fieldName, file, metadata, load, error, progress, abort, transfer, options) => {
#this.upload('{{ $attributes->whereStartsWith('wire:model')->first() }}', file, load, error, progress)
},
#else
process: '/file-upload',
#endisset
#isset($_instance)
revert: (filename, load) => {
#this.removeUpload('{{ $attributes->whereStartsWith('wire:model')->first() }}', filename, load)
},
remove: (source, load, error) => {
#this.remove('{{ $attributes->whereStartsWith('wire:model')->first() }}',source);
load();
},
#endisset
load: (source, load, error, progress, abort, headers) => {
var myRequest = new Request(source);
fetch(myRequest).then(function(response) {
response.blob().then(function(myBlob) {
load(myBlob)
});
});
}
},
files: {{$files}}
});
}"
>
<input type="file" x-ref="filepond" name="{{$name}}" {{$attributes}}/>
</div>
<x-form.error field="{{ $attributes->whereStartsWith('wire:model')->first() }}"></x-form.error>
#if($tooltip)
<div class="file-pond-doted-box-tooltip">
{{$tooltip}}
<div class="file-pond-doted-box-tooltip-arrow"></div>
</div>
#endif

Bootstrap file-input does not call the controller method in Laravel

I am new to Laravel. I am using Bootstrap file-input plugin to upload multiple files in Laravel. But in my code, url in the uploadUrl is not called. That means ajax call is not sent to the laravel backend controller and controller method is not called. Could you please help me in resolving this issue? Thank you.
HTML CODE
<div class="form-group">
<label class="col-sm-2 control-label required">FEATURED IMAGES</label>
<div class="col-sm-10">
<input id="featured-file" name="featured-file[]" type="file" multiple class="file-loading">
<p class="notice">Please use to upload 550px width x 670px height images for better view</p>
</div>
</div>
jQuery Code
$("#featured-file").fileinput({
theme: 'fa',
uploadAsync:true,
uploadUrl:"{{ url('/news/uploadimgsaddmode') }}",
uploadExtraData: function() {
return {
_token: '<?php echo csrf_token() ?>',
};
},
allowedFileExtensions: ['jpg', 'png', 'gif','jpeg'],
overwriteInitial: false,
maxFileSize:2000,
maxFilesNum: 10
}).on('fileuploaded', function(event, previewId, index, fileId) {
console.log('File Uploaded', 'ID: ' + fileId + ', Thumb ID: ' + previewId);
}).on('fileuploaderror', function(event, data, msg) {
console.log('File Upload Error', 'ID: ' + data.fileId + ', Thumb ID: ' + data.previewId);
});
Laravel Controller Method
public function uploadimagesaddmode(Request $request){
Session::put('uploaded_files','Hi');
Session::save();
return response()->json(['uploaded' =>'Hi']);
}
And I used some html code to test whether controller method is called or not
<p>#if(Session::has('uploaded_files')) {{ Session::get('uploaded_files') }} #endif</p>
If controller method is called Session values should be printed. But no value is printed.
I found a solution. Thanks for all who responded to my question :)
I edited the jQuery Code. Here's the edited one. It works for me.
$(document).on("ready", function() {
$("#featured-file").fileinput({
theme: 'fa',
allowedFileExtensions: ['jpg', 'png', 'gif','jpeg'],
uploadUrl: "{{ url('news/uploadimgsaddmode') }}",
uploadExtraData: function() {
return {
_token: '<?php echo csrf_token() ?>',
};
},
uploadAsync:true,
overwriteInitial: false,
maxFileSize:2000,
maxFilesNum: 10,
}).on("filebatchselected", function(event, files) {
$("#featured-file").fileinput("upload");
});
});

How to Pass initialPreview Data in bootstrap-fileinput

I have a page that allows users to edit a property listing they had previously submitted. I've been using bootstrap-fileinput to allow users to add images, and it will use the initialPreview attribute to show images that they've already uploaded. Users can remove the initialPreview images to remove images from the dropzone, but I can't find a way to pass this info to the server, that the user has removed these initialPreview images.
I've tried uploadExtraData: function() {}
But I can't get any information about the initialPreview images. Also, I am using the Laravel 5.7 PHP framework for my website.
<div class="form-group">
<label for="additional_info" class="col-lg-12 control-label">Add Photos to Attract Lender Interest</label>
<div class="col-lg-12">
<input type="file" name="image[]" id="image" multiple class="image" data-overwrite-initial="false"
data-min-file-count="0" value="{{ $mortgage->close_date}}">
</div>
</div>
{{-- Scripts for the pretty file input plugin called bootstrap-fileinput --}}
<script src="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-fileinput/4.4.7/js/fileinput.js" type="text/javascript"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-fileinput/4.5.2/themes/fas/theme.min.js" type="text/javascript"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.11.0/umd/popper.min.js" type="text/javascript"></script>
<script type="text/javascript">
$("#image").fileinput({
overwriteInitial: false,
initialPreview: [
// IMAGE DATA
"http://digitalbroker.test/storage/properties/847%20Queen%20Street%20West,%20Toronto,%20ON,%20Canada_1.JPG",
// IMAGE DATA
"http://digitalbroker.test/storage/properties/847%20Queen%20Street%20West,%20Toronto,%20ON,%20Canada_2.JPG",
],
initialPreviewAsData: true, // identify if you are sending preview data only and not the raw markup
initialPreviewFileType: 'image', // image is the default and can be overridden in config below
initialPreviewDownloadUrl: 'http://kartik-v.github.io/bootstrap-fileinput-samples/samples/{filename}', // includes the dynamic `filename` tag to be replaced for each config
showUpload: false,
theme: 'fas',
uploadUrl: "/submit-mortgage",
uploadExtraData: function () {
return {
_token: $("input[name='_token']").val(),
};
},
allowedFileExtensions: ['jpg', 'png', 'gif', 'jpeg'],
overwriteInitial: true,
showCaption: false,
showRemove: true,
maxFileSize: 5000,
maxFilesNum: 8,
fileActionSettings: {
showRemove: true,
showUpload: false,
showZoom: true,
showDrag: false,
},
slugCallback: function (filename) {
return filename.replace('(', '_').replace(']', '_');
}
});
</script>
Right now it just removes any old images upon submit and will save any newly uploaded ones. I'd like to both keep track of what initialPreview images were not removed, and which new images were uploaded.
I know this is an older question, but for those who stumble upon it here is a solution:
When a user clicks the remove button on the initialPreview frame you can pass information from that to the server by adding additional option to fileinput which will make an Ajax call each time the remove button is clicked.
Using the question above you would need to add:
initialPreviewConfig: [
{
// This is passed to the server in the request body as key: 0
key: 0,
// This is the url that you would send a POST request to that will handle the call.
url: 'http://www.example.com/image/remove',
// Any extra data that you would like to add to the POST request
extra: {
key: value
}
}
]
You would need to create an object for each item you have within your initialPreview array.
The OP's .fileinput would become:
$("#image").fileinput({
overwriteInitial: false,
initialPreview: [
// IMAGE DATA
"http://digitalbroker.test/storage/properties/847%20Queen%20Street%20West,%20Toronto,%20ON,%20Canada_1.JPG",
// IMAGE DATA
"http://digitalbroker.test/storage/properties/847%20Queen%20Street%20West,%20Toronto,%20ON,%20Canada_2.JPG",
],
initialPreviewConfig: [
{
key: 0,
url: '/image/remove', //custom URL
extra: {
image: '847 Queen Street West, Toronto, ON, Canada_1.JPG
}
},
{
key: 1,
url: '/image/remove', //custom URL
extra: {
image: 847 Queen Street West, Toronto, ON, Canada_2.JPG
}
},
],
initialPreviewAsData: true, // identify if you are sending preview data only and not the raw markup
initialPreviewFileType: 'image', // image is the default and can be overridden in config below
initialPreviewDownloadUrl: 'http://kartik-v.github.io/bootstrap-fileinput-samples/samples/{filename}', // includes the dynamic `filename` tag to be replaced for each config
showUpload: false,
theme: 'fas',
uploadUrl: "/submit-mortgage",
uploadExtraData: function () {
return {
_token: $("input[name='_token']").val(),
};
},
allowedFileExtensions: ['jpg', 'png', 'gif', 'jpeg'],
overwriteInitial: true,
showCaption: false,
showRemove: true,
maxFileSize: 5000,
maxFilesNum: 8,
fileActionSettings: {
showRemove: true,
showUpload: false,
showZoom: true,
showDrag: false,
},
slugCallback: function (filename) {
return filename.replace('(', '_').replace(']', '_');
}
});
I hope this helps anybody who comes across it.
FYI this is my first answer on SO (please be kind :P )

DropZone.js uploading is not working on programmatically

I am working on dropzone js programmatically. this is My div,
<div class="dropzone" id="my-dropzone">
<div class="dz-message">
<div class="col-xs-8">
<div class="message">
<p>Drop files here or Click to Upload</p>
</div>
</div>
</div>
<div class="fallback">
<input type="file" name="file" multiple>
</div>
</div>
and rpzone class is
// Dropzone class:
var myDropzone = new Dropzone("div#my-dropzone", { url: "/file/post"});
but when I drag and drop images to dropzone box images are preview with cross symbols (not success upload). then how can I fix this problem?
dropzone.confif.js
var total_photos_counter = 0;
Dropzone.options.myDropzone = {
uploadMultiple: true,
parallelUploads: 2,
maxFilesize: 5,
previewTemplate: document.querySelector('#preview').innerHTML,
addRemoveLinks: true,
dictRemoveFile: 'Remove file',
dictFileTooBig: 'Image is larger than 16MB',
timeout: 10000,
init: function () {
this.on("removedfile", function (file) {
$.post({
url: '/images-delete',
data: {id: file.name, _token: $('[name="_token"]').val()},
dataType: 'json',
success: function (data) {
total_photos_counter--;
$("#counter").text("# " + total_photos_counter);
}
});
});
},
success: function (file, done) {
total_photos_counter++;
$("#counter").text("# " + total_photos_counter);
}
};
after long time spending find the solution. problem is {{ csrf_field() }} not configuring in my div tag,
first Add this to your main blade template in the section:
<meta name="csrf-token" content="{{ csrf_token() }}">
and then configure dropzone.config.js file to csrf
Dropzone.options.myDropzone = {
uploadMultiple: true,
parallelUploads: 2,
maxFilesize: 16,
previewTemplate: document.querySelector('#preview').innerHTML,
addRemoveLinks: true,
dictRemoveFile: 'Remove file',
dictFileTooBig: 'Image is larger than 16MB',
timeout: 10000,
init: function () {
this.on("removedfile", function (file) {
$.post({
url: '/images-delete',
data: {id: file.name, _token: $('[name="_token"]').val()},
dataType: 'json',
success: function (data) {
total_photos_counter--;
$("#counter").text("# " + total_photos_counter);
}
});
});
},
success: function (file, done) {
total_photos_counter++;
$("#counter").text("# " + total_photos_counter);
},
sending: function(file, xhr, formData){
formData.append('_token', $('meta[name="csrf-token"]').attr('content'));
}
};
now it is working fine with correct url

Laravel: Dropzone js, getting [object Object], but why?

I'm trying to upload an image using Dropzone.js in Laravel, but I'm getting an error showing [object Object] on my thumbnails after uploading a photo. I can't find my error and I don't understand what the cause is.
Here is my code and an image of the error. Why is this happening? What can I do?
View:
<div class="container col-md-8 col-12 mx-auto">
<div class="row">
<div class="col-sm-10 offset-sm-1">
<h2 class="page-heading">Upload your Images <span id="counter"></span></h2>
<form method="post" action="{{ url('/addimage') }}"
enctype="multipart/form-data" class="dropzone" id="my-dropzone">
{{ csrf_field() }}
<div class="dz-message">
<div class="col-xs-8">
<div class="message">
<p>Drop files here or Click to Upload</p>
</div>
</div>
</div>
<div class="fallback">
<input type="file" name="file" multiple>
<input type="hidden" name="id" value="{{$id}}" >
</div>
</form>
</div>
</div>
</div>
Route:
Route::group(['middleware'=>'auth'], function (){
...
Route::post('/addimage', 'FrontendController#addimage');
Route::post('/adddeleteimage', 'FrontendController#adddeleteimage');
...
});
Controller:
public function addimage(Request $request){
$file = $request->file('file');
$filename = uniqid().".".$file->clientExtension();
$file->move('img/product', $filename);
$dropzone = new Imagedb;
$dropzone->product_id = $request->id;
$dropzone->url = 'img/product'.$filename;
$dropzone->save();
}
JS:
var total_photos_counter = 0;
Dropzone.options.myDropzone = {
uploadMultiple: true,
parallelUploads: 2,
maxFilesize: 16,
acceptedFiles: "image/*",
resizeWidth: 360,
previewTemplate: document.querySelector('#preview').innerHTML,
addRemoveLinks: true,
dictRemoveFile: 'Remove file',
dictFileTooBig: 'Image is larger than 16MB',
timeout: 10000,
init: function () {
this.on("removedfile", function (file) {
$.post({
url: '/adddeleteimage',
data: {id: file.name, _token: $('[name="_token"]').val()},
dataType: 'json',
success: function (data) {
total_photos_counter--;
$("#counter").text("# " + total_photos_counter);
}
});
});
},
success: function (file, done) {
total_photos_counter++;
$("#counter").text("# " + total_photos_counter);
}
};
Firstly, try
$('meta[name="csrf-token"]').attr('content')
as token
I fixed this error by adding in head tag
<meta name="csrf-token" content="{{ csrf_token() }}">
and in dropzone initialization config
headers: { 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content') }
Example:
autoProcessQueue:false,
required:true,
acceptedFiles: ".png,.jpg,.gif,.bmp,.jpeg",
addRemoveLinks: true,
maxFiles:8,
parallelUploads : 100,
maxFilesize:5,
headers: { 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content') }

Resources