PHP readfile return data - php

(my first question on stack, so sorry for errors and/or inaccuracies...)
So : I've developed a Wordpress Theme and I'd like my users to download the attachments of a post. So I created a Zip Archive and use a readfile(). The function is called by link and using a $_GET['zip'] test.
The Problem : readfile() returns (i mean display) binary characters like this (here I tried to download a test .png file) : �PNG IHDRp�r�*� pHYs�� OiCCPPhotoshop ICC profilexڝSgTS�=���BK���KoR
And nothing is downloaded.
Here my code (the readfile part) :
$zip = new ZipArchive();
if ($zip->open($file_path.$archive_file_name, ZIPARCHIVE::CREATE)!==TRUE) {
exit("cannot open <$archive_file_name>\n");
}
foreach($file_names as $file){
$zip->addFile($file,$file);
}
$zip->close();
header('Content-Description: File Transfer');
header('Content-Type: application/zip');
header('Content-Disposition: attachment; filename="'.basename($file_path.$file).'"');
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
header('Content-Length: ' . filesize($file_path.$file));
ob_clean();
flush();
readfile($file_path.'screenshot.png');
I don't know where to search, and it's my first time with zip archive AND readfile()...
Thanks for the tracks (? do we say that? ) !

I don't know how exactly but it works now. I added an ob_start() just at the beginning of the function. Thanks for support !
The entire function :
if (!function_exists('zipThoseFiles')) {
ob_start();
function zipThoseFiles($id){
if (!function_exists('zipFilesDownload')) {
function zipFilesDownload($file_names,$archive_file_name,$file_path){
$zip = new ZipArchive();
if ($zip->open($file_path.$archive_file_name, ZIPARCHIVE::CREATE )!==TRUE) {
exit("cannot open <$archive_file_name>\n");
}
foreach($file_names as $file){
$zip->addFile($file,$file);
}
$zip->close();
header('Content-Description: File Transfer');
header('Content-Type: application/zip');
header('Content-Disposition: attachment; filename="'.basename($file_path.$archive_file_name).'"');
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
header('Content-Length: ' . filesize($file_path.$archive_file_name));
ob_end_clean();
flush();
readfile($file_path.$archive_file_name);
unlink($file_path.$archive_file_name);
exit;
}
}
$fileNames = array();
$args = array(
'post_type' => 'attachment',
'numberposts' => null,
'post_status' => null,
'post_parent' => $id
);
$attachments = get_posts($args);
if ($attachments) {
foreach ($attachments as $attachment) {
$fileNames[] = get_attached_file( $attachment->ID );
}
}
$zip_file_name = 'mediasArchive.zip';
$file_path = dirname(__FILE__).'/';
zipFilesDownload($fileNames,$zip_file_name,$file_path);
}
}

Related

php zipfile returning an empty zip file

<?php
$files = array('1.txt', '2.txt', '3.txt');
$zipname = 'test.zip';
$zip = new ZipArchive;
$zip->open($zipname, ZipArchive::CREATE);
foreach ($files as $file) {
$zip->addFile($file);
}
$zip->close();
header('Content-Type: application/zip');
header('Content-disposition: attachment; filename='.$zipname);
header('Content-Length: ' . filesize($zipname));
readfile($zipname);
?>
this is my code, the only issue is it is not downloading the files i have specified.
am i doing something wrong? is it the browser im using? (opera)
the file downloads but it ends up being empty.
First check zip file is creating or not and then,
Add File transfer header...
header('Content-Description: File Transfer');
header('Content-Type: application/zip');
header('Content-Disposition: attachment; filename="' . $fileName . '"');
header('Content-Transfer-Encoding: binary');
header('Connection: Keep-Alive');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
header('Content-Length: ' ."Your file size" );
set_time_limit(0);
It will work.
Append "Your file size" to the length of the file size.
I had the same problem. I don't know why, but when I change the logic to use addFromString instead of addFile PHP generated the ZIP file as expected.

Header Content-length not working

I'm doing file download with renaming it before. Everything works except size. I can't set file size with
header('Content-Length: ');
even I'm setting it to
header('Content-Length: 15444544545');
it's not working. I'm using PHP codeigniter framework, where is the problem?
EDIT: more code:
$file_data = array(
'originalName' => $post_info['file_info'][0]['original_name'],
'fakeName' => $post_info['file_info'][0]['file_name'],
'modificationId' => $post_info['file_info'][0]['modification_article_id'],
'extension' => end(explode('.', $post_info['file_info'][0]['original_name'])),
'name' => str_replace(".".end(explode('.', $post_info['file_info'][0]['original_name'])), "", $post_info['file_info'][0]['original_name']),
'filesize' => filesize($post_info['file_info'][0]['file_name'])
);
header('Cache-Control: public');
header('Content-Description: File Transfer');
header('Content-Disposition: attachment; filename=' . $file_data['name'] . '.' . $file_data['extension']);
header('Content-Length: ' . filesize(base_url().$file_data['fakeName']));
// Read file
readfile(base_url().$file_data['fakeName']);
//print_r($file_data);
echo "<script>window.close();</script>";
EDIT: Solution
there was a server problem
You can try like this:
$mm_type="application/octet-stream";
header("Cache-Control: public, must-revalidate");
header("Pragma: hack");
header("Content-Type: " . $mm_type);
header("Content-Length: " .(string)(filesize($fullpath)) );
header('Content-Disposition: attachment; filename="'.$filename.'"');
header("Content-Transfer-Encoding: binary\n");
readfile($fullpath);
wrong usage of base_url().
where is your file stored?
maybe you can try the constant FCPATH instead of call function base_url()
and you have the filesize stored in $file_data['filesize']
finally there should not be a line echo "<script>window.close();</script>"; in your php script when the file content was output.
You tried with download_helper?? Sintax: force_download($filename, $data).
Also in your code you're reading file through URL. Use file system path instead.
From controller action:
<?php
public function download()
{
//Your code here...
$filePath = realpath(FCPATH.DIRECTORY_SEPARATOR.'uploads/myfile.pdf'); //FakeName????
force_download($file_data['fakeName'], readfile($filePath));
}
If my solution don't works give me a touch to give you other way.
Note: FCPATH is the front controller path, a public folder of server e.g.(/var/www/CodeIgniter). Other path constants are already defined on index.php (front-controller).
A print of $file_data['fakeName'] will be useful.
If your CodeIgniter version don't have download_helper make your own... refer to CI docs for full explanation. There is the force_download function code:
function force_download($filename = '', $data = '')
{
if ($filename == '' OR $data == '')
{
return FALSE;
}
// Try to determine if the filename includes a file extension.
// We need it in order to set the MIME type
if (FALSE === strpos($filename, '.'))
{
return FALSE;
}
// Grab the file extension
$x = explode('.', $filename);
$extension = end($x);
// Load the mime types
if (defined('ENVIRONMENT') AND is_file(APPPATH.'config/'.ENVIRONMENT.'/mimes.php'))
{
include(APPPATH.'config/'.ENVIRONMENT.'/mimes.php');
}
elseif (is_file(APPPATH.'config/mimes.php'))
{
include(APPPATH.'config/mimes.php');
}
// Set a default mime if we can't find it
if ( ! isset($mimes[$extension]))
{
$mime = 'application/octet-stream';
}
else
{
$mime = (is_array($mimes[$extension])) ? $mimes[$extension][0] : $mimes[$extension];
}
// Generate the server headers
if (strpos($_SERVER['HTTP_USER_AGENT'], "MSIE") !== FALSE)
{
header('Content-Type: "'.$mime.'"');
header('Content-Disposition: attachment; filename="'.$filename.'"');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header("Content-Transfer-Encoding: binary");
header('Pragma: public');
header("Content-Length: ".strlen($data));
}
else
{
header('Content-Type: "'.$mime.'"');
header('Content-Disposition: attachment; filename="'.$filename.'"');
header("Content-Transfer-Encoding: binary");
header('Expires: 0');
header('Pragma: no-cache');
header("Content-Length: ".strlen($data));
}
exit($data);
}

Zipping checkboxed files PHP

<?PHP
function zipFilesAndDownload($file_names,$archive_file_name,$file_path){
$zip = new ZipArchive();
//create the file and throw the error if unsuccessful
if ($zip->open($archive_file_name, ZIPARCHIVE::CREATE )!==TRUE) {
exit("cannot open <$archive_file_name>\n");
}
//add each files of $file_name array to archive
foreach($file_names as $files) {
$zip->addFile($file_path.$files,$files);
}
$zip->close();
$zipped_size = filesize($archive_file_name);
header("Content-Description: File Transfer");
header("Content-type: application/zip");
header("Content-Type: application/force-download");// some browsers need this
header("Content-Disposition: attachment; filename=$archive_file_name");
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
header("Content-Length:". " $zipped_size");
ob_clean();
flush();
readfile("$archive_file_name");
unlink("$archive_file_name"); // Now delete the temp file (some servers need this option)
exit;
}
if(($_POST['formSubmit'])) {
//$file_names=$_POST['items'];// Always sanitize your submitted data!!!!!!
//$file_names = filter_var_array($_POST['items']);//works but it's the wrong method
$filter = filter_input_array(INPUT_POST, FILTER_SANITIZE_SPECIAL_CHARS) ;
$file_names = $filter['items'] ;
//Archive name
$archive_file_name= "zip.zip";
//Download Files path
$file_path= $leadon;
//cal the function
zipFilesAndDownload($file_names,$archive_file_name,$leadon);
}
?>
I have a working code here.
The main problem is
//Download Files path
$file_path= $leadon;
//cal the function
zipFilesAndDownload($file_names,$archive_file_name,$leadon);
This code
echo $leadon;
returns string images2/User/
And it doesn't create me the zip file ( well it creates a blank ) but if I manually type in the path
"images2/User/"
into
$file_path= and then I just change
zipFilesAndDownload($file_names,$archive_file_name,$file_path);
everything works fine can you tell me why is it so? And how can I change it:s

pdf file not downloading

I am using following code to start downloading but the pop-up for download is not opening. Instead, it shows the binary format of that pdf file. It's working perfectly on local server but not working hosted server.
$file = '../Notes/chapter01.pdf';
if (file_exists($file)) {
header('Content-Description: File Transfer');
// header('Content-Type: application/octet-stream');
header('Cache-Control: public'); // needed for i.e.
header('Content-Type: application/pdf');
header('Content-Disposition: attachment; filename='.basename($file));
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
//header('Cache-Control: must-revalidate');
header('Pragma: public');
header('Content-Length: ' . filesize($file));
ob_end_clean();
flush();
readfile($file);
exit;
}
else {
die('Error: File not found.');
}
This code works.
$file = '../Notes/chapter01.pdf';
$mime_type = 'application/pdf';
$filesize = filesize( $file );
header( "Content-type:" . $mime_type );
header( "Content-Length:" . $filesize );
header( "Content-Disposition: attachment; filename=" . $file );
header( "Cache-Control: private, max-age=15" );
#readfile( $file );
Hope this helps.

Downloading file from localhost site in PHP

When i am download a file with extention like mp3,flv etc it will now download it start buffering And when I remove extention from the file it downloads ...
can you please tell whats the problem behind that ...
file to download is => theangelfoundation-12-5-2012-09-17-27-somebody.mp3
Thanks in advance ..
$file_types=array();
$file_types['mp3'] ='audio/mpeg';
$file_types['mpeg'] ='video/mpeg';
$file_types['mpg'] ='video/mpeg';
$file_types['pdf'] ='application/pdf';
$file_types['pps'] ='application/vnd.ms-powerpoint';
$file_types['ppt'] ='application/vnd.ms-powerpoint';
$file_types['ps'] ='application/postscript';
$file = 'you.mp3';
download($file,$file_types);
function download($file_name,$file_types){
$file = $file_name;
$ext = end(explode('.',$file_name));
if($ext && array_key_exists($ext,$file_types)){
if (file_exists($file)) {
header('Content-Description: File Transfer');
header('Content-Type: application/octet-stream');
header('Content-Disposition: attachment; filename='.basename($file));
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
header('Cache-Control: must-revalidate');
header('Pragma: public');
header('Content-Length: ' . filesize($file));
ob_clean();
flush();
readfile($file);
exit;
}
}
else {
die("this is not a downloadable file");
}
}
?>
download ok.txt

Categories