在 php 中删除 zip 内的文件夹


Delete a folder inside zip in php

我有一个具有以下结构的ZIP文件(skins.zip):

yellow  
  |_resources  
  |_theme  
  |_codes

我需要删除skins.zip内名为theme/的文件夹。我尝试了以下代码,但没有奏效。

$zip = new ZipArchive;
if ($zip->open('skins.zip') === TRUE) {
        $zip->deleteName('yellow/theme/');
        $zip->close();
}

请问谁能帮我?

我只有以下代码,并留下了print_r输出供您了解发生了什么:

$z = new ZipArchive;
$folder_to_delete = "gifresizer/resized/";  //folder to delete relative to root
if($z->open("gifresizer.zip")===TRUE){      //zip file name
    print_r($z);
    for($i=0;$i<$z->numFiles;$i++){
        $entry_info = $z->statIndex($i);
        print_r($entry_info);
        if(substr($entry_info["name"],0,strlen($folder_to_delete))==$folder_to_delete){
            $z->deleteIndex($i);
        }
    }
}

它输出如下内容:

ZipArchive Object
(
    [status] => 0
    [statusSys] => 0
    [numFiles] => 10
    [filename] => C:'xampp'htdocs'test'zipdelete'gifresizer.zip
    [comment] => 
)
Array
(
    [name] => gifresizer/
    [index] => 0
    [crc] => 0
    [size] => 0
    [mtime] => 1339360746
    [comp_size] => 0
    [comp_method] => 0
)
Array
(
    [name] => gifresizer/frames/
    [index] => 1
    [crc] => 0
    [size] => 0
    [mtime] => 1328810540
    [comp_size] => 0
    [comp_method] => 0
)
Array
(
    [name] => gifresizer/gifresizer.php
    [index] => 2
    [crc] => 1967518989
    [size] => 18785
    [mtime] => 1328810430
    [comp_size] => 3981
    [comp_method] => 8
)
etc..

试试

$zip->deleteName('./yellow/theme/');

这是我使用的方法(基于Taha Paksu的回答),带有php8风格:

/**
 * Removes an entry from an existing zip file.
 *
 * The name is the relative path of the entry to remove (relative to the zip's root).
 *
 *
 * @param string $zipFile
 * @param string $name
 * @param bool $isDir
 * @throws 'Exception
 */
public static function deleteFromZip(string $zipFile, string $name, bool $isDir)
{
    $zip = new 'ZipArchive();
    if (true !== ($res = $zip->open($zipFile))) {
        throw new 'RuntimeException("Could not open the zipFile: " . $zip->getStatusString());
    }

    $name = rtrim($name, DIRECTORY_SEPARATOR);
    if (true === $isDir) {
        $name .= DIRECTORY_SEPARATOR;
    }
    for ($i = 0; $i < $zip->numFiles; $i++) {
        $info = $zip->statIndex($i);
        if (true === str_starts_with($info['name'], $name)) {
            $zip->deleteIndex($i);
        }
    }
    $zip->close();
}