我需要向经过身份验证的用户提供文件,并认识到使用PHP会带来性能损失,但到目前为止我所经历的似乎是不可行的。
我有一个非常简单的控制器动作,它发送文件:
public function view($id = null) {
$id = $id | $this->params->named['id'];
if (!$this->Attachment->exists($id)) {
throw new NotFoundException(__('Invalid attachment'));
}
$this->autoRender = false;
$this->Attachment->recursive = -1;
$file = $this->Attachment->findById($id);
$this->response->file(APP . DS . $file['Attachment']['dir']);
return $this->response;
}
使用此方法加载一个小的(55 KB)PNG文件需要8秒钟,就好像我将文件移动到webroot目录并直接加载它需要不到2.5秒。通过查看Chrome开发工具,响应中的“接收”部分采用> 7s(直接与1.5s相比)。
中等大小的PDF文件(2.5MB)通过CakeResponse需要2分钟以上,相比之下直接需要~4s。当然,我必须在控制器操作中遗漏一些东西,因为这对任何人都是不可行的吗?
编辑:CakePHP版本是2.4.1。
答案 0 :(得分:3)
由于建议使用Xdebug,我能够快速找到问题所在。
在CakeResponse中,有以下功能:
/**
* Flushes the contents of the output buffer
*
* @return void
*/
protected function _flushBuffer() {
//@codingStandardsIgnoreStart
@flush();
@ob_flush();
//@codingStandardsIgnoreEnd
}
显然,对于错误抑制运算符,对flush
和ob_flush
的调用通常不会导致问题。
但是,我也安装了Sentry作为远程调试工具。这会忽略错误抑制操作符,报告没有要刷新的缓冲区(因为没有调用ob_start),这样做会将文件内容输出到日志文件中!