I've got a problem sending a file to a serverside PHP-script using jQuery's ajax-function.
It's possible to get the File-List with $('#fileinput').attr('files')
but how is it possible to send this Data to the server? The resulting array ($_POST
) on the serverside php-script is 0 (NULL
) when using the file-input.
I know it is possible (though I didn't find any jQuery solutions until now, only Prototye code (http://webreflection.blogspot.com/2009/03/safari-4-multiple-upload-with-progress.html)).
This seems to be relatively new, so please do not mention file upload would be impossible via XHR/Ajax, because it's definitely working.
I need the functionality in Safari 5, FF and Chrome would be nice but are not essential.
My code for now is:
$.ajax({
url: 'php/upload.php',
data: $('#file').attr('files'),
cache: false,
contentType: 'multipart/form-data',
processData: false,
type: 'POST',
success: function(data){
alert(data);
}
});
One gotcha I ran into today I think is worth pointing out related to this problem: if the url for the ajax call is redirected then the header for content-type: 'multipart/form-data' can be lost.
For example, I was posting to http://server.com/context?param=x
In the network tab of Chrome I saw the correct multipart header for this request but then a 302 redirect to http://server.com/context/?param=x (note the slash after context)
During the redirect the multipart header was lost. Ensure requests are not being redirected if these solutions are not working for you.
Nova days you not need even jQuery:) fetch API support table
All the solutions above are looks good and elegant, but the FormData() object does not expect any parameter, but use append() after instantiate it, like what one wrote above:
formData.append(val.name, val.value);
Just wanted to add a bit to Raphael's great answer. Here's how to get PHP to produce the same
$_FILES
, regardless of whether you use JavaScript to submit.HTML form:
PHP produces this
$_FILES
, when submitted without JavaScript:If you do progressive enhancement, using Raphael's JS to submit the files...
... this is what PHP's
$_FILES
array looks like, after using that JavaScript to submit:That's a nice array, and actually what some people transform
$_FILES
into, but I find it's useful to work with the same$_FILES
, regardless if JavaScript was used to submit. So, here are some minor changes to the JS:(14 April 2017 edit: I removed the form element from the constructor of FormData() -- that fixed this code in Safari.)
That code does two things.
input
name attribute automatically, making the HTML more maintainable. Now, as long asform
has the class putImages, everything else is taken care of automatically. That is, theinput
need not have any special name.With these changes, submitting with JavaScript now produces precisely the same
$_FILES
array as submitting with simple HTML.Devin Venable's answer was close to what I wanted, but I wanted one that would work on multiple forms, and use the action already specified in the form so that each file would go to the right place.
I also wanted to use jQuery's on() method so I could avoid using .ready().
That got me to this: (replace formSelector with your jQuery selector)
The FormData class does work, however in iOS Safari (on the iPhone at least) I wasn't able to use Raphael Schweikert's solution as is.
Mozilla Dev has a nice page on manipulating FormData objects.
So, add an empty form somewhere in your page, specifying the enctype:
Then, create FormData object as:
and proceed as in Raphael's code.