When working with ZIP archives, especially those containing multi-level directory structures, it is crucial to ensure the target directories exist. Otherwise, writing files may fail due to missing paths. This article demonstrates how to use the zip_read() function to read each entry in a ZIP file and combine it with file_exists() and mkdir() to automatically create the necessary directories, achieving a reliable file extraction process.
Make sure your PHP environment has the zip extension enabled. You can check it using the following code:
<?php
if (!class_exists('ZipArchive')) {
die('Zip extension is not enabled');
}
?>
Below is a complete example that reads files and directories from a ZIP archive and automatically creates the directory structure:
<?php
$zipPath = 'example.zip'; // Path to the ZIP file
$extractTo = 'output/'; // Extraction directory
<p>$zip = zip_open($zipPath);<br>
if (!is_resource($zip)) {<br>
die('Unable to open ZIP file');<br>
}</p>
<p>while ($entry = zip_read($zip)) {<br>
$entryName = zip_entry_name($entry);<br>
$fullPath = $extractTo . $entryName;</p>
$dir = dirname($fullPath);
// Automatically create the directory
if (!file_exists($dir)) {
mkdir($dir, 0777, true);
}
// If the entry is a file, read its content and write it
if (zip_entry_open($zip, $entry, "r")) {
$content = zip_entry_read($entry, zip_entry_filesize($entry));
file_put_contents($fullPath, $content);
zip_entry_close($entry);
}
}
zip_close($zip);
?>
zip_open()
Used to open a ZIP file and returns a resource handle.
zip_read() and zip_entry_name()
Reads entries from the ZIP archive one by one using zip_read(), then obtains each entry's relative path via zip_entry_name().
dirname() extracts the directory path
Whether the entry is a file or directory, dirname() extracts the path portion to check if the directory exists.
Using file_exists() and mkdir() together
file_exists() checks whether the directory already exists;
mkdir() with the third parameter set to true creates directories recursively.
Writing file content
If the current entry is a file, open it, read its contents, and write it to the target path.
Suppose you downloaded a ZIP archive from http://m66.net/files/archive.zip and want to preserve its original structure after extraction. You just need to modify the $zipPath variable like this:
$zipPath = 'http://m66.net/files/archive.zip'; // Note: zip_open does not support direct URLs; the file must be downloaded locally first
You can save the file locally using file_get_contents() and file_put_contents():
$tempZip = 'temp_archive.zip';
file_put_contents($tempZip, file_get_contents('http://m66.net/files/archive.zip'));
Then replace $zipPath with $tempZip.
By combining zip_read(), file_exists(), and mkdir(), we can efficiently extract ZIP file contents and automatically create directories without worrying about missing paths causing errors. This method is especially suitable for batch extracting ZIP files with complex directory structures, improving the robustness and usability of your scripts.