File does not exist while downloading Zip file in Laravel - php

I'm getting error as the "file does not exist" as folder does exist.
The file "../storage/app/public/bks/case_1/XsIbdGSJow7O3fhq9LyU.zip" does not exist
I have checked with Database field name zipname is not present but job_id is present. I'm not sure but do we have to have field name as zipname present in Database for this to download.
public function downloadZip(Request $request)
{
#$job_id = $request->job_id;
#$filenames = DB::table('analytics_report')->where('job_id',$job_id)->get()->pluck('filename')->toArray();
#$zipname = $request->job_id;
$zip = new \ZipArchive;
$zip->open($zipname, \ZipArchive::CREATE);
foreach ($filenames as $filename){
$zip->addFile($filename);
}
$zip->close;
#$path = '../storage/app/public/bks/case_1/'.$zipname;
return response()->download($path);
}
Thanks!

You have a typo here $zip->close;. Should be $zip->close();
Your code needs some checks before everything else.
public function downloadZip(Request $request)
{
if($request->has("job_id") === false) return;
$job_id = $request->job_id;
$filenames = DB::table('analytics_report')
->where('job_id',$job_id)
->get()
->pluck('filename')
->toArray();
if (count($filenames) == 0) return;
$zipname = $request->job_id;
$zip = new \ZipArchive;
$zip->open($zipname, \ZipArchive::CREATE);
foreach ($filenames as $filename){
$zip->addFile($filename);
}
$zip->close();
$path = stprage_path('app/public/storage/bks/case_1/'.$zipname);
return response()->download($path);
}

Related

laravel return download creates extra file

I'm using following codes to create zip file in Laravel:
$files = Answer::where('questionid', $questionId)
->pluck('answer')
->all();
$zip = new ZipArchive;
$zip_name = time() . "_$questionId" . ".zip";
if ($zip->open(storage_path($zip_name), ZipArchive::CREATE) === true) {
foreach ($files as $file) {
$relativeNameInZipFile = explode('/', $file)[3];
$zip->addFile(Storage::path($file), $relativeNameInZipFile);
}
$zip->close();
}
return Storage::download($zip_name);
It works properly.But when the last line of the code that returns file to download create an extra zip file in the storage!
return Storage::download($zip_name);
Why!!??

PHP Create a Zip archive for file only particular extension

How to create Zip archive for file only particular extension in my case .TIF .JPG .TXT
currently i have added single extensions in code you can modify it later on.
<?php
/* creates a compressed zip file */
function create_zip($files = array(), $destination = '', $overwrite = false) {
//if the zip file already exists and overwrite is false, return false
if (file_exists($destination) && !$overwrite) {
return false;
}
//vars
$valid_files = array();
//if files were passed in...
if (is_array($files)) {
//cycle through each file
foreach ($files as $file) {
//make sure the file exists
if (file_exists($file)) {
$valid_files[] = $file;
}
}
}
//if we have good files...
if (count($valid_files)) {
//create the archive
$zip = new ZipArchive();
if ($zip->open($destination, $overwrite ? ZIPARCHIVE::OVERWRITE : ZIPARCHIVE::CREATE) !== true) {
return false;
}
//add the files
foreach ($valid_files as $file) {
$zip->addFile($file, $file);
}
//debug
//echo 'The zip archive contains ',$zip->numFiles,' files with a status of ',$zip->status;
//close the zip -- done!
$zip->close();
//check to make sure the file exists
return file_exists($destination);
} else {
return false;
}
}
//your directory path where all files are stored
$dir = 'D:\xampp\htdocs\samples\zip';
$files1 = scandir($dir, 1);
// $ext = "png"; //whatever extensions which you want to be in zip.
$ext = ['jpg','tif','TXT']; //whatever extensions which you want to be in zip.
$finalArray = array();
foreach ($files1 as $key => $value) {
$getExt = explode(".", $value);
if ( in_array($getExt[1] , $ext) ) {
$finalArray[$key] = $value;
}
}
$result = create_zip($finalArray, 'my-archive' . time() . '.zip');
if ($result) {
echo "Operation done.";
}
?>
i think this is what you want.
let me know if you have any issue.

create and download zip file using php

