PHP Forums Archive

Ajax upload, free PHP script

Tags: ajax, jquery, javascript, upload form

Posted by Olaf #

While the upload via XMLHttpRequest is not possible are there many examples and tutorials to upload file via some "virtual IFRAME".

upload demoIn this quick tutorial we will show how-to create such an Ajax upload form using the jQuery Form plug-in and our easy upload class. There is also a upload demo page available if you like to have a quick view on how it works. Okay let's start...

The system is very simple, build your upload form just like normal. In place of posting the form to the script you use some JavaScript code to post the data to some PHP script in the background.

Requirements

Download the required files and place the JavaScript files into the same directory as your HTML document and place the following JavaScript code into the HTML header:

<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="jquery.form.js"></script>
<script type="text/javascript">

$(document).ready(function() {
	$("#loading")
	.ajaxStart(function(){
		$(this).show();
	})
	.ajaxComplete(function(){
		$(this).hide();
	});
	var options = {
		beforeSubmit:  showRequest,
		success:       showResponse,
		url:       'upload4jquery.php',  // your upload script
		dataType:  'json'
	};
	$('#Form1').submit(function() {
		document.getElementById('message').innerHTML = '';
		$(this).ajaxSubmit(options);
		return false;
	});
}); 

function showRequest(formData, jqForm, options) {
	var fileToUploadValue = $('input[@name=fileToUpload]').fieldValue();
	if (!fileToUploadValue[0]) {
		document.getElementById('message').innerHTML = 'Please select a file.';
		return false;
	} 

	return true;
} 

function showResponse(data, statusText)  {
	if (statusText == 'success') {
		if (data.img != '') {
			document.getElementById('result').innerHTML = '<img src="/upload/thumb/'+data.img+'" />';
			document.getElementById('message').innerHTML = data.error;
		} else {
			document.getElementById('message').innerHTML = data.error;
		}
	} else {
		document.getElementById('message').innerHTML = 'Unknown error!';
	}
} 

</script>

Next create a PHP script named "upload4jquery.php" and place it in the same directory where other files are located. Place this code into that new file:

<?php
include($_SERVER['DOCUMENT_ROOT'].'/classes/upload/foto_upload_script.php');

$foto_upload = new Foto_upload;	

$json['size'] = $_POST['MAX_FILE_SIZE'];
$json['img'] = '';

$foto_upload->upload_dir = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->foto_folder = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->thumb_folder = $_SERVER['DOCUMENT_ROOT']."/upload/thumb/";
$foto_upload->extensions = array(".jpg", ".gif", ".png");
$foto_upload->language = "en";
$foto_upload->x_max_size = 480;
$foto_upload->y_max_size = 360;
$foto_upload->x_max_thumb_size = 120;
$foto_upload->y_max_thumb_size = 120;

$foto_upload->the_temp_file = $_FILES['fileToUpload']['tmp_name'];
$foto_upload->the_file = $_FILES['fileToUpload']['name'];
$foto_upload->http_error = $_FILES['fileToUpload']['error'];
$foto_upload->rename_file = true; 

if ($foto_upload->upload()) {
	$foto_upload->process_image(false, true, true, 80);
	$json['img'] = $foto_upload->file_copy;
} 

$json['error'] = strip_tags($foto_upload->show_error_string());
echo json_encode($json);
?>

This tutorial or guide is not about how to use the easy upload class. If you never used the class before try the example files first and than start with this Ajax upload form.

Paths and upload directories

You need to create some upload directories (2 one for the upload and one for the thumbs) and check the permission (chmod the upload directory with 777). If you use the same structure as suggested in the class file you don't need to change the include at the top from the PHP script.

Now we need the form HTML and some other containers where the response data is placed.

<form id="Form1" name="Form1" method="post" action="">
    <input type="hidden" name="MAX_FILE_SIZE" value="<?php echo $max_size; ?>" />
    Select an image from your hard disk:

    <div>
        <input type="file" name="fileToUpload" id="fileToUpload" size="18" />
        <input type="Submit" value="Submit" id="buttonForm" />
    </div>
</form>
<img id="loading" src="loading.gif" style="display:none;" />

<p id="message">

<p id="result">

The file loading.gif is the upload indicator image, pick the I used on the demo page or check Google for more stylish images or image generators.

Some final note, the code works as it is. Don't change name or if attributes if you not sure if you use them inside the JavaScript code.

Comments / discussions

Posted by Jet #

Hi Olaf,

As usual, everything works out of the box. The only minor exception being, it seems, that the latest classes zip file now contains an extra file - foto_upload_script.php

The Easy Upload Class plus your instructions above form a very good and complete set of PHP, Mysql Ajax upload scripts.

Thank you Olaf.

Posted by Olaf #

Yes right this file is without the example code, I will split them for good and post an update. Thanks for mentioning.

