SitePoint Sponsor

User Tag List

Results 1 to 10 of 10
  1. #1
    SitePoint Member
    Join Date
    Jun 2002
    Location
    Norway
    Posts
    19
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    Secure downloads

    Hi!

    I'm writing a script that will allow certain useres to download certain files.
    But, i'm usure on how i can make this as secure as possible. I have 3 ideas on how i can do this, but i want to hear if anybody here has comments or other smarter solutions.

    1. E-Mail the file
    When a user press the download link, the file will be emailed to the user. This is bad if the file is big, and the user has a hotmail account.

    2. "Stream" the file to the client
    A user press the download link, and the file is opened by a php script, read and sendt directly to the user. I have to send spesific headres, depending on the file type. This often causes problemes when you want to save a file, it is named after the php script, and not the original file name.

    3. Copy the file to a temporary folder, download it just the way you download any other file
    A user presses the download link. The file is copied to a folder named like this: md5(microtime()). The user can download the file just as he please. But other people could also download it. I could password protect this directory. But then the script requires apache, Allow Override and all sorts of other stuff. I don't want that. I laso have to write a script that removes old folders. I don't want that either..


    Any other smart solutions, og suggestions are higly appriciated.
    -xqus
    Your friend in the fight against everyday sanity.

  2. #2
    SitePoint Zealot easyrew's Avatar
    Join Date
    Nov 2001
    Location
    Milton Keynes, UK
    Posts
    186
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Options one and three are not great - for the reasons you've specified. I always use:
    Quote Originally Posted by xqus
    2. "Stream" the file to the client
    A user press the download link, and the file is opened by a php script, read and sendt directly to the user. I have to send spesific headres, depending on the file type. This often causes problemes when you want to save a file, it is named after the php script, and not the original file name.
    I'm a ColdFusion bod, so can't help with the PHP, but I am familiar with the problem you've mentioned (where the downloaded file uses the name of the script, rather than the source filename).

    Quote Originally Posted by xqus
    Any other smart solutions, og suggestions are higly appriciated.
    In ColdFusion, I also use Custom header information, and one particular custom header solves the above problem.

    Code:
    <cfheader name="Content-Disposition" value="attachment; filename=mySpecificFilename.xyz">
    Not sure how to translate that into PHP - but I'm sure someone around here can help you with that.

    Hope that's helpful (and 'smart') ...

    Rich
    If a man stands alone in the forest
    and there's no woman around to hear him,
    is he still wrong?
    w: www.EasyRew.com

  3. #3
    SitePoint Member
    Join Date
    Jun 2002
    Location
    Norway
    Posts
    19
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Thak you for your reply!

    In PHP it would look like something like this:
    PHP Code:
    <?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');

    ?>
    The problem is, that i don't know what sort of content-type to use for the file. PHP has a function for determing a files MIME content-type, but it is only supported in PHP 4.3.0 and higher, and you need to complie PHP with support for that function.

    And sice this is a script i plan to sell, it's not a good solution.

    I could also use /etc/mime.types, and import this into a database, and make the user select the correct content-type for that file.


    Edit
    Actually, PHP fetches the content-type when you upload files..

    From : http://www.php.net/manual/en/features.file-upload.php

    $_FILES['userfile']['type']
    The mime type of the file, if the browser provided this information. An example would be "image/gif".
    Last edited by xqus; Mar 3, 2003 at 11:38.
    -xqus
    Your friend in the fight against everyday sanity.

  4. #4
    The doctor is in... silver trophy MarcusJT's Avatar
    Join Date
    Jan 2002
    Location
    London
    Posts
    3,509
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by xqus
    Thak you for your reply!

    In PHP it would look like something like this:
    PHP Code:
    <?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');

    ?>
    The problem is, that i don't know what sort of content-type to use for the file. PHP has a function for determing a files MIME content-type, but it is only supported in PHP 4.3.0 and higher, and you need to complie PHP with support for that function.

    And sice this is a script i plan to sell, it's not a good solution.

    I could also use /etc/mime.types, and import this into a database, and make the user select the correct content-type for that file.


    Edit
    Actually, PHP fetches the content-type when you upload files..
    Since you're (correctly) forcing a download with your Content-Disposition, the ContentType doesn't really matter, but "application/octet-stream" is the correct generic binary format to use, which works a treat with everything!
    MarcusJT
    - former ASP web developer / former SPF "ASP Guru"
    - *very* old blog with some useful ASP code

    - Please think, Google, and search these forums before posting!

  5. #5
    SitePoint Member
    Join Date
    Jun 2002
    Location
    Norway
    Posts
    19
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by M@rco
    Since you're (correctly) forcing a download with your Content-Disposition, the ContentType doesn't really matter, but "application/octet-stream" is the correct generic binary format to use, which works a treat with everything!
    Okey.. thank you.. it works like a charm..
    -xqus
    Your friend in the fight against everyday sanity.

  6. #6
    The doctor is in... silver trophy MarcusJT's Avatar
    Join Date
    Jan 2002
    Location
    London
    Posts
    3,509
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by xqus
    Okey.. thank you.. it works like a charm..
    Y'welcome!
    MarcusJT
    - former ASP web developer / former SPF "ASP Guru"
    - *very* old blog with some useful ASP code

    - Please think, Google, and search these forums before posting!

  7. #7
    ********* Genius Mike's Avatar
    Join Date
    Apr 2001
    Location
    Canada
    Posts
    5,458
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Here's what I use:

    PHP Code:
    <?php

        $size 
    filesize($file);
        
    header("Cache-control: private");
        
    header("Content-Type: application/octet-stream");
        
    header("Content-Type: application/force-download");
        
    header("Content-Length: $size");
        if(
    preg_match("/MSIE 5.5/"$_SERVER["HTTP_USER_AGENT"])){
            
    header("Content-Disposition: filename=".$name.".pdf","pdf");
        }
        else
        {
            
    header("Content-Disposition: attachment; filename=".$name.".pdf","pdf");
        }
        
    readfile("$file");
        exit();

    ?>
    Mike
    It's not who I am underneath, but what I do that defines me.

  8. #8
    The doctor is in... silver trophy MarcusJT's Avatar
    Join Date
    Jan 2002
    Location
    London
    Posts
    3,509
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by naramation
    Here's what I use:

    PHP Code:
        header("Content-Type: application/octet-stream");
        
    header("Content-Type: application/force-download"); 
    Only one of those lines is needed, since an HTTP request header is only permitted to contain one of each type (doing otherwise breaks the specs). Depending on the browser's method of reading the header information, it could use either, so this approach is ill-advised for compatibility (especially with download managers, etc).

    Using a made-up content-type (of which "application/force-download" is one) happens to work because the browser doesn't recognise it and hence prompts the user to save or specify a helper (i.e. viewer) application for it. Thus, "pigs/might-fly" would have the same effect. "application/octet-stream" on the other hand IS a recognised MIME type, but this is configured to save, not display, and hence the same resulting action occurs.

    Thus, in the interests of compatibility (and the removal of redundant code), I suggest that you remove the second line I have quoted.
    MarcusJT
    - former ASP web developer / former SPF "ASP Guru"
    - *very* old blog with some useful ASP code

    - Please think, Google, and search these forums before posting!

  9. #9
    ********* Genius Mike's Avatar
    Join Date
    Apr 2001
    Location
    Canada
    Posts
    5,458
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    One of the browsers does not care about the octet-stream header I read, so I use the second one for that browser
    Mike
    It's not who I am underneath, but what I do that defines me.

  10. #10
    The doctor is in... silver trophy MarcusJT's Avatar
    Join Date
    Jan 2002
    Location
    London
    Posts
    3,509
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    I find that hard to believe, but if that is indeed the case then you're still better off using the second one by itself rather than violating HTTP specifications, don't you think?
    MarcusJT
    - former ASP web developer / former SPF "ASP Guru"
    - *very* old blog with some useful ASP code

    - Please think, Google, and search these forums before posting!


Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •