I'm trying to figure out a way how to rename file after upload using dropzone.js so I could later delete it just by sending correct name.
What I have right now:
this.on("success", function(file, responseText) {
console.log(responseText); // responseText contains actual file name after server modifications
});
addRemoveLinks: true,
this.on("removedfile", function(file) {
var name = file.name;
$.ajax({
type: 'POST',
url: 'delete_file.html',
data: {
'file-name': name,
},
});
});
As you can see in my ajax data I am sending initial file name, not the one that is actually on the server (e.g. if there are multiple same named files server will rename them).
I have been thinking of changing previewElement name on success:
file.previewElement.querySelector(".name").textContent = responseText;
and then refer to this in ajax, but it doesn't look like an elegant approach.
Other alternative would be to create a map with <file, new_name> mapping, but I'm not sure if that's not an overkill.
How would you recommend accessing new file name after upload?
The cleanest option I came up with is using file.xhr.response value which hold the new name instead of file.name
Related
I want to upload multiple file upload.
I have this on client side :
$(document).on( "click", ".save-button", function () {
var data = new FormData();
data.append('title', $(this).parent().parent().find("#title_place").val());
$.each($(this).parent().parent().find("input[type='file']")[0].files, function(i, file) {
data.append('file', file);
});
$.ajax({type: "POST",
url: 'save_view.php',
data: data,
success : viewSaveCallBack,
cache: false,
contentType: false,
processData: false,
});
});
I checked all the data in the debuger, and it is working properly. To see this I displayed the value of
$(this).parent().parent().find("#title_place").val()
And
$(this).parent().parent().find("input[type='file']")[0].files
Then, when I try to var_dump $_FILES or $_POST on server side, it's empty.
Same thing with a debugger.
I tried also with
data.append('files[]', file);
When I try to upload a single file (in another input, not exactly the same code), that is working fine.
The html of the input is this one :
<input type=\"file\" multiple directory webkitdirectory allowdirs class=\"form-control input\" id=\"marzipano\">
And it is added dynamically to the DOM.
When I upload a single file, that is working fine.
It is not a duplicate of Sending multipart/formdata with jQuery.ajax since I already use a FormData object, and my code is the same as the answer. It is still not working as intended.
Try to do:
var files = $(this).parent().parent().find("input[type='file']")[0].files;
for(var i=0; i<files.length; i++) {
data.append('file['+i+']', files[i]);
}
and in PHP you might get files via $_POST["file"]
My code is working actually, problem was that post_max_size in the php.ini was too low.
I want a local file (on the server) to be downloaded by the user. The user first kicks off the file creation by pressing a button and once the file is ready, he should be able to clock on a link or a button to download the file.
Creating the file has not been a problem, as i simply send an AJAX call to my backend which looks like
#POST
#Path("/createFile")
#Produces("application/text")
#Consumes("application/json")
public String createFile(String argsFromPage) {
/*File creation code here*/
return "Path of file created";
}
Now, that the file is created, all I want is to create a link which the user can click and download this file. For now, the file can be either a binary or a CSV file. I have made several attempts but without any success
<button onclick='create_file()'>Create</button>
function create_file() {
$.ajax({
method : "POST",
url : ".path/to/backend/service",
contentType : "application/json",
data : JSON.stringify({
param1 : val1
})
}).done(function(data) {
console.log(data);
});
}
now once the file has been created, is it possible to create a download link? Better still, is it possible to invoke the download as soon as the file is created? Should this be done in the browser, or the back end?
Follow Up
Once the file has been downloaded, how can i delete it form the server? Is there any way to endure that the file download has been completed?
To create a link to the file you can just create an a element in the DOM within the done() handler. Try this:
function create_file() {
$.ajax({
method: "POST",
url: ".path/to/backend/service",
contentType: "application/json",
data: { param1: val1 } // I assume 'val1' is declared in a higher scope?
}).done(function(path) {
$('#someContainer').append('Click here to download');
});
}
Note that I removed the manual JSON.stringify call as jQuery will do this for you. Also note that it would be better to return JSON from the AJAX request as it avoids issues with whitespace, although the above should still work given the code sample you provided.
I'm writing a single page application with EmberJS and need to upload a few files.
I wrote a special view, that wraps the file input field and extracts the first file selected. This lets me bind the File-Object to a model-attribute.
Now I have to choose.
I can write a special file transform, that serialises the File-Object to base64 and simply PUT/POST this.
Or I can intercept the RESTAdapter methods createRecord and updateRecord to check every model for File-Objects and switch the PUT/POST requests to multipart/form-data and send it with the help of FormData
Does one of these directions pose significant problems?
I've had to evaluate the same concern for a Restful API I'm developing. In my opinion, the most ideal method would be to just use the RESTAdapter with base64 encoded data.
That being said, I had to use the multipart/form-data method in my case, because the data transfer is 30% higher when you base64 encode the file data. Since my API would be have to accept large (100MB+) files, I opted to have the POST method of the API to receive multipart form data, with the file and json data being one of the POST variables.
So, unless you need to upload large files like in my case, I'd recommend always sticking to the REST methods.
Just ran into this myself, and ended up using a simple jQuery AJAX call using the FormData object. My multi-select implementation (where one can drop multiple files at once) looks like this:
filesDidChange: function() {
// Get FileList
var $input = this.$('input'),
fileList = $input.get(0).files;
// Iterate files
for (var i = 0; i < fileList.length; i++) {
var file = fileList[i],
formData = new FormData();
// Append information to FormData instance
formData.append('attachment[title]', file.name);
formData.append('attachment[file]', file);
formData.append('attachment[post_id]', this.get('post.id'));
// Send upload request
Ember.$.ajax({
method: 'POST',
url: '/attachments',
cache: false,
contentType: false,
processData: false,
data: formData,
success: makeSuccessHandler(this),
error: makeErrorHandler(this)
});
}
// Notify
this.container.lookup('util:notification').notify('Uploading file, please wait...');
// Clear FileList
$input.val(null);
},
I've been beating my head over this for quite a while now, so I think it's time I reach out for help. I have some already existing code that uses the jQuery File Uploader plugin, allowing me to upload files to my webserver. The trouble I am having is listing files that already exist on the web server.
Here is my initialization code that runs at the client:
$('#fileupload').fileupload({
disableImageResize: false,
url: '/api/upload',
done: function (e, data) { // data is checked here }
});
// Load existing files:
$('#fileupload').addClass('fileupload-processing');
$.ajax({
url: $('#fileupload').fileupload('option', 'url'),
dataType: 'json',
context: $('#fileupload')[0],
data: { action: "FileList", blob: "uts", path: "Unit 14/Binaries/" }
}).always(function (e, data) {
$(this).removeClass('fileupload-processing');
}).done(function (result) {
$(this).fileupload('option', 'done')
.call(this, $.Event('done'), { result: result });
});
Now, I am trying to return a list of pre-existing files on the server side that matches the JSON response akin to the documentation. My ASP.NET code on the server side is as follows (with two bogus files called "Something" and "SomethingElse" using my FilesStatus class).
// Get a list of files from
private void FileList(HttpContext hc)
{
var serializer = new System.Web.Script.Serialization.JavaScriptSerializer();
List<FilesStatus> fs_list = new List<FilesStatus>();
fs_list.Add(new FilesStatus("Something", 124));
fs_list.Add(new FilesStatus("SomethingElse", 124));
HttpContext.Current.Response.AddHeader("Pragma", "no-cache");
HttpContext.Current.Response.AddHeader("Cache-Control", "private, no-cache");
hc.Response.AddHeader("Content-Disposition", "inline; filename=\"files.json\"");
var result = new { files = fs_list.ToArray() };
hc.Response.Write(serializer.Serialize(result));
hc.Response.ContentType = "application/json";
HttpContext.Current.Response.StatusCode = 200;
}
In the "done" function of the AJAX code, I see what I believe is the proper response on the client side. Here, you can see the format in my Javascript debugger (i.e., a top level "files" that is an array):
These files do not get populated in to the file list, though. The code that I marked "//data is checked here" in the main done() function shows that the array can be accessed as "data.result.files" NOT "data.files." I can change ".call(this, $.Event('done'), { result: result });" to ".call(this, $.Event('done'), { files: result.files });" so that "data.files" is the location of the file array, but this does not solve the problem. I can't seem to get any pre-existing files to load in to the list.
Does anyone see what I am doing wrong? Happy holidays.
What happens when you change the line:
hc.Response.Write(serializer.Serialize(result));
into
hc.Response.Write(serializer.Serialize(fs_list.ToArray()));
It looks like the serializer is taking the variable name into account when you are serializing your file descriptions. The 'result' JSON object should disappear from the response.
I was overwriting the done() method where I have:
done: function (e, data) { // data is checked here }
I did this for debugging, but apparently it blocks the pre-existing file list from being loaded and calling the download template.
I can't find a decent example of this anywhere.
Basically have a dropdown list, each option value is the productID and text is the Product name.
I want to post all the selected option values to an action method that will return the respective images on document ready. Image data will the be passed to a function which will update the DOM and then execute the same function everytime a different option from dropdown list is selected to retrieve and change the selected options/product image only.
The action method will return the image for this option/value to the client in an AJAX response, I also want to return the product description too.
Should the response data-type be JSON or do I have to return it in some other way i.e HTTP response with image MIME type?
Something like the below collects all the selected values in an array:
$(document).ready(function () {
var arr = new Array();
$('select option').each(function () {
arr.push($(this).val());
});
// This below will post it off:
$.ajax({
type: "POST",
url: "/System/GetProductImages",
data: { arr: arr },
traditional: true,
success: function (data) {
mydata = data;
OnSuccess(data) // <--- The function that will load/update the images
},
dataType: "json" //<--- ?
});
});
I am not sure how to form the AJAX request correctly so I can request both an image and some text, or is it best to make separate calls when requiring different data types? Maybe I can pack them all in into an array of some sort? Also not to sure how the function that will update the DOM with the retrieved images will look.
I would say that your response should be JSON having and Image ID(a value to identify your image from DB) and Product description. Then using that construct dynamic image elements in HTMl and set their src tag to a URL by passing that image ID as parameter and on server side there should be a handler for your request(like servlet, which reads the Image ID and fetches image stream and returns as response). So, browser make a request for each image and get it rendered on browser. hope it will help you!
You can retrieve the new data using the change event on the select box:
$(document).ready(function(){
$('select').change(function(){
$.ajax({
type: "POST",
url: "/System/GetProductImages",
dataType: 'json',
data: { 'id': $('select').selectedIndex.val() },
traditional: true,
success: function (data) {
mydata = data;
OnSuccess(data) // <--- The function that will load/update the images
}
});
});
});
Additionally, if you're more comfortable with PHP, you could echo out the results from the PHP script and call the load function on change of the select option like so:
/* JQuery code */
$(document).ready(function(){
$('select').change(function(){
$.load("/System/GetProductImages", function(){
// The script to run when a successful load operation takes place
});
});
});
/* PHP Code */
echo "<script>$('tag name').html('value you want to set'); $('img').attr('src','new image src');</script>";
Though I'm not sure calling the script from within PHP is the best solution. You should also keep in mind that the Content-Type response header should be set to "application/json".
If you're using PHP, you can use the json_encode function to return a JSON result. You can read more about the PHP JSON options here - http://php.net/manual/en/function.json-encode.php
Hope this helps.