Posted by 90210 #

include($_SERVER['DOCUMENT_ROOT'].'/classes/upload/foto_upload_script.php');
where can I download this file?

Posted by rizmedh #

@90210
you can download in Easy Upload PHP class..
but the problem, why my image when i upload not showing??
because there are no thumbs that created in my files.
help me.

Posted by rizmedh #

thanks, now its work, i was setting image_magick = false .. =)

Posted by 90210 #

how can I upload media files like .avi and .mpeg instead of picture files?

Posted by Olaf #

Hi,

just add the extension to the code:
$foto_upload->extensions = array(".jpg", ".gif", ".png");

not if you like to show the content after upload you need to change the html too (don't use the image tag for videos)

Posted by bicho44 #

Hi:
Maybe it to much, but can i upload a .zip file, then unzip it and then move to another directory watermarking the image in the way?

I know, i know im a little bit...(you know) but was a question i was having and maybe someone can point me some directions.

TIA

Fede

Posted by Olaf #

Hi,

why do you need to zip that file? is the file so big?

Posted by bicho44 #

Nop, just a bunch of photos, so if you zip them, i think its more easy. Dont you think?

Posted by Olaf #

sure it's faster for the internet user to upload many files at the same time, but you know that handling lots of files at the same time is more resource extensive for the server. Finally it depends on your application.

After upload is done, you need to use some linux commands to expand the zip file. Imagemagicks should help you with the watermarks.

Note that this question is not related to this thread, if you have further questions please start a new thread.

Posted by Snelmer #

i just made the same.. read eveything here.. but when i try to upload something, the screen just blinks and than doesn't upload a thing.

http://snelmer.nl/upload/
(the link)

Posted by Olaf #

??? you're missing the half of your html, If you're new to web-design you should try some basic html tutorials first ;)

Posted by Snelmer #

i didnt put it in a design or so..

and im not new to web-design, only new to php

Posted by Olaf #

Quote from: Snelmer
"i didnt put it in a design or so..
and im not new to web-design, only new to php"

create a FULL and valid html page with all code you need (check the demo two)

look you forgot all JS code too

Posted by the_gnoid #

Thanks, Olaf. This is very useful. I have one question though. Is there supposed to be a thumb and an original size image? I'm only getting the thumb version.

Posted by Olaf #

Quote from: the_gnoid
"Is there supposed to be a thumb and an original size image? I'm only getting the thumb version."

yes right the example creates only one image:

check the settings for this method (inside the class file):

$foto_upload->process_image(false, true, true, 80);

and don't forget to change the values for this vars:

$foto_upload->upload_dir = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->foto_folder = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->x_max_size = 480;
$foto_upload->y_max_size = 360;
$foto_upload->x_max_thumb_size = 120;
$foto_upload->y_max_thumb_size = 120;

Posted by the_gnoid #

So, the temporary file is the original file, then? Makes sense. Thanks!

Posted by Olaf #

Quote from: the_gnoid
"So, the temporary file is the original file, then? Makes sense. Thanks!"

yeah I did that because I needed only one resized file...

Posted by bicho44 #

Hi:

I was testing this tutorial, but i think the json dont return the file info...

You can see my demo at Ajax Test I have to say the scripts works. But never receive the answer from the server (the function "showResponse" never get fired, and i dont know why)

Before this i was test the upload demo and seem to work ok,

Also (trying to make it work) i modify a little the javascript, so its more jquery, but still i never receive an error.

Im using the last jquery (1.2.6) packed, and the last forms plugin too

Do i miss something?

TIA

Fede

Posted by Olaf #

Hi,

just tried your php script and noticed that it didn't give a response.

check all pathes and also the permissions for the upload directory. Your upload page looks fine, you need to debug the upload script.

Posted by bicho44 #

Yup, the script works...

Also i no have the imagemagic and the variable its setted(?) to false... its that a problem?

Its xtrange because the 'showResponse' never get the info, also never get fired(In one of my test i just put an alert to see if something comming from the upload4 script)

Im gonna recheck, but maybe i just use a multiple uploader till i can modify to make a watermark and unzip version :D

Posted by Olaf #

hi,
try the php upload script without using ajax, check if you get the JSON string (response) back

If you switch-off the imagemagick function than it's fine...

Posted by the_gnoid #

What do I add to convert the file type of the thumb? I'm not very familiar with ImageMagick.

Posted by Olaf #

Hi,

I like Imagemagick very much because it's so easy :)

check this page: http://www.imagemagick.org/script/convert.php

don't forget that you have to write some custom code...

and please open a new thread if you have further questions about IM

Posted by yancho #

Hi,

The script is almost working fine, except that what I am having returned is: File: me.jpg successfully uploaded! The uploaded file is renamed to 1225052057.jpg.

I cannot find this file, tried to search my host but to no luck, there are no files in the upload folder :S

