关于ZipArchive关闭的警告

时间:2016-05-18 12:19:04

标签: php ziparchive

我正在尝试修复一些图像的自动zip脚本中的问题,这是我刚才写的,直到现在才有效。在$zip->close();给出以下内容之前,一切似乎都很好:

 <b>Warning</b>:  ZipArchive::close(): Read error: No such file or directory in <b></b> on line <b>287</b><br />

我阅读了文档和一些论坛,发现这可能发生在以下某种情况中:

  1. 如果没有实际文件添加到zip,自PHP 5.6以来,这可能是一个可能的解释,因为我最近升级到PHP 5.6。然而:
    • 我在添加之前检查每个文件是否存在
    • 我尝试在zip中添加一个虚拟的非空文本文件。将其添加到zip返回true,文件
    • 上的file_exists()也是如此
    • 当我回复$zip->numFiles并且它给出的数字至少为1(当zip没有文件时除了假人)
  2. 如果需要写入zip的目录不存在或者没有正确的权限:这似乎不是这种情况,但只是为了确定,我写了一个文本文件到同一个文件夹中的相同文件夹并没有问题
  3. 如果写入临时目录时出现问题。检查这个有点难,但我在同一系统中有一个上传脚本,我确保没有磁盘空间问题等。
  4. 这是相关代码。一些变量是事先定义的。请注意,我将每个问题写入我的日志,并且此脚本不会生成任何条目!

    $zip_file = 'Project'.$project_id.'.zip';
    $zip = new ZipArchive;
    if ($zip_result = $zip->open($zip_path.'/'.$zip_file, ZIPARCHIVE::CREATE) !== true) {
        echo 'Error creating zip for project: '.$project_id.'. Error code: '.$zip_result;
        help::debugLog('Error creating zip for project: '.$project_id.'. Error code: '.$zip_result);
        return false;
    }
    $file_list = array();
    
    foreach ($item_thumbs as $item)
    {
        $full_thumb_path = $thumb_dir.'/'.$item['thumb'];
        if (file_exists($full_thumb_path) and $item['thumb'])
        {
            $file_added = $zip->addFile($full_thumb_path, basename($item['thumb']));
            if (!$file_added)
                help::debugLog('Failed to add item thumb to project zip. Project: '.$project_id.', file name: '.$item['thumb']);
            else
                $file_list[] = $item['thumb'];
        }
        elseif ($item['thumb']) /* If thumb indicated in DB doesn't exist in file system */
            help::debugLog('Item thumb file '.$item['thumb'].' from item: '.$item['id'].' is missing from its indended location: '.$full_thumb_path);
    }
    
    /* Added 2016-05-18 -- creates dummy file for the zip listing its contents, important in case zip is empty */
    $file_list_path = $zip_path.'/file_list.txt';
    if (!($file_list_file = fopen($file_list_path, 'w+')))
        help::debugLog('Failed to create list file (intended for zip) for project: '.$project_id);
    fwrite($file_list_file, "File list:\n");
    fwrite($file_list_file, implode("\n", $file_list));
    if (file_exists($file_list_path))
    {
        fclose($file_list_file);
        if (!$zip->addFile($file_list_path))
            help::debugLog('Failed to add list file to project zip for project: '.$project_id);
        unlink($file_list_path);
    }
    else
        help::debugLog('Failed to create list file (intended for zip) for project: '.$project_id);
    
    $zip->close(); // line 287
    

3 个答案:

答案 0 :(得分:9)

事实证明解决方案非常简单,实际上在文档(php.net)中引用了其中一条评论:

  

对某些人来说,这似乎有点明显,但这是对我的疏忽。

     

如果要将文件添加到要删除的zip文件中,请确保在调用close()函数后删除。

     

如果添加到对象的文件在保存时不可用,则不会创建zip文件。

因此,从上面的代码开始,在关闭zip之前删除了“虚拟”文本文件,必然会使zip文件在创建时不存在。

我有充分的理由相信zip是在临时位置创建的,只是移动到close()上的最终位置。事实证明并非如此。

答案 1 :(得分:0)

仅仅因为这是错误消息在 Google 中排名第一,我添加了另一个可能导致此完全相同错误的问题。

如果您没有向 zip 存档添加任何文件,则它尚不存在,因此 close() 将在空存档上失败。

例如:

$zip = new ZipArchive;
$zip->open("foo.zip", ZipArchive::CREATE | ZipArchive::OVERWRITE);
$zip->close();

产生:

ERROR: ZipArchive::close(): Can't remove file: No such file or directory

因此,如果您要循环并添加文件,请确保在调用 close() 之前添加了一些内容。

答案 2 :(得分:-1)

检查

行中“$ full_thumb_path”的值
    $file_added = $zip->addFile($full_thumb_path, basename($item['thumb']));

值应该是文件路径,不能是目录路径。