i am trying to create a zip file(using php) for this i have written the following code:
$fileName = "1.docx,2.docx";
$fileNames = explode(',', $fileName);
$zipName = 'download_resume.zip';
$resumePath = asset_url() . "uploads/resume/";
//http://localhost/mywebsite/public/uploads/resume/
$zip = new ZipArchive();
if ($zip->open($zipName, ZIPARCHIVE::CREATE) !== TRUE) {
echo json_encode("Cannot Open");
}
foreach ($fileNames as $files) {
$zip->addFile($resumePath . $files, $files);
}
$zip->close();
header("Content-type: application/zip");
header("Content-Disposition: attachment; filename=".$zipName."");
header("Content-length: " . filesize($zipName));
header("Pragma: no-cache");
header("Expires: 0");
readfile($zipName);
exit;
however on a button click i am not getting anything..not even any error or message..
any help or suggestion would be a great help for me.. thanks in advance
Why not use the Zip Encoding Class in Codeigniter - it will do this for you
$name = 'mydata1.txt';
$data = 'A Data String!';
$this->zip->add_data($name, $data);
// Write the zip file to a folder on your server. Name it "my_backup.zip"
$this->zip->archive('/path/to/directory/my_backup.zip');
// Download the file to your desktop. Name it "my_backup.zip"
$this->zip->download('my_backup.zip');
https://www.codeigniter.com/user_guide/libraries/zip.html
... it work for me
public function downloadall(){
$createdzipname = 'myzipfilename';
$this->load->library('zip');
$this->load->helper('download');
$cours_id = $this->input->post('todownloadall');
$files = $this->model_travaux->getByID($cours_id);
// create new folder
$this->zip->add_dir('zipfolder');
foreach ($files as $file) {
$paths = 'http://localhost/uploads/'.$file->file_name.'.docx';
// add data own data into the folder created
$this->zip->add_data('zipfolder/'.$paths,file_get_contents($paths));
}
$this->zip->download($createdzipname.'.zip');
}
What is asset_url() function? Try to use APPPATH constant istead this function:
$resumePath = APPPATH."../uploads/resume/";
Add "exists" validation for file names:
foreach ($fileNames as $files) {
if (is_file($resumePath . $files)) {
$zip->addFile($resumePath . $files, $files);
}
}
Add exit() after:
echo json_encode("Cannot Open");
Also I think it's the better desision to use CI zip library User Guide. Simple example:
public function generate_zip($files = array(), $path)
{
if (empty($files)) {
throw new Exception('Archive should\'t be empty');
}
$this->load->library('zip');
foreach ($files as $file) {
$this->zip->read_file($file);
}
$this->zip->archive($path);
}
public function download_zip($path)
{
if (!file_exists($path)) {
throw new Exception('Archive doesn\'t exists');
}
$this->load->library('zip');
$this->zip->download($path);
}
Below scripting working ok in my local system. 1st remove asset_url() from $resumePath and set zip file store location relative path.
- Pass zip file name with its location path to $zip->open()
$fileName = "1.docx,2.docx";
$fileNames = explode(',', $fileName);
$zipName = 'download_resume.zip';
$resumePath = "resume/";
$zip = new ZipArchive();
if ($zip->open($resumePath.$zipName, ZIPARCHIVE::CREATE) !== TRUE) {
echo json_encode("Cannot Open");
}
foreach ($fileNames as $files) {
$zip->addFile($files, $files);
}
$zip->close();
/* create zip folder */
public function zip(){
$getImage = $this->cart_model->getImage();
$zip = new ZipArchive;
$auto = rand();
$file = date("dmYhis",strtotime("Y:m:d H:i:s")).$auto.'.zip';
if ($zip->open('./download/'.$file, ZipArchive::CREATE)) {
foreach($getImage as $getImages){
$zip->addFile('./assets/upload/photos/'.$getImages->image, $getImages->image);
}
$zip->close();
$downloadFile = $file;
$download = Header("Location:http://localhost/projectname/download/".$downloadFile);
}
}
model------
/* get add to cart image */
public function getImage(){
$user_id = $this->session->userdata('user_id');
$this->db->select('tbl_cart.photo_id, tbl_album_image.image as image');
$this->db->from('tbl_cart');
$this->db->join('tbl_album_image', 'tbl_album_image.id = tbl_cart.photo_id', 'LEFT');
$this->db->where('user_id', $user_id);
return $this->db->get()->result();
}

zip generating function generating blank files

