Menu

PHP Unzip

Because my free webhost places a limit on the number of files that can be uploaded using FTP, I needed to come up with a way to upload an archive and then unzip it on the server. Even if weren’t for the limit, this is still a potentially great idea - when uploading FTP opens a connection to the server for every file it uploads, so uploading an archive file of 25mb is significantly faster than uploading a thousand smaller files that total 25mb for example.

After some googling, I found some code that makes use of PHP’s built in zip file compatability to allow me to upload a zipped archive and along with a single PHP file. My tool first unzips the archive into a folder corresponding to the archive name, then deletes the original archive file and finally deletes itself.

I didn’t write the code below, merely adapted it for my own purposes. Unfortunately I don’t remember where I found it so I’m unable to credit the original author.

The code is below and it’s also available for quick and easy download via the link at the top right of this page. There are more detailed usage instructions at the bottom of the page.

<?php
	if (!isset($_GET['src'])) echo "Usage: unzip.php?src=<em><strong>file.zip</strong></em>";
	else {
		unzipnew($_GET['src']);
		unlink("unzip.php");
	}

	function unzipnew($src_file, $dest_dir=false, $create_zip_name_dir=true, $overwrite=true, $delzip=true) {
		$filecounter = 0;
		echo "<p>Writing files (a count of files written will be at the bottom the page)...</p>";
		if ($zip = zip_open($src_file)) {
			if ($zip) {
				$splitter = ($create_zip_name_dir === true) ? "." : "/";
				if ($dest_dir === false) $dest_dir = substr($src_file, 0, strrpos($src_file, $splitter))."/";
				create_dirs($dest_dir);
				while ($zip_entry = zip_read($zip)) {
					$pos_last_slash = strrpos(zip_entry_name($zip_entry), "/");
					if ($pos_last_slash !== false) {
						create_dirs($dest_dir.substr(zip_entry_name($zip_entry), 0, $pos_last_slash+1));
					}
					if (zip_entry_open($zip,$zip_entry,"r")) {
						$file_name = $dest_dir.zip_entry_name($zip_entry);
						if ($overwrite === true || $overwrite === false && !is_file($file_name)) {
							$fstream = zip_entry_read($zip_entry, zip_entry_filesize($zip_entry));
							@file_put_contents($file_name, $fstream );
							chmod($file_name, 0777);
							echo "File written: ".$file_name."<br />";
							$filecounter++;
						}
						zip_entry_close($zip_entry);
					}
				}
				zip_close($zip);
				if($delzip) unlink($src_file);
				echo "<p>".$filecounter." files written.</p>";
			}
		} else {
			return false;
		}
		return true;
	}

	function create_dirs($path) {
		if (!is_dir($path)) {
			$directory_path = "";
			$directories = explode("/",$path);
			array_pop($directories);
			foreach($directories as $directory) {
				$directory_path .= $directory."/";
				if (!is_dir($directory_path)) {
					mkdir($directory_path);
					@chmod($directory_path, 0777);
				}
			}
		}
	}
?>

Usage instructions:

  1. Save the file as unzip.php (or download it using the link at the top right of this page) and upload it along with the zipped archive you’d like to extract to a folder of your choice.
    For the purposes of an example, let’s say you’re uploading it to the root of your website, foo.com, and the archive you have is named stuff.zip
  2. Once it’s uploaded, open a web-browser and navigate to the unzip.php file, adding the archive filename as a an attribute in the URL named src.
    E.g., foo.com/unzip.php?src=stuff.zip
  3. The files within stuff.zip will be extracted to foo.com/stuff, and any directory structure that existed within the stuff.zip archive is retained.
  4. Both the original archive file, stuff.zip, and the tool itself, unzip.php, are deleted at the end of the process.

Enjoy!

Comments & Discussion