PHP 如何正确托管大文件?

标签 php html ftp timeout request

我当前正在使用以下 PHP 函数来允许用户选择文件然后下载它。这通过 FTP 发生。但是,如果用户选择大文件,那么在下载时,它会锁定服务器以应对任何其他请求。有什么方法可以在让 PHP 继续响应请求的同时托管该文件吗?

我需要 PHP 来验证用户是否有权使用其凭据下载该文件,因此我不能仅将其作为 Assets 托管。该文件位于 FTP 服务器上。

function download($file) {
    $fileStream = "";
    if($this->get($file)) {
        //Send header to browser to receive a file
        header("Content-disposition: attachment; filename=\"$file\"");
        header("Content-type: application/octet-stream");
        header("Pragma: ");
        header("Cache-Control: no-cache");
        header("Expires: 0");

        $data = readfile($this->downloadDir . $file);
        $i=0;
        while ($data[$i] != "")
        {
            $fileStream .= $data[$i];
            $i++;
        }
        unlink($this->downloadDir . $file);
        echo $fileStream;
        exit;
    } else {
        return false;
    }
}

最佳答案

PHP 并不是此类工作的最佳解决方案,但它可以将工作委托(delegate)给您正在使用的 Web 服务器。由于该文件与您的应用程序位于同一位置,因此这是可行的。

通常运行 PHP 应用程序的所有主要 Web 服务器( Apachelighttpdnginx )都支持 XSendfile

要使用它,您必须首先在 Web 服务器中启用该功能(检查上面每个 Web 服务器的链接),然后在脚本中添加新 header :

Apache :

header("X-Sendfile: $location_of_file_to_download");

Lighttpd:

header("X-LIGHTTPD-send-file: $location_of_file_to_download");

nginx:

header("X-Accel-Redirect: $location_of_file_to_download");

Web 服务器将从您的应用程序捕获此 header ,并用该文件替换 PHP 响应的正文。当它将此文件发送给用户时,PHP 就会解锁并准备好为新用户提供服务。

(其他 header 将保留,因此您可以保留内容类型和内容处置 header )

关于PHP 如何正确托管大文件?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14430102/

相关文章:

html - 延伸过去文本的边框

Ruby FTP 从文件夹中分离文件

php - 为什么我的代码无法检索/显示 PDO 记录集?

php - 用于获取最近 30 天的每日数据的 MYSQL 查询计数,即使任何日期的数据都不存在

php - codeigniter在哪里创建和销毁mysql连接以及db类单例?

javascript - 如何将 HTML 重写为 PHP 回显?

javascript - 将内容从 textarea Javascript 插入到 div 中

jquery - 使用 jquery 的动态内容

php - 警告 : ftp_get(): Delete operation successful

java - 使用 apache FTPclient 使用 Collections.sort() 排序和下载文件