darwinwen
(Darwinwen)
1
今天在做一个文件下载时, 在Nginx下面使用文件下载性能X-Accel-Redirect 提升下载文件下载性能, 使用CHttpRequest xSendFile方法, 始终返回空白.
根据Nginx 官方文档说明, http://wiki.nginx.org/XSendfile , 必须使用internal作为内部使用,alias标识文件存储的真实路径,
location /filedown/ {
internal;
alias /some/path/; # note the trailing slash
}
在Yii应用程序中我们必须使用/filedown/ 来获得下载目录+文件名称Nginx才能正常解析,类似下面的代码.
Yii::app()->request->xSendFile('/filedown/test.zip',array(
'saveName'=>$filename,
'mimeType'=>'application/octet-stream',
'xHeader'=>'X-Accel-Redirect',
'terminate'=>false,
));
而翻开CHttpRequest -> xSendfile 方法源码可以看到头一行检测文件存在代码将永远返回false,直接返回空白。
public function xSendFile($filePath, $options=array())
{
if(!is_file($filePath)) //在Ningx下面,这行代码不需要检测,永远为false,因为Nginx内部通过别名来获取真实路径.
return false;
}
目前有遇到这个问题的朋友,可以直接使用解决.
header('Content-type: '.$options['mimeType']);
header('Content-Disposition: attachment; filename="'.$options['saveName'].'"');
header('X-Accel-Redirect: '.$filePath);
yiqing95
(Yiqing 95)
2
像文件下载这种功能 从来都只用绝对路径 配合 pathAlias 不会出啥问题吧:
xSendFile(Yii::getPathOfAlias(‘application.filedown’).DIRECTOR_SEPERATOR.‘test.zip’,array(
'saveName'=>$filename,
'mimeType'=>'application/octet-stream',
'xHeader'=>'X-Accel-Redirect',
'terminate'=>false,
));
darwinwen
(Darwinwen)
3
这个/filedown/是nginx配置文件里面定义的,不是由Yii解析, 查看CHttpRequest -> xSendfile 方法源代码可以看到这一行,实际是交由Web服务器处理这个路径,而Nginx必须配置
location /filedown/ {
internal;
alias /some/path/;
}
使用internal 标记为只有nginx内部使用,才可以正常使用X-Accel-Redirect协议, X-Accel-Redirect本身不是一个标准协议,每个Web服务器使用都不同。
public function xSendFile($filePath, $options=array())
{
header(trim($options['xHeader']).': '.$filePath);
}
上面这一行实际等于:
header(‘X-Accel-Redirect : /filedown/test.zip’);
Yii和PHP不做任何事情,全部交给Nginx来处理, 查看Nginx配置说明:
http://wiki.nginx.org/XSendfile
相关性能文章介绍:
http://www.iteye.com/topic/154538
http://www.yiiframew…b-applications/