These are my paths:

$foto_upload->upload_dir = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->foto_folder = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->thumb_folder = $_SERVER['DOCUMENT_ROOT']."/upload/thumb/"

You can view the page here: http://exigy.solutions-lab.net/admin/news_mgt.php - any help is extremely appreciated

thanks

Matthew

Posted by Olaf #

Hi,

do you "chmod" the upload directoires?

Posted by Olaf #

I see also that the location where the image is shown after upload is differnet from your upload directory:

/files/thumb/1225053135.jpg

Posted by yancho #

Thanks alot for pointing the /files/ thing :)

Was having the file saving to the wrong folder .. now its working fine :)

Thanks alot for your prompt help :)

Btw this : $fileUpload->file_copy .. can be used so that I store the uploaded name to a database right?

$_COOKIE['uploaded_image'] = $fileUpload->file_copy; will do the trick?

Posted by Olaf #

sure you can use this variable in your sql statement (don't know why you use a cookie var...)

Posted by yancho #

hi :)

i tried to pay a bit more with ur script .. however found another problem. when i put the form inside another form both submit buttons are submitting the image not the script. is there any way i can capture the work done by the picture form so i use it with an onclick method please?

http://exigy.solutions-lab.net/admin/edit_news.php

thanks

Posted by Olaf #

Hi, use two forms, simple right?

Posted by yancho #

can't because i need to have the image upload in the middle of the form .. or its not possible?

Posted by Olaf #

A form is just an element like a p, h3 or whatever. It depends on what code you use during upload.

Posted by yancho #

so i can use :

<form id="main_form" action="edit.php"> method="post">
bla bla
  <form id="Form1" name="Form1" method="post" action="">
  </form>
</form>

this is the code i have atm : http://pastebin.ca/1242322

thanks for prompt replies :)

Posted by Olaf #

No, you can't have nested forms. Place them side by side and style (float) them with CSS.

I see that you use tables, don't use them ;)

Posted by corro8 #

hi,
i've been using your easy upload script on many occasions and i think it's great - so many thanks. However, i've just started using a new server and i come up against a problem - whilst everything is fine with the image resizing and renaming etc, it doesn't create and upload a thumbnail copy to the server. Does anyone know why this may be happening?

Posted by Olaf #

Please start a new thread since this question doesn't belong to this thread.

Posted by shbashba #

Hi,

Thank you for the wonderful script. Currently I want to put the script into another form and since there is no such nested forms, I can't use "form1" anymore. So can i change the event to onclick or onchange when the user has choose their files then start passing the jquery function?

Thank you.

Posted by Olaf #

Hello,

check the last posts in this thread (it was asked before)

Posted by nlarnold #

Quote from: bicho44
"Yup, the script works...
Also i no have the imagemagic and the variable its setted(?) to false... its that a problem?
Its xtrange because the 'showResponse' never get the info, also never get fired(In one of my test i just put an alert to see if something comming from the upload4 script)
Im gonna recheck, but maybe i just use a multiple uploader till i can modify to make a watermark and unzip version :D"

Did you every find a resolution for this? I am having the exact same problem. The script uploads and resizes just fine, creates both images, etc., but no response is posted. I, too, tried to just have it put some text to display and the response functions never get called. I'm stumped! Any insight would be greatly appreciated!

Posted by Olaf #

Hi,

if you don't get response (image) I guess your pathes are wrong (at least for the output)

Posted by nat.hagey@gmail.com #

This script is great–but I'm having a hard time installing image magick on leapord running MAMP–any good resources? Or at least a good host that has already imagemagic on it?

Posted by Olaf #

Hi,

I got a shared hosting account from linkdisk.com , they offer directadmin hosting with imagemagicks is enabled. They are very helpful and their server was always online until now ;)

Posted by nat.hagey@gmail.com #

Quote from: Olaf"Hi,
I got a shared hosting account from linkdisk.com , they offer directadmin hosting with imagemagicks is enabled. They are very helpful and their server was always online until now ;)"

Thanks Olaf! I'll look them up.

Posted by andrew_answer #

small fixes needed (at least for Chrome browser which I use):
- first, in upload4jquery.php you should use different dirs:

$foto_upload->upload_dir = $_SERVER['DOCUMENT_ROOT']."/upload/";
$foto_upload->foto_folder = $_SERVER['DOCUMENT_ROOT']."/upload/files/";
$foto_upload->thumb_folder = $_SERVER['DOCUMENT_ROOT']."/upload/thumb/";

- second, you should fix JS showRequest function:

function showRequest(formData, jqForm, options) {
  var fileToUploadValue = document.getElementById('fileToUpload').value;
  if (fileToUploadValue=="") {
    document.getElementById('message').innerHTML = 'Please select a file.';
    return false;
  }
  return true;
}

Posted by Olaf #

Hi,

you say that the "jquery styled" code doesn't work in Chrome?

var fileToUploadValue = $('input[@name=fileToUpload]').fieldValue();

Posted by bt #

Hi
Great code, seems to work after making Chrome changes above although I am on Mac and running Firefox and Safari. Although I get the showRequest results in form page, I do not get anything from showResponse. It uploads the file but it stays quite.

Posted by bt #

Moreover, sometimes thumbs are created sometimes not.
Lastly, where do you control the naming convention for files, I want to give my files the session IDs as names.

Posted by bt #

By the way, I inserted an error object to AJAX request and I keep getting (object Object) as a response from JSON.

Posted by Olaf #

bt, please open a new thread for your questions and please provide us with an URL

Posted by bt #

Olaf

This is running on my local machine so I do not have a URL.

Here is the latest of my script which I saved as upload.js. As you will see, I added an error condition to AJAX request.

$(document).ready(function() {
			$("#loading")
			.ajaxStart(function(){
				$(this).show();
			})
			.ajaxComplete(function(){
				$(this).hide();
			});
			var options = {
				beforeSubmit:  showRequest,
				success:       showResponse,
				url:       'upload4jquery.php',  // your upload script
				dataType:  'json',
				error: function(msg){
				alert( "Houston we have a problem: " + msg );
				}
			};
			$('#Form1').submit(function() {
				document.getElementById('message').innerHTML = '';
				$(this).ajaxSubmit(options);
				return false;
			});
		}); 

		function showRequest(formData, jqForm, options) {
		  var fileToUploadValue = document.getElementById('fileToUpload').value;
		  if (fileToUploadValue=="") {
		    document.getElementById('message').innerHTML = '<img src="images/warning.jpeg" width="15 height="15" /><font color="red">&nbsp; Please select a file.</font>';
		    return false;
		  }
		  return true;
		}
		function showResponse(data, statusText) {
			if (statusText== 'success') {
				if (data.img!= '') {
					document.getElementById('result').innerHTML = '<img src="upload/thumb/'+data.img+'" />';
					document.getElementById('message').innerHTML = data.error;
				} else {
					document.getElementById('message').innerHTML = data.error;
				}
			} else {
				document.getElementById('message').innerHTML = 'Unknown error!';
			}
			/*document.getElementById('message').innerHTML = 'here is what I got';*/

		}

I may send you an email, If you would like more info

Posted by bmorvai #

Hi!

I tried to install on my localhost and on a live server, but i have encountered the same error.
When i try to submit a file, the screen just gives a blink...
Firebug says this after the submit, but disappears very quickly and demands enctype :

[Exception... "'Syntax error, unrecognized expression: [@name=fileToUpload]' when calling method: [nsIDOMEventListener::handleEvent]" nsresult: "0x8057001e (NS_ERROR_XPC_JS_THREW_STRING)" location: "<unknown>" data: no]

Thanks in advance,
scubi

Posted by Olaf #

Hi,

do you tried the upload script without using ajax?

Posted by Olaf #

No I meant the upload script which is used with ajax upload (just upload with form with ajax disabled)

Posted by bmorvai #

The upload works even in ajax version. The problem is that I don't receive any response. Nor the image or error message. Without ajax everything is fine.
I found in the forum that someone has the same error.

Posted by Olaf #

strange, I use the same code on my demo page:
http://www.finalwebsites.com/demos/php_ajax_upload_example.php

do you noticed any difference between both scripts?

Posted by bmorvai #

I started from the beginning using your scripts.

And the reason why I can't get message and the uploaded picture is :

Permission denied to call method Location.toString

It has to do something with the links, hasn't it?

thanks for your time

Posted by Olaf #

Try the client side code from the demo I posted before together with the file PHP (and other) files from the tutorial. I think that the demo works fine?

Posted by bmorvai #

Hi!

I had problems of the response because of the json library. I would advice for others having the same problem, to check php version and json. After 5.2 json is integrated, but you can install to earlier versions too.

And now other question, how could I implement button to delete uploaded image running without page refresh?

thx

Posted by Olaf #

The JSON function in PHP is very simple, there are alternative functions in the PHP manual for PHP versions lower than 5.2.

Please start a new thread for your new question.

Posted by sladda #

nice script, works fine.
But tell me please: i want to extend this script a bit, but just adding an echo somewhere, produces problems.
I want to have the hole path of the uploaded file (got it already in a var) and want to read it then with phpExcelReader. Ive already written this XLS-Read-Script and it works, but i cant connect the upload script with my excel-read-script. if i past any code at the (i think) right position, the upload doesnt work anymore :(

Some Help!?
Thanks a lot
Greetz
Sladda

Posted by Olaf #

Hi,

first of all start uploading without Ajax. the upload script works find step over to the ajax part (ajax is just some client stuff).

Please open a new thread if you need further help.