用php提供可下载的文件

时间:2012-02-14 01:18:46

标签: php file header download attachment

服务器可下载的文件通常位于PHP公共文件夹之外:

$fp = fopen($file,"r") ;
header("Content-Type: application/msword");
header('Content-Disposition: attachment; filename="'.$filename.'"');

while (! feof($fp)) {
    $buff = fread($fp,4096);
    echo $buff;
}

我有两个问题:

  1. 与Web服务器提供的静态文件(直接文件URL)进行比较;这种方法需要更多的资源(内存和CPU),因为PHP需要读取文件并交付吗?

  2. 我们如何在页面上显示一些文字?正如我们定义的header,我们没有php脚本的html输出。

4 个答案:

答案 0 :(得分:3)

  1. 是的,使用PHP读取文件并将其写入用户将使用更多内存和CPU,当然这取决于文件的大小。
  2. 首先显示一个页面,并在页面上有一个按钮/链接,将用户带到实际的下载脚本。
  3. 我也建议使用Content Length Header。

    header('Content-Length: '. filesize($path));
    

答案 1 :(得分:2)

  1. 直接提供文件的开销略高,因为你现在涉及PHP
  2. 不,你不能。如果您输出(比方说)application / msword标头,那么输出AT ALL的任何内容都将被视为.doc文件的一部分并导致其损坏。如果要输出一些文本,则必须分两部分进行下载 - 输出带有文本的标准HTML页面,并包含定时<meta>(或javascript)重定向以将用户转发到实际的下载URL

答案 2 :(得分:2)

1由于您必须使用此脚本处理文件,因此需要更多     资源不仅仅是普通的下载链接。但这取决于您的需求。如果您认为这些文件需要更高的安全性。假设只有经过身份验证的用户才能下载该文件,并且只有该文件属于他。然后你需要验证这些。在这种情况下,您需要在问题中添加的代码。如果您的文件向公众开放,那么您可以显示文件的直接链接,可能会暂时将它们定位在公共场所。

2我可以建议你两种方法来执行此操作。

方法1:

您需要javascript支持才能以方便的方式执行此类要求。假设您需要在可以下载的页面上显示一些HTML。您可以使用所需的HTML创建页面,也可以下载按钮。

<input type="button" name="cmdDownload" id="cmdDownload" value="Download" onclick="downloadFile('<?php echo $pathToTheFile; ?>');" />

您可以保留隐藏的iframe来处理下载。

<iframe id="downloadFrame" style="display:none"></iframe>

假设您的PHP下载页面是download.php。

然后你可以拥有这样的javascript函数。

<script type="text/javascript">
function downloadFile(filepath) 
{
    var ifrme = document.getElementById("downloadFrame");
    ifrme.src = "download.php?filepath="+filepath;
}
</script>

方法2:

除了上述方法,您也可以使用META Refresh。

<meta http-equiv="Refresh" content="3;URL=<?php echo $fullHTTPathToYourFile ?>" />

您也可以使用HTML进行HTML显示。

答案 3 :(得分:1)

如果输出缓冲处于活动状态,使用PHP提供文件会消耗大量内存,性能将比apache提供的常规文件更糟糕。

所以要给已经给出的答案添加一些内容:

  • 完成发送标头后,使用ob_end_flush()结束输出缓冲,因此在开始输出之前文件内容不会缓存在内存中
  • readfile()可能会比您的循环更有效地将文件从磁盘流式传输到Web

有人说过但不能强调:包含Content-Length标题,因为它会允许下载程序来衡量进度。