Best practices for image uploading and resizing

I made a script for uploading and resizing images that uses the php commands move_uploaded_file() and imagecopyresampled(). It works. Sort of…

The problem I’ve been having is that it hangs from time to time. Especially on images with larger image dimensions. I believe the server is running out of memory during resizing.

Its on a shared hosting platform on Dreamhost. It might be that it doesn’t allow enough execution time. The really annoying thing is that it just kills the process. It doesn’t return any errors.

The current resizes the image 3 times. IE:
saveAndResize($img,100);
saveAndResize($img,350);
saveAndResize($img,1200);

Is there a way of submitting the process and if it times out return an error or re-run it? Is there a better way of resizing images. Maybe using Perl for example.

Thanks E

[SIZE=3]You can do something like:

set_time_limit(180);
ini_set(‘memory_limit’, ‘512M’);[/SIZE]

tinySrc

After saving each resized image, are you using imagedestroy() to freeup the memory that was used during the resizing of an image?

saveAndResize($img,100);
saveAndResize($img,350);
saveAndResize($img,1200);

Are those 3 commands all using a high resolution source file?
Why not go in reverse order (biggest to smallest) and use the result of the previous operation to make the smaller size.

All Excellent comments. I’m going to take a look at my code and adjust.

Thanks!!
E

For any serious and reliable image manipulation I advise against usigng imagecopyresampled() or any other gd functions. Use Imagemagick - a much more advanced image processing application. It will resize your images faster and as a bonus you will get better image quality if you set it up properly.

You only need to check if imagemagick is available at your host. Most good hosts nowadays have it. Personally, if I plan to do any image processing in php then I first check availability of IM and I refuse to do my work on a host that doesn’t provide it - moving to another (better) host is so easy today that it’s not really a problem.

Well first of all you should put a cap on image DIMENSIONS besizes the filesize; say maximum 1024x768 pixels. Or even better, put a cap on the number of pixels in the image. This is because user might upload images with arbitrary aspect ratio, e.g. 768x1024 which should be allowed. So here is how you check if the image is 5 megapixels or less:


list($source_image_width, $source_image_height, $source_image_type) = getimagesize($source_image_path);

if ($source_image_width * $source_image_height > 5*1000*1000) {
   die("Images more than 5MP are not allowed");
}
else {
    // resize
}

Also go through the code that does the resizing, make sure it destroys the image before attempting to perform another resize.

Using imagemagick addressed the problem with large dimension files.
It easily handled a 42mp image.

imagemagick didn’t show up as available in phpinfo() on my host and instantiating it didn’t work. So I had assumed it wasn’t available. It turns out it was.

For anyone using Dreamhost, this how to use imagemagick on there shared hosting platform:

 
  	//Image Magick !!

	// Set the path to where the ImageMagick program is on your server 
	$path_imagemagick="/usr/bin/"; 
	// Set the path and filename to the picture 
	$path_picture=$file;  
	// Set the path and filename to where the thumb will be created 
	$path_thumb=$_SERVER['DOCUMENT_ROOT'].'/images/'.$directory.$filename; 
	// Set the largest dimension of the thumbnail (width for landscape and height for portraits) 
	$thumbnail_size=$size; 
	// Set umask to 0 in order not to affect the file permissions during the next operation 
	umask(000); 
	// Execute the shell command that calls Image Magick with the proper parameters (as set above) 
	$ok=shell_exec($path_imagemagick."convert -size $thumbnail_size $path_picture -quality 70% -geometry $thumbnail_size $path_thumb");  

Unfortunately, I am getting reports of stalling from pdf files. Maybe changing the timeout setting like
speda1 recommended will fix this. I keep testing it but can’t produce this error.

Hopefully you are using extra escaping before passing the filename to shell_exec, otherwise a malformed file name could execute malicious shell commands.

Good point, yes actually I use this inside a function. The file name is passed to it in a clean format.