为大型文件,PHP和Nginx的X-加速重定向(Serve large file with PHP

2019-09-01 00:48发布

您好我希望用户能够从nginx的PHP配置我的服务器(Windows)下载PDF文件。 这是我的nginx.conf(服务器块)

http {
    include       mime.types;
    default_type  application/octet-stream;
    sendfile      on;
    keepalive_timeout  65;
    server {
        listen       80;
        server_name  localhost;
        location / {
            root   html;
            index  index.php;

        }

         location /download {
            internal;
            alias /protected;
        }
    }
}

..和PHP文件(标题部分)

$file = '/download/real-pdf-file.pdf'; //this is the physical file path
$filename = 'user-pdf-file.pdf'; //this is the file name user will get
header('Cache-Control: public, must-revalidate');
header('Pragma: no-cache');
header('Content-Type: application\pdf');
header('Content-Length: ' .(string)(filesize($file)) );
header('Content-Disposition: attachment; filename='.$filename.'');
header('Content-Transfer-Encoding: binary');
header('X-Accel-Redirect: '. $file);

该文件是从呼叫URL是这样的:

download.php?id=a2a9ca5bd4a84294b421fdd9ef5e438ded7fcb09

我已经尝试几个例子/解决方案从这里,但至今没有工作。 该文件是很大,每个用户(每250到400 MB之间),就可以下载4个文件。

有使用PHP,只是似乎没有工作nginx的配置下载部分没有问题。 没有错误日志检测。

Answer 1:

好了 - 有一对夫妇在这里的问题:

1)的位置处的内部Puting根是一个坏主意根据nginx的开发者。

2)用于告诉Nginx的,这是一个内部重定向不应暴露给用户的内部URL。

3)我不能看到你的download.php文件正在从提供服务,所以我改变你的根位置块使用try_files所以请求/download.php将通过该文件,而不是index.php文件送达。

您的项目应当设置为:

project\
    html - this is the root of your website
    protected  - this directory is not accessible directly

和你的Nginx的conf应该是这样的:

http {
    include       mime.types;
    default_type  application/octet-stream;
    sendfile      on;
    keepalive_timeout  65;
    server {
        listen       80;
        server_name  localhost;

        root   /path/to/project/html;

        location / {
            try_files $uri /index.php?$args;
        }

        location /protected_files {
            internal;
            alias /path/to/project/protected;
        }
    }
}

这是一个好主意,不要重复使用相同的名称意味着不同的东西,因为它是相当混乱。 我已经改变了他们,因此现在protected刚是指包含要提供的文件的实际物理目录。 protected_files仅仅是一个字符串,它允许Nginx的以匹配来自x加速度头中的请求。

需要在你的PHP代码改变的唯一的事情就是用正确的字符串,使Nginx的皮卡内的位置:

$aliasedFile = '/download/real-pdf-file.pdf'; //this is the nginx alias of the file path
$realFile = '/path/to/project/protected/real-pdf-file.pdf'; //this is the physical file path
$filename = 'user-pdf-file.pdf'; //this is the file name user will get
header('Cache-Control: public, must-revalidate');
header('Pragma: no-cache');
header('Content-Type: application\pdf');
header('Content-Length: ' .(string)(filesize($realFile)) );
header('Content-Disposition: attachment; filename='.$filename.'');
header('Content-Transfer-Encoding: binary');
header('X-Accel-Redirect: '. $aliasedFile);
exit(0);


Answer 2:

从Danack建议和解决方案,并作出一些澄清卡斯滕基础,我发现,在Windows即成,我们需要设置的完整路径在这样的别名:

location /protected_files {
            internal;
            alias C:/absolute/path/to/project/protected/;
        }

请注意,需要额外的正斜杠(在我的情况下,Windows 7的临上开发,Windows Server 2008的部署)。 唯一的问题现在我需要测试并发下载,看看服务器资源霸占。

我是新nginx的,因为它似乎真的快,我从Apache的切换。 感谢家伙的启示! 我'高兴能#1社区的一部分:)



文章来源: Serve large file with PHP and nginx X-Accel-Redirect
标签: php nginx