Sending file to a browser as attachment

23,961

Solution 1

From another server without downloading to your server:

header('Location: http://thirdparty.com/file.ext');

Without downloading the file locally you have no authorization in the external server, so you have to tell the browser what to do, thus the redirect header, it will tell the server to go directly to the url provided, thus loading the download.

From your server you would do:

if (file_exists($file))
{
    if(false !== ($handler = fopen($file, 'r')))
    {
        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, post-check=0, pre-check=0');
        header('Pragma: public');
        header('Content-Length: ' . filesize($file)); //Remove

        //Send the content in chunks
        while(false !== ($chunk = fread($handler,4096)))
        {
            echo $chunk;
        }
    }
    exit;
}
echo "<h1>Content error</h1><p>The file does not exist!</p>";

Taken from another question I have answered

Solution 2

http://php.net/manual/en/function.header.php#example-3655

If you want the user to be prompted to save the data you are sending, such as a generated PDF file, you can use the » Content-Disposition header to supply a recommended filename and force the browser to display the save dialog.

<?php
// We'll be outputting a PDF
header('Content-type: application/pdf');

// It will be called downloaded.pdf
header('Content-Disposition: attachment; filename="downloaded.pdf"');

// The PDF source is in original.pdf
readfile('original.pdf');
?>
Share:
23,961

Related videos on Youtube

12 secs ago
Author by

12 secs ago

Updated on April 02, 2020

Comments

  • 12 secs ago
    12 secs ago about 4 years

    How to send a file to the browser as attachment if the meant file resides on a 3rd party server (without prior downloading or streaming)?

    • mario
      mario about 13 years
      There is no way to accomplish that. You have no influence over the handling of remote resources. And HTTP clients do not support message/external-body payloads.
  • Gumbo
    Gumbo about 13 years
    Better use application/octet-stream.
  • RobertPitt
    RobertPitt about 13 years
    he did say without prior downloading or streaming.
  • RobertPitt
    RobertPitt about 13 years
    this would send a file stored locally, please re-read the question at hand.
  • RobertPitt
    RobertPitt about 13 years
    Not quite, using the redirect function will create the illusion that the file is being downloaded from his server.
  • Sam Vloeberghs
    Sam Vloeberghs about 11 years
    fopen requires 2 parameters, the second should be the mode, in this case "r" for read
  • Asaelko
    Asaelko about 8 years
    fopen + fread by chunks isn't a good way — too slow. Use readfile($file) after headers for speed up.
  • user3161924
    user3161924 over 3 years
    If you get corrupted file (space prefixed) you need to add ob_end_clean(); after the last header() function.

Related