ZipArchive与filesize有关,没有这样的文件Laravel

时间:2018-04-27 11:36:43

标签: laravel amazon-s3 ziparchive

我已经尝试过全力以赴寻找解决方案并尽力而为,但没有成功。我有一个Laravel项目,它实现了从Amazon S3存储中获取的照片,我需要能够从特定页面获取所有照片并将其压缩以备下载。但是,根据我的编码方式,我会遇到各种错误。

这是我目前的......

首先,我初始化ZipArchive,然后打开检查是否存在任何可能的错误。此代码始终返回" All good"响应。

$zipfile = storage_path() . '/case_photos.zip';
$zip = new ZipArchive;

$ZIP_ERROR = [
    ZipArchive::ER_EXISTS => 'File already exists.',
    ZipArchive::ER_INCONS => 'Zip archive inconsistent.',
    ZipArchive::ER_INVAL => 'Invalid argument.',
    ZipArchive::ER_MEMORY => 'Malloc failure.',
    ZipArchive::ER_NOENT => 'No such file.',
    ZipArchive::ER_NOZIP => 'Not a zip archive.',
    ZipArchive::ER_OPEN => "Can't open file.",
    ZipArchive::ER_READ => 'Read error.',
    ZipArchive::ER_SEEK => 'Seek error.',
];


$result_code = $zip->open($zipfile, ZipArchive::CREATE);
if( $result_code !== true ){
    $msg = isset($ZIP_ERROR[$result_code])? $ZIP_ERROR[$result_code] : 'Unknown error.';
    Log::info("error: " . $msg);
} else {
    Log::info("All good");
}

然后我检查照片(先前从数据库记录中获取)并循环浏览它们,将它们逐个添加到之前打开的存档中。

if (!empty($photos)) {
    foreach ($photos as $photo) {
        $sizedPhoto = $this->photoRepo->getPhotoBySize($photo->id, 'large');
        $source = $this->fileStorage->getFileStream($sizedPhoto->storage_name);
        $tmpfname = tempnam(storage_path(), "tmp");
        $destination = fopen($tmpfname, "w");
        while (!feof($source)) {
            fwrite($destination, fread($source,10000));
        }
        fclose($source);
        fclose($destination);
        $zip->addFile($tmpfname, 'photo-'.$photo->id.'.jpg');
        unlink($tmpfname);
    }

    $zip->close();

但是,这会在$zip-close()行引发以下错误:

  

ZipArchive :: close():无法打开文件:没有这样的文件或目录

为了测试,我将此行注释掉并继续下载部分:

$response = new StreamedResponse();
$response->setCallback(function () use($zipfile){
    readfile($zipfile);
    unlink($zipfile);
});


$response->headers->set('Content-Type', 'application/x-zip-compressed');
$response->headers->set('Cache-Control', '');
$response->headers->set('Content-Length', filesize($zipfile));
$response->headers->set('Last-Modified', gmdate('D, d M Y H:i:s'));
$contentDisposition = $response->headers->makeDisposition(ResponseHeaderBag::DISPOSITION_ATTACHMENT, basename($zipfile));
$response->headers->set('Content-Disposition', $contentDisposition);

return $response;

但后来我收到了这个错误:

  

filesize():stat失败了   /home/vagrant/webapp/storage/case_photos.zip

在逐个浏览照片之后,我发现很难找到每张照片的大小,因为它要么告诉我它是资源,要么文件大小为零。

我想在这一行上使用每张照片的尺寸:

fwrite($destination, fread($source,10000));

而不是硬编码10000的限制,但我无法工作。

这变得非常令人沮丧,因为无论我做什么,我得到500错误,另一个问题我无法解决。任何有关这方面的帮助将不胜感激。

1 个答案:

答案 0 :(得分:0)

好的,所以我发现它是什么。事实证明tmp文件在被添加到zip文件之前被取消链接了 - 所以,最终的zip是空的/ 0kb这就是为什么它没有读取文件大小,因此它为什么没有关闭拉链。