I am using this function to generate zip files:
function create_zip($files = array(),$destination = '',$overwrite = false) {
//if the zip file already exists and overwrite is false, return false
if(file_exists($destination) && !$overwrite) { return false; }
//vars
$valid_files = array();
//if files were passed in...
if(is_array($files)) {
//cycle through each file
foreach($files as $file) {
//make sure the file exists
if(file_exists($file)) {
$valid_files[] = $file;
}
}
}
//if we have good files...
if(count($valid_files)) {
//create the archive
$zip = new ZipArchive();
if($zip->open($destination,$overwrite ? ZIPARCHIVE::OVERWRITE : ZIPARCHIVE::CREATE) !== true) {
return false;
}
//add the files
foreach($valid_files as $file) {
$zip->addFile($file,$file);
//echo $file;
}
//debug
//echo 'The zip archive contains ',$zip->numFiles,' files with a status of ',$zip->status;
//close the zip -- done!
$zip->close();
//check to make sure the file exists
echo $destination;
return file_exists($destination);
}
else
{
return false;
}
}
I am using this to zip a vanilla, unaltered Wordpress install.(http://wordpress.org/) However for some reason the wp-content folder is having a 'ghost' empty file generated with it's name. The folder (and everything else) itself compresses correctly, but most unzip applications (including php's own extractTo()) break when they reach this unwanted file due to the name conflict.
I've looked into the folder/file structure and as far as I can see the only difference of note between this and the other folders in the site is that it is the biggest at 5.86 mb.
Can anyone suggest a fix / workaround?
This is the sample example to zip a folder.
<?php
function Create_zipArch($archive_name, $archive_folder)
{
$zip = new ZipArchive;
if ($zip->open($archive_name, ZipArchive::CREATE) === TRUE)
{
$dir = preg_replace('/[\/]{2,}/', '/', $archive_folder . "/");
$dirs = array($dir);
while (count($dirs))
{
$dir = current($dirs);
$zip->addEmptyDir($dir);
$dh = opendir($dir);
while ($file = readdir($dh))
{
if ($file != '.' && $file != '..')
{
if (is_file($file))
$zip->addFile($dir . $file, $dir . $file);
elseif (is_dir($file))
$dirs[] = $dir . $file . "/";
}
}
closedir($dh);
array_shift($dirs);
}
$zip->close();
$result='success';
}
else
{
$result='failed';
}
return $result;
}
$zipArchName = "ZipFileName.zip"; // zip file name
$FolderToZip = "zipthisfolder"; // folder to zip
echo Create_zipArch($zipArchName, $FolderToZip);
?>

php creating zips without path to files inside the zip

I'm trying to use php to create a zip file (which it does - taken from this page - http://davidwalsh.name/create-zip-php), however inside the zip file are all of the folder names to the file itself.
Is it possible to just have the file inside the zip minus all the folders?
Here's my code:
function create_zip($files = array(), $destination = '', $overwrite = true) {
if(file_exists($destination) && !$overwrite) { return false; };
$valid_files = array();
if(is_array($files)) {
foreach($files as $file) {
if(file_exists($file)) {
$valid_files[] = $file;
};
};
};
if(count($valid_files)) {
$zip = new ZipArchive();
if($zip->open($destination,$overwrite ? ZIPARCHIVE::OVERWRITE : ZIPARCHIVE::CREATE) !== true) {
return false;
};
foreach($valid_files as $file) {
$zip->addFile($file,$file);
};
$zip->close();
return file_exists($destination);
} else {
return false;
};
};
$files_to_zip = array('/media/138/file_01.jpg','/media/138/file_01.jpg','/media/138/file_01.jpg');
$result = create_zip($files_to_zip,'/...full_site_path.../downloads/138/138_files.zip');
The problem here is that $zip->addFile is being passed the same two parameters.
According to the documentation:
bool ZipArchive::addFile ( string $filename [, string $localname ] )
filename
The path to the file to add.
localname
local name inside ZIP archive.
This means that the first parameter is the path to the actual file in the filesystem and the second is the path & filename that the file will have in the archive.
When you supply the second parameter, you'll want to strip the path from it when adding it to the zip archive. For example, on Unix-based systems this would look like:
$new_filename = substr($file,strrpos($file,'/') + 1);
$zip->addFile($file,$new_filename);
I think a better option would be:
$zip->addFile($file,basename($file));
Which simply extracts the filename from the path.
This is just another method that I found that worked for me
$zipname = 'file.zip';
$zip = new ZipArchive();
$tmp_file = tempnam('.','');
$zip->open($tmp_file, ZipArchive::CREATE);
$download_file = file_get_contents($file);
$zip->addFromString(basename($file),$download_file);
$zip->close();
header('Content-disposition: attachment; filename='.$zipname);
header('Content-type: application/zip');
readfile($tmp_file);
I use this to remove root folder from zip
D:\xampp\htdocs\myapp\assets\index.php
wil be in zip:
assets\index.php
our code:
echo $main_path = str_replace("\\", "/", __DIR__ );// get current folder, which call scipt
$zip_file = 'myapp.zip';
if (file_exists($main_path) && is_dir($main_path))
{
$zip = new ZipArchive();
if (file_exists($zip_file)) {
unlink($zip_file); // truncate ZIP
}
if ($zip->open($zip_file, ZIPARCHIVE::CREATE)!==TRUE) {
die("cannot open <$zip_file>\n");
}
$files = 0;
$paths = array($main_path);
while (list(, $path) = each($paths))
{
foreach (glob($path.'/*') as $p)
{
if (is_dir($p)) {
$paths[] = $p;
} else {
// special here: we remove root folder ("D:\xampp\htdocs\myapp\") :D
$new_filename = str_replace($main_path."/" , "", $p);
$zip->addFile($p, $new_filename);
$files++;
echo $p."<br>\n";
}
}
}
echo 'Total files: '.$files;
$zip->close();
}

Categories