I try to create a ZIP file with PHP. Inside this ZIP files I want to add multiple PDF files.
My code
$actual_link = "https://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
$parts = parse_url($actual_link);
parse_str($parts['query'], $query);
$downloads = json_decode($query["downloads"]);
$files = array();
foreach ($downloads as $download) {
array_push($files, "https://website.com/downloads/". $download->value .".pdf");
}
# create new zip object
$zip = new ZipArchive();
# create a temp file & open it
$tmp_file = tempnam('.', '');
$zip->open($tmp_file, ZipArchive::CREATE);
# loop through each file
foreach ($files as $file) {
# download file
$download_file = file_get_contents($file);
#add it to the zip
$zip->addFromString(basename($file), $download_file);
}
;
# close zip
$zip->close();
# send the file to the browser as a download
header('Content-disposition: attachment; filename="test.zip"');
header('Content-type: application/zip');
readfile($tmp_file);
unlink($tmp_file);
The ZIP file downloads fine, but my PDF files have 0kb and no content....
Do you find the error?
Related
I have written this code to download files after adding them in a zip file. However, my code removes the files which have the same name ( duplicate ).
<?php
# define file array
$files = array(
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Physics.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Physics.PDF',
);
# create new zip object
$zip = new ZipArchive();
# create a temp file & open it
$tmp_file = tempnam('.', '');
$zip->open($tmp_file, ZipArchive::CREATE);
# loop through each file
foreach ($files as $file) {
# download file
$download_file = file_get_contents($file);
#add it to the zip
$zip->addFromString(basename($file), $download_file);
}
# close zip
$zip->close();
# send the file to the browser as a download
header('Content-disposition: attachment; filename="my file.zip"');
header('Content-type: application/zip');
readfile($tmp_file);
unlink($tmp_file);
?>
So my question is,
How can I download duplicate files from an array?
or
How can I change the names of duplicate files?
Just rename your files.
<?php
# define file array
$files = array(
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Physics.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Physics.PDF',
);
# create new zip object
$zip = new ZipArchive();
# create a temp file & open it
$tmp_file = tempnam('.', '');
$zip->open($tmp_file, ZipArchive::CREATE);
// Variable to Keep Filenames
$filename = '';
// Variable to add "-1, -2" to duplicate files
$i = 1;
# loop through each file
foreach ($files as $file) {
# download file
$download_file = file_get_contents($file);
if ( $filename == basename($file) )
{
// If this file already exists add "-1, -2"
$filename = $i . '-' . basename($file);
$i++;
} else
{
$filename = basename($file);
$i = 1;
}
#add it to the zip
$zip->addFromString($filename, $download_file);
}
# close zip
$zip->close();
# send the file to the browser as a download
header('Content-disposition: attachment; filename="my file.zip"');
header('Content-type: application/zip');
readfile($tmp_file);
unlink($tmp_file);
?>
Edit after #RiggsFolly Comment to support out of order duplicate files
<?php
# define file array
$files = array(
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Chemistry.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2018/SSC-II/Physics.PDF',
'https://www.fbise.edu.pk/Old%20Question%20Paper/2017/SSC-II/Physics.PDF',
);
# create new zip object
$zip = new ZipArchive();
# create a temp file & open it
$tmp_file = tempnam('.', '');
$zip->open($tmp_file, ZipArchive::CREATE);
// Array to keep filenames
$filenames = array();
# loop through each file
foreach ($files as $file) {
# download file
$download_file = file_get_contents($file);
if( array_key_exists( basename($file), $filenames ) )
{
$filename = $filenames[basename($file)] . '-' . basename($file);
$filenames[basename($file)] = $filenames[basename($file)] + 1;
} else
{
$filename = basename($file);
$filenames[basename($file)] = 1;
}
#add it to the zip
$zip->addFromString($filename, $download_file);
}
# close zip
$zip->close();
# send the file to the browser as a download
header('Content-disposition: attachment; filename="my file.zip"');
header('Content-type: application/zip');
readfile($tmp_file);
unlink($tmp_file);
?>
How can I download multiple files as a zip-file using php?
You can use the ZipArchive class to create a ZIP file and stream it to the client. Something like:
$files = array('readme.txt', 'test.html', 'image.gif');
$zipname = 'file.zip';
$zip = new ZipArchive;
$zip->open($zipname, ZipArchive::CREATE);
foreach ($files as $file) {
$zip->addFile($file);
}
$zip->close();
and to stream it:
header('Content-Type: application/zip');
header('Content-disposition: attachment; filename='.$zipname);
header('Content-Length: ' . filesize($zipname));
readfile($zipname);
The second line forces the browser to present a download box to the user and prompts the name filename.zip. The third line is optional but certain (mainly older) browsers have issues in certain cases without the content size being specified.
This is a working example of making ZIPs in PHP:
$zip = new ZipArchive();
$zip_name = time().".zip"; // Zip name
$zip->open($zip_name, ZipArchive::CREATE);
foreach ($files as $file) {
echo $path = "uploadpdf/".$file;
if(file_exists($path)){
$zip->addFromString(basename($path), file_get_contents($path));
}
else{
echo"file does not exist";
}
}
$zip->close();
Create a zip file, then download the file, by setting the header, read the zip contents and output the file.
http://www.php.net/manual/en/function.ziparchive-addfile.php
http://php.net/manual/en/function.header.php
You are ready to do with php zip lib,
and can use zend zip lib too,
<?PHP
// create object
$zip = new ZipArchive();
// open archive
if ($zip->open('app-0.09.zip') !== TRUE) {
die ("Could not open archive");
}
// get number of files in archive
$numFiles = $zip->numFiles;
// iterate over file list
// print details of each file
for ($x=0; $x<$numFiles; $x++) {
$file = $zip->statIndex($x);
printf("%s (%d bytes)", $file['name'], $file['size']);
print "
";
}
// close archive
$zip->close();
?>
http://devzone.zend.com/985/dynamically-creating-compressed-zip-archives-with-php/
and there is also php pear lib for this
http://www.php.net/manual/en/class.ziparchive.php
currently I am trying to put files in a zip and download them. I use the following code:
# create new zip opbject
$zip = new ZipArchive();
# create a temp file & open it
$tmp_file = tempnam('.','');
$zip->open($tmp_file, ZipArchive::CREATE);
# loop through each file
foreach($files as $file){
# download file
$download_file = file_get_contents($file);
#add it to the zip
$zip->addFromString(basename($file),$download_file);
}
# close zip
$zip->close();
# send the file to the browser as a download
header('Content-disposition: attachment; filename=Resumes.zip');
header('Content-type: application/zip');
readfile($tmp_file);
The files are added to the array the following way:
$weborder = $_POST['weborder'];
$printlocation = $_POST['print'];
$dir = "z:\Backup\\$printlocation\\$weborder.zip";
$zip = new ZipArchive;
$files = array();
if ($zip->open($dir))
{
for($i = 0; $i < $zip->numFiles; $i++)
{
if ($zip->getNameIndex($i) != "order-info.txt" && $zip->getNameIndex($i) != "workrequest.xml" && $zip->getNameIndex($i) != "workrequest.pdf")
{
$filename = $zip->getNameIndex($i);
$files[$i] = $dir . "\\" . $filename;
}
}
}
This downloads the zip and the files that are in the zip. The only problem I am having is that the files are empty.
instead of
$zip->addFromString(basename($file),$download_file);
try
$zip->addFile($basename($file));
This code is working make sure that your files are existed or not.
$array = array("sites/README.txt","sites/chessboard.jpg"); //files to Add/Create in zip file
$zip = new ZipArchive(); // Load zip library
$zip_name = time().".zip"; // Zip name
if($zip->open($zip_name, ZIPARCHIVE::CREATE)!==TRUE)
{
// Opening zip file to load files
$error .= "* Sorry ZIP creation failed at this time";
}
foreach($array as $key => $value)
{
if(file_exists($value)){
$zip->addFile($value); // Adding files into zip
}else{echo $value ." file not exist<br/>";}
}
$zip->close();
if(file_exists($zip_name))
{
echo "yes";die;
// push to download the zip
header('Content-type: application/zip');
header('Content-Disposition: attachment; filename="'.$zip_name.'"');
readfile($zip_name);
// remove zip file is exists in temp path
unlink($zip_name);
}else{echo "zip not created";die; }
For Download Existing file
$zip_name = "YOUR_ZIP_FILE PATH";
if(file_exists($zip_name))
{
// push to download the zip
header('Content-type: application/zip');
header('Content-Disposition: attachment; filename="'.$zip_name.'"');
readfile($zip_name);
// remove zip file is exists in temp path
//unlink($zip_name);
}else{
echo "zip not created";exit;
}
I have lots of files in a particular Directory. In a certain PHP page I lists the contents of the particular directory with links to download each item separately. Now I need to display a Link which will ZIP all the contents of that directory so any visitor can download all the contents as a Single ZIP file.
Use ZipArchive for zipping files and RecursiveDirectoryIterator for getting all files in a directory
something like
$zipfilename = <zip filename>;
$zip = new ZipArchive();
$zip->open($zipfilename, ZipArchive::CREATE);
// add all files in directory to zip
foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator('path/to/files/')) as $filename) {
$zip->addFile($filename);
}
$zip->close();
Then send the zip to the browser
header('Content-Type: application/zip');
header('Content-disposition: attachment; filename="'. $zipfilename .'"');
header('Content-Length: ' . filesize($zipfilename));
readfile($zipfilename);
Obviously you could post the directory name and event the zip file name to the script but it gives you a starting point
Try this
$files = array('file1.txt', 'file2.txt', 'file3.txt');
$zip = new ZipArchive;
$zip->open('file.zip', ZipArchive::CREATE);
foreach ($files as $file) {
$zip->addFile($file);
}
$zip->close();
How can I download multiple files as a zip-file using php?
You can use the ZipArchive class to create a ZIP file and stream it to the client. Something like:
$files = array('readme.txt', 'test.html', 'image.gif');
$zipname = 'file.zip';
$zip = new ZipArchive;
$zip->open($zipname, ZipArchive::CREATE);
foreach ($files as $file) {
$zip->addFile($file);
}
$zip->close();
and to stream it:
header('Content-Type: application/zip');
header('Content-disposition: attachment; filename='.$zipname);
header('Content-Length: ' . filesize($zipname));
readfile($zipname);
The second line forces the browser to present a download box to the user and prompts the name filename.zip. The third line is optional but certain (mainly older) browsers have issues in certain cases without the content size being specified.
This is a working example of making ZIPs in PHP:
$zip = new ZipArchive();
$zip_name = time().".zip"; // Zip name
$zip->open($zip_name, ZipArchive::CREATE);
foreach ($files as $file) {
echo $path = "uploadpdf/".$file;
if(file_exists($path)){
$zip->addFromString(basename($path), file_get_contents($path));
}
else{
echo"file does not exist";
}
}
$zip->close();
Create a zip file, then download the file, by setting the header, read the zip contents and output the file.
http://www.php.net/manual/en/function.ziparchive-addfile.php
http://php.net/manual/en/function.header.php
You are ready to do with php zip lib,
and can use zend zip lib too,
<?PHP
// create object
$zip = new ZipArchive();
// open archive
if ($zip->open('app-0.09.zip') !== TRUE) {
die ("Could not open archive");
}
// get number of files in archive
$numFiles = $zip->numFiles;
// iterate over file list
// print details of each file
for ($x=0; $x<$numFiles; $x++) {
$file = $zip->statIndex($x);
printf("%s (%d bytes)", $file['name'], $file['size']);
print "
";
}
// close archive
$zip->close();
?>
http://devzone.zend.com/985/dynamically-creating-compressed-zip-archives-with-php/
and there is also php pear lib for this
http://www.php.net/manual/en/class.ziparchive.php