black image when forcing download - php

when i click a button the browser force the image to download
the code work it download the image with the right size but it's all black
im using this code :
// get attachment location
$attachment_location = "files/image.jpg";
if (file_exists($attachment_location)) {
// attachment exists
// send open/save jpg dialog to user
header('Cache-Control: public'); // needed for i.e.
header('Content-Type: application/jpg');
header('Content-Disposition: attachment; filename="image.jpg"');
readfile($attachment_location);
die(); // stop execution of further script because we are only outputting the jpg
}
else {
die('Error: File not found.');
}

I tried your code on my test server. (PHP5.3, Apache2.2, Win7)
Works fine in both Firefox and IE8.
Are you sure the problem is not with your image, or with your own browser?
Which version of PHP are you using? What HTTP server? Which OS?
Which browser did you test this on?

Is it possible you have other data still in the buffer? what happens if you use echo file_get_contents() instead of readfile? What happens if you call ob_clean(); flush(); before calling readfile?
Also do you have error_reporting truned on? Try turning it off before calling readfile or using any of the buffer operations i mentioned above.

Related

Forcing download of excel file through Ajax request fails silently

I am trying to make a link that is clickable; when it's clicked on it forces a download (or even a Save As option would be nice) of an .xls file. This is what I have below.
When the link is clicked, there are no php log errors and it goes through this code. The file does exist as well. Are my headers wrong?
if (#file_exists("/tmp/report/{$php_session_id}.xls")) {
$filename = "/tmp/report/{$php_session_id}.xls";
$content_length = filesize($filename);
header("Pragma: public");
header("Expires: 0");
header("Content-type: application/vnd.ms-excel");
header("Content-length: {$content_length}");
header("Content-disposition: attachment; filename=\"missing_addresses.xml\"");
readfile($filename);
}
If the code is correct, is it possibly a server that is locked out of doing this?
Also, I am testing on Chrome for Mac (newest version)
UPDATE: I used AJAX which was the problem.
You can't initiate a download through Ajax; the response will simply vanish in the ether, as a normal Ajax response. (You could theoretically capture it, but you won't be able to write it to disk.)
Use
location.href = "source.php";
or
<a href='source.php' target='_blank'>
to direct the browser to the resource directly instead. It will automatically detect that it's a file to be downloaded, and initiate the download.

How to Stop Header, so I can echo to screen from the same function (PHP)

I'm finding Headers a nightmare to get my head around, I have a file the user downloads which works fine. However I then whish to echo to the screen that xx file has been sent; but ofc this echo is just placed inside the sent file.
Full dowload code is as follows:
function download()
{
$orderNo = $_POST['orderNo'];
$lines = file('F:/xamptest/htdocs/UniProject/upload/Amazon output.txt');
$lineCount = count($lines);
if($orderNo>0&&$orderNo<=$lineCount)
{
$lineEx = explode("\t", $lines[($orderNo-1)]);
$file = fopen('Order.txt', 'w');
fwrite($file, $lineEx[8].PHP_EOL .$lineEx[17].PHP_EOL .$lineEx[18].PHP_EOL .$lineEx[19].PHP_EOL .$lineEx[20].PHP_EOL .$lineEx[21].PHP_EOL .$lineEx[22].PHP_EOL .$lineEx[23].PHP_EOL);
fclose($file);
$file = 'Order.txt';
ob_end_clean();
header("Cache-Control: private");
header("Content-Description: File Transfer");
header("Content-Disposition: attachment; filename=$file");
header("Content-Type: application/zip");
header("Content-Transfer-Encoding: binary");
readfile($file);
echo "Current order, number: ".$orderNo."<br> Has been downloaded";
}
else
{
echo "Please enter a valid Order Number between 1 and ".$lineCount;
}
}
I can't seem to find how to stop the headers without using exit(); which then still means it won't show the echo, and any more use of ob_end_clean(); in any other ways causes the sent file to be empty. Only other thing I could think was having the echo in its own function, but as it runs at the same time the headers do it still places it in the file.
Many thanks for any help - Tom.
What you're dealing with is an HTTP request. The browser requests a URL with an HTTP request, the server sends a response. Click a link → browser sends request → server sends HTML page in response. Use Chrome, Safari or Firefox + Firebug and play around with the Network tab in their Web Inspector/development tools to get a real feeling for what's happening.
If you want to download a file, it works the same way. Only the server tells the browser through HTTP headers that this response is not an ordinary HTML page, but is supposed to be a file which it should save on disk.
As you should be able to see, there's no way to respond with a file download and an HTML page at the same time in one response. There's simply no way to do it. You have to output your HTML page with the message first, then link to the file download from there.

PHP to force download breaks document

I am using the following code in a php document to force download of a pdf form since the submission works only after you have it on your local machine rather online.
It downloads the file ok but it corrupts it.
I can no longer open the pdf document.
<?php
$file_name = 'costumer.pdf';
$file_url = 'http://www.lopezi.com/forms/' . $file_name;
header('Content-Type: application/pdf');
header("Content-Transfer-Encoding: Binary");
header("Content-disposition: attachment; filename=\"".$file_name."\"");
readfile($file_url);
?>
The Content-Transfer-Encoding header shouldn't be needed in this case. Further I suspect that you have corruption in the outputted file.
Download it somewhere, open notepad, and drag the file in there. If any PHP warnings or errors were generated you will see them at the top.
Also, try to avoid the option of having more content return from the script, causing problems with the download, end with something like:
die(file_get_contents($file_url));
This way you cannot accidentally break the code easily by adding more output.

File downloaded in PHP using Firefox is wrong size

I have a problem with invalid signing certificates on files downloaded using Firefox. IE, Opera, Safari and Chrome are all fine. If the file is downloaded directly by clicking a link in FF it's also ok but if the file is downloaded using PHP for security it is 1 byte larger, having a x0A tacked on the end and I think this is causing it to fail the validation check. The PHP is very simple:
<?php
$file = "../downloads/".$_GET['link'];
$size = filesize($file);
$type = filetype($file);
header('Content-Type: application/octet-stream');
header("Content-Transfer-Encoding: Binary");
header( "Content-Disposition: attachment; filename=".basename($file));
header("Content-Length: ".$size);
header("Content-Type: ".$type);
readfile($file);
?>
Does anyone have any idea why Firefox alone should be having problems with getting the size right here? Grateful for any ideas.
Check if file exists and is placed in allowed location - now attacker is able to download nearly every file on your webserver
Don't use closing phptag - ?>, every whitespace after it will be send to the browser
Use exit; just after readfile to make sure no other function that produces output is called.
check on the Content-Type header, you set it twice so the latter one will be used, it could be something like "Content-Type: file" due to function filetype(), the browser can't understand "file" content type and take it as a text file. I guess that's the cause of the extra 0x0a.
Comment "header("Content-Type: ".$type);" and it will work fine.
replace below line
<?php
header("Content-Length: ".strlen($file));
?>
good luck :)

image button "save as" to save file from external servers php script

I have a pictrures gallery on my server. The pictures are stored on diffrent external servers. On my server are placed the thumbnails only.
How I can make a button "save as" in php so that a user can download a big picture file which is from external servers. I need a simple php script which can do download a jpg file cross all browser agents and from diffrent external servers. The button will be implemented inside html code. The button is a regular link formated in css style.
So how to do it properly. Thanks.
I would like also that the path of file should be send as a variable parameter to php script somehow.
I am guessing you are trying to have the pictures be downloaded automatically (you want a dialog box to pop up prompting where to save the file).
There is a great tutorial on this site that uses the php header function to force download
Check it out: http://www.ryboe.com/tutorials/php-headers-force-download
I found some solution with following php script
<?PHP
// Define the path to file
$file = $_GET['file'];
$name = basename ($file);
if(!file)
{
// File doesn't exist, output error
die('file not found');
}
else
{
// Set headers
header("Cache-Control: public");
header("Content-Description: File Transfer");
header("Content-Disposition: attachment; filename=$name");
header("Content-Type: image/jpg");
header("Content-Transfer-Encoding: binary");
// Read the file from disk
readfile($file);
}
?>
and I can send parameters like url address cross html code
download
The only problem is that it is not working with all servers. It's not woriking for exemple with that file
http://backalleypics.com/Pictures/Letter Je~Ju/Jessica Alba/Jessica Alba 230.jpg
I don't know what I need to do?
Remove the spaces from your file name:
change: http://backalleypics.com/Pictures/Letter Je~Ju/Jessica Alba/Jessica Alba 230.jpg
to: http://backalleypics.com/Pictures/Letter_Je~Ju/Jessica_Alba/Jessica_Alba_230.jpg

Categories