PHP Zip files and directory

Sometimes you require zipping a file or even an entire directory at your server with PHP. The best way is to use ZipArchive class to do it. If you have PHP 5.2 or later version installed on your server and if zip library is enabled then ZipArchive class will be available to you. This class has lots of useful member function which makes easier in zipping files.

How to use ZipArchive class in PHP

Like any other classes first you have to create an object of ZipArchive class to use its public member functions.
$zip-> new ZipArchive();

PHP create zip file

After creating an object of ZipArchive class now you can create a new zip file. The member function open() is used to create a new zip file or to open an existing zip archive.

Code | Download
$filename='backup.zip';
if(($zip->open($filename, ZipArchive::CREATE))!==true){ die('Error: Unable to create zip file');}

Please remember if the file 'backup.zip' already exists this function will open the existing file.

Adding files inside a zip archive

To add a new file inside a zip archive use member function
addFile('realname',['saveAs']).
As you can see this function takes two arguments, one is the 'realname', i.e. name of the file to be added and other is the optional argument 'saveAs'. The 'saveAs' parameter is the name of the file by which you want to add it inside the zip archive. If you omit this parameter the file will be saved by its real name. The importance of this parameter can be explained by the following example.

Code | Download
<?php
//File to be added inside zip archive.
$file='/home/domain/public_html/example.txt';
//Open zip archive.
$zip-> new ZipArchive();
if(($zip->open('test.zip', ZipArchive::CREATE))!==true){ die('Error: Unable to create zip file');}
//Add file by its real name.
$zip->addFile($file);
//Add the same file with different name say, 'newname.txt'.
$zip->addFile($file,'newname.txt');
//Close zip archive.
$zip->close();
//Download zip file.
header("Location: test.zip");
exit;
?>

After running this script you will be prompted to download test.zip file. Save this file at your computer desktop and open it. You will see the file 'newname.txt' is at the root of your zip archive while the file 'example.txt' resides inside directories '/home/domain/public_html/'.

Closing an open zip archive

In the above example I use a new member function close(). This function is used to close an open zip archive. Although PHP will automatically close it at the end of the script but you should do it yourself.

Zip a directory in PHP

You can insert a complete directory, all files and subdirectory in it into a zip archive by PHP. The most efficient way is to use a recursive program to do it. Below, I write a recursive function which can zip a directory.

Code | Download
function recurse_zip($src,&$zip,$path_length) {
        $dir = opendir($src);
        while(false !== ( $file = readdir($dir)) ) {
            if (( $file != '.' ) && ( $file != '..' )) {
                if ( is_dir($src . '/' . $file) ) {
                    recurse_zip($src . '/' . $file,$zip,$path_length);
                }
                else {
                    $zip->addFile($src . '/' . $file,substr($src . '/' . $file,$path_length));
                }
            }
        }
        closedir($dir);
}
//Call this function with argument = absolute path of file or directory name.
function compress($src)
{
        if(substr($src,-1)==='/'){$src=substr($src,0,-1);}
        $arr_src=explode('/',$src);
        $filename=end($src);
        unset($arr_src[count($arr_src)-1]);
        $path_length=strlen(implode('/',$arr_src).'/');
        $f=explode('.',$filename);
        $filename=$f[0];
        $filename=(($filename=='')? 'backup.zip' : $filename.'.zip');}
        $zip = new ZipArchive;
        $res = $zip->open($filename, ZipArchive::CREATE);
        if($res !== TRUE){
                echo 'Error: Unable to create zip file';
                exit;}
        if(is_file($src)){$zip->addFile($src,substr($src,$path_length));}
        else{
                if(!is_dir($src)){
                     $zip->close();
                     @unlink($filename);
                     echo 'Error: File not found';
                     exit;}
        recurse_zip($src,$zip,$path_length);}
        $zip->close();
        header("Location: $filename");
        exit;
}
User comments:

Why variable pass by reference

COMMENT BY: Reazool DATE: Dec 18, 00:58
Why variable $zip pass by reference in function recurse_zip? Is it mandatory?

Pointer variables always pass by reference

COMMENT BY: admin DATE: Dec 18, 01:03

A function can accept arguments in two ways; either by value or by reference. When you pass argument by value a copy of original data is sent to the function. During processing function can alter that data, but the original data remains unchanged. On the other hand when you pass data by reference (by using '&' before the argument of the function statement) the memory address of the original data is sent to the function. Here during function works on original data. In recurse_zip() function we need to handle the original zip file open by ZipArchive class object $zip. So here I pass the $zip pointer by reference. In short you should remember that all pointer data (like $handle from fopen function) always pass through reference.

How to store zipped directory in another folder

COMMENT BY: sheetal DATE: Jul 06, 01:30
Hello,

I have used script for creating zip directory.
Nice script.
However ,I want to store zipped directory in another folder.Now, its saving zipped directory in same folder.
What changes have to do in the script so that zipped directory will store in another directory?

Ur help is required.

Thanks,
Sheetal

Re: How to store zipped directory in another folder

COMMENT BY: admin DATE: Jul 07, 08:18
Hello,
Thank you for your interest. If you want to store in different directory then you have to modify the variable $filename. In function compress() see the lines,
$filename=(($filename=='')? 'backup.zip' : $filename.'.zip');}
$zip = new ZipArchive;
Replace them,
Code:
$filename=(($filename=='')? 'backup.zip' : $filename.'.zip');}
$yourpath='newfolder/';//or $yourpath='../newfolder/';
$filename=$yourpath.$filename;
$zip = new ZipArchive;
------------------
**Please give me feedback

Undefined var

COMMENT BY: JStern DATE: Jul 07, 12:24
your line $f=explode('/',$filename); breaks. $filename is not declared yet.

Re: Undefined var

COMMENT BY: admin DATE: Jul 07, 13:19
Thank you for mentioning this error. I already rectify it.
Thank you very much.

Add comment

RAMUI WEBBLOG
HomeAboutContact SitemapTerms of useXMLForum
© 2010,  http://ramui.com   All rights reserved.
Powered by: ramui webblog® Version 1.0