Zipfile.ZipFile.extract: примеры (PYTHON)
zipfile.ZipFile.extract(member, path, pwd): strОписание функции ZipFile.extract
Метод extract() принадлежит классу zipfile.ZipFile и предназначен для извлечения отдельного файла из ZIP-архива в файловую систему. Применение метода требуется в случаях, когда необходим выборочный доступ к содержимому архива без полной его распаковки.
Сигнатура метода: ZipFile.extract(member, path=None, pwd=None)
Аргументы:
- member (обязательный) – определяет файл для извлечения. Может быть строкой с именем файла в архиве или объектом ZipInfo.
- path (опциональный) – путь к целевой директории для извлечения. По умолчанию используется текущая рабочая директория (None). Если указанный путь не существует, он будет создан.
- pwd (опциональный) – байтовая строка с паролем для расшифровки зашифрованных файлов. Для архивов, созданных в старых версиях Python, может потребоваться строковый тип.
Возвращаемое значение: метод возвращает абсолютный путь к извлеченному файлу в виде строки.
Метод выполняет проверки на безопасность, предотвращая атаки типа "Zip Slip", которые пытаются записать файлы за пределами целевой директории.
Краткие примеры использования
Пример 1: Базовое извлечение файла.
import zipfile
with zipfile.ZipFile('archive.zip', 'r') as zf:
extracted_path = zf.extract('document.txt')
print(extracted_path)C:\Projects\document.txt
Пример 2: Извлечение файла в указанную директорию.
import zipfile
with zipfile.ZipFile('archive.zip', 'r') as zf:
extracted_path = zf.extract('image.jpg', path='output/images')
print(extracted_path)C:\Projects\output\images\image.jpg
Пример 3: Использование пароля для зашифрованного архива.
import zipfile
with zipfile.ZipFile('encrypted.zip', 'r') as zf:
extracted_path = zf.extract('secret.txt', pwd=b'my_password')
print(extracted_path)C:\Projects\secret.txt
Похожие функции в Python
1. ZipFile.extractall() – извлекает все файлы из архива сразу. Предпочтительнее использовать, когда требуется полная распаковка всего содержимого архива. Метод extract более эффективен для выборочного извлечения.
2. ZipFile.read() – читает содержимое файла из архива и возвращает его в виде байтовой строки, не создавая файлов на диске. Удобен для обработки данных непосредственно в памяти, например, для парсинга CSV или JSON из архива.
3. shutil.unpack_archive() – высокоуровневая функция для распаковки различных форматов архивов (ZIP, TAR, GZTAR и др.). Подходит для простых сценариев, где не требуется тонкого контроля над процессом извлечения.
Аналоги в других языках программирования
Java (java.util.zip.ZipFile): требует более многословного кода, работа ведется через потоки ввода-вывода.
import java.util.zip.ZipFile;
import java.io.*;
public class Main {
public static void main(String[] args) throws IOException {
ZipFile zipFile = new ZipFile("archive.zip");
zipFile.stream().forEach(entry -> {
try {
InputStream is = zipFile.getInputStream(entry);
Files.copy(is, Paths.get("output/" + entry.getName()));
} catch (IOException e) { e.printStackTrace(); }
});
zipFile.close();
}
}JavaScript (Node.js, библиотека adm-zip): работа с архивами через сторонние библиотеки.
const AdmZip = require('adm-zip');
const zip = new AdmZip('archive.zip');
zip.extractEntryTo('document.txt', './output', false, true);PHP (ZipArchive): интерфейс, похожий на Python, но с использованием префикса методов.
$zip = new ZipArchive;
if ($zip->open('archive.zip') === TRUE) {
$zip->extractTo('./output', ['document.txt']);
$zip->close();
}C# (System.IO.Compression.ZipFileExtensions): метод ExtractToFile в пространстве имен System.IO.Compression.
using System.IO.Compression;
using (ZipArchive archive = ZipFile.OpenRead("archive.zip"))
{
archive.GetEntry("document.txt").ExtractToFile("./output/document.txt");
}Основное отличие Python-реализации заключается в использовании контекстного менеджера (with) для автоматического управления ресурсами и более лаконичном синтаксисе.
Типичные ошибки при использовании
1. KeyError при отсутствии файла в архиве.
import zipfile
try:
with zipfile.ZipFile('archive.zip', 'r') as zf:
zf.extract('missing_file.txt')
except KeyError as e:
print(f"Файл не найден в архиве: {e}")Файл не найден в архиве: 'missing_file.txt'
2. RuntimeError при неверном пароле для зашифрованного архива.
import zipfile
try:
with zipfile.ZipFile('encrypted.zip', 'r') as zf:
zf.extract('file.txt', pwd=b'wrong_password')
except RuntimeError as e:
print(f"Ошибка распаковки: {e}")Ошибка распаковки: Bad password for file 'file.txt'
3. FileNotFoundError при отсутствии архива.
import zipfile
try:
with zipfile.ZipFile('nonexistent.zip', 'r') as zf:
zf.extract('file.txt')
except FileNotFoundError as e:
print(f"Архив не найден: {e}")Архив не найден: [Errno 2] No such file or directory: 'nonexistent.zip'
4. ValueError при попытке извлечения файла с помощью объекта ZipInfo, не принадлежащего текущему архиву.
Изменения в последних версиях
В Python 3.11 в модуль zipfile было добавлено улучшение, касающееся работы с паролями. В более ранних версиях, при использовании метода extract() с неверным паролем, возникало общее исключение RuntimeError. В Python 3.11 добавлена более конкретная ошибка zipfile.BadZipFile с уточняющим сообщением для случаев неверного пароля.
В Python 3.6 были улучшены механизмы безопасности, предотвращающие атаки типа Zip Slip. Метод extract() стал более строго проверять пути извлечения файлов.
С Python 3.4 метод extract() и другие методы класса ZipFile стали возвращать путь в кодировке файловой системы, что улучшило обработку путей с не-ASCII символами на Windows.
Расширенные примеры использования
Пример 1: Извлечение файла с использованием объекта ZipInfo. Это может быть полезно при работе с метаданными файлов в архиве.
import zipfile
import os
with zipfile.ZipFile('archive.zip', 'r') as zf:
# Получаем объект ZipInfo для файла
file_info = zf.getinfo('data.csv')
print(f"Имя файла: {file_info.filename}")
print(f"Размер сжатого файла: {file_info.compress_size} байт")
print(f"Исходный размер: {file_info.file_size} байт")
# Извлекаем с использованием объекта ZipInfo
extracted_path = zf.extract(file_info, path='extracted_data')
print(f"Извлечен в: {extracted_path}")Имя файла: data.csv Размер сжатого файла: 1024 байт Исходный размер: 2048 байт Извлечен в: C:\Projects\extracted_data\data.csv
Пример 2: Извлечение файла с переименованием в целевой директории. Метод extract не поддерживает прямое переименование, поэтому можно использовать комбинацию с os.rename.
import zipfile
import os
with zipfile.ZipFile('archive.zip', 'r') as zf:
# Извлекаем файл во временное расположение
temp_path = zf.extract('old_name.txt', path='temp')
# Переименовываем извлеченный файл
new_path = os.path.join('temp', 'new_name.txt')
os.rename(temp_path, new_path)
print(f"Файл переименован: {new_path}")Файл переименован: temp/new_name.txt
Пример 3: Безопасное извлечение файлов с проверкой пути. Демонстрация встроенной защиты от Zip Slip атак.
import zipfile
# Создаем архив с потенциально опасным именем файла
with zipfile.ZipFile('malicious.zip', 'w') as zf:
zf.writestr('../../dangerous.txt', 'harmful content')
# Попытка извлечения опасного файла
with zipfile.ZipFile('malicious.zip', 'r') as zf:
try:
zf.extract('../../dangerous.txt')
except Exception as e:
print(f"Безопасность: {type(e).__name__}: {e}")Безопасность: ValueError: '../../dangerous.txt' является абсолютным или выходит за пределы целевого каталога
Пример 4: Извлечение файлов из вложенных директорий архива. Метод extract корректно обрабатывает пути с поддиректориями.
import zipfile
import os
# Создаем архив с вложенной структурой
with zipfile.ZipFile('nested.zip', 'w') as zf:
zf.writestr('folder/subfolder/file.txt', 'Содержимое файла')
# Извлекаем файл из вложенной директории
with zipfile.ZipFile('nested.zip', 'r') as zf:
extracted_path = zf.extract('folder/subfolder/file.txt', path='output')
# Проверяем существование файла
if os.path.exists(extracted_path):
print(f"Файл успешно извлечен: {extracted_path}")
# Проверяем, что структура каталогов создана
print("Существует ли директория 'output/folder/subfolder':",
os.path.exists('output/folder/subfolder'))Файл успешно извлечен: output/folder/subfolder/file.txt Существует ли директория 'output/folder/subfolder': True
Пример 5: Пакетное извлечение нескольких файлов по условию. Извлечение только файлов с определенным расширением.
import zipfile
with zipfile.ZipFile('project.zip', 'r') as zf:
# Получаем список всех файлов в архиве
all_files = zf.namelist()
# Фильтруем только Python файлы
python_files = [f for f in all_files if f.endswith('.py')]
# Извлекаем каждый Python файл
for py_file in python_files:
extracted_path = zf.extract(py_file, path='python_code')
print(f"Извлечен: {py_file} -> {extracted_path}")Извлечен: main.py -> python_code/main.py Извлечен: utils/helpers.py -> python_code/utils/helpers.py
питон zipfile.ZipFile.extract function comments
- питон zipfile.ZipFile.extract - аргументы и возвращаемое значение
- Функция python zipfile.ZipFile.extract - описание
- zipfile.ZipFile.extract - примеры
- zipfile.ZipFile.extract - похожие методы на python
- zipfile.ZipFile.extract на php, c#, sql, java
- zipfile.ZipFile.extract изменения python
- Примеры zipfile.ZipFile.extract на питон