php 关闭ZipArchive时的警告

bwntbbo3  于 2022-12-26  发布在  PHP
关注(0)|答案(4)|浏览(278)

我正在尝试修复一些图像的自动压缩脚本中的一个问题,这是我不久前写的,直到现在还能正常工作。一切似乎都很好,直到$zip->close();,它给出了以下内容:

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

我阅读了文档和一些论坛,发现这可能发生在以下场景之一:

  • 如果没有实际的文件被添加到压缩文件中,从PHP 5.6开始-这可能是一个可能的解释,因为我最近升级到了PHP 5.6。
  • 我在添加文件之前检查每个文件是否存在
  • 我尝试向zip中添加一个虚拟的非空文本文件,将其添加到zip中返回true,就像file_exists()对该文件所做的那样
  • 当我回显$zip->numFiles时,它给出的数字至少为1(当zip文件除了dummy文件之外没有其他文件时)
  • 如果需要写入zip的目录不存在或没有正确的权限:这看起来并不是这样,但是为了确保这一点,我在同一个脚本中向同一个文件夹写入了一个文本文件,没有出现任何问题
  • 如果有一个问题写入临时目录。这是一个有点困难,以检查这一点,但我有一个上传脚本在同一系统中的工作,我确保没有磁盘空间的问题等。

下面是相关的代码。一些变量是预先定义的。注意,我把每个问题都写进了我的日志,这个脚本不会生成任何条目!

$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
1sbrub3j

1sbrub3j1#

事实证明,这个解决方案非常简单,实际上在文档(php.net)中也有提到,在Jared在kippage. com的一条评论中:
这对一些人来说可能看起来有点明显,但这是我的疏忽。
如果您正在向要删除的zip文件添加文件,请确保在调用close()函数后删除。
如果添加到对象的文件在保存时不可用,则不会创建zip文件。
(资料来源:https://www.php.net/manual/en/ziparchive.close.php#93322)
因此,从我上面的代码中可以看出,在zip关闭之前删除了“dummy”文本文件,这必然会使该文件在zip创建时不存在。
我有充分的理由相信zip是在一个临时位置创建的,只是移动到了close()上的最终位置。

2ledvvac

2ledvvac2#

仅仅因为这是谷歌的错误信息#1,我添加了另一个可能的问题,导致这个完全相同的错误。
如果您没有添加任何文件到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()之前添加了一些内容。

nx7onnlm

nx7onnlm3#

正如Ynhockey的回答中提到的,最可能的原因是在关闭zip文件之前删除了该文件。一个明显的解决方案是在调用$zip->close()之后删除文件。
而不是做

$zip->addFile('file.txt', 'file.txt');
unlink('file.txt');
$zip->close(); //gives error!

您可以调用addFromString函数并执行以下操作:

$zip->addFromString(file_get_contents('file.txt'), 'file.txt');
unlink('file.txt');
$zip->close(); //does not give any error!
fumotvh3

fumotvh34#

检查行中“$full_thumb_path”的值

$file_added = $zip->addFile($full_thumb_path, basename($item['thumb']));

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

相关问题