pin_drop当前位置:知识文库 ❯ 图文

Python shutil.unpack_archive详解 - 解压归档文件教程

一、概述

shutil.unpack_archive()make_archive() 的对应函数,用于解压归档文件到指定目录。它支持 zip、tar、gztar、bztar、xztar 等格式,能够自动识别归档格式并解压。unpack_archive() 是快速解压归档文件的标准工具。


二、语法与参数说明

语法

代码示例

import shutil

shutil.unpack_archive(filename, extract_dir=None, format=None)

参数说明

参数 类型 默认值 说明
filename str/PathLike 必填 归档文件路径
extract_dir str/PathLike '.' 解压目标目录
format str None 归档格式,None则自动识别

返回值

没有返回值。


三、代码示例

示例1:解压ZIP文件

代码示例

import shutil
import os

# 先创建归档
os.makedirs('src_data', exist_ok=True)
with open('src_data/info.txt', 'w') as f:
    f.write('Hello from archive!')
archive = shutil.make_archive('test_archive', 'zip', base_dir='src_data')

# 解压
os.makedirs('extracted', exist_ok=True)
shutil.unpack_archive(archive, 'extracted')

# 验证
print(f"解压成功: {os.path.exists('extracted/info.txt')}")
with open('extracted/info.txt', 'r') as f:
    print(f"内容: {f.read()}")

# 清理
os.remove(archive)
shutil.rmtree('src_data')
shutil.rmtree('extracted')

输出:

代码示例

解压成功: True
内容: Hello from archive!

示例2:自动识别格式

代码示例

import shutil
import os

# 创建测试目录和归档
os.makedirs('pack_me', exist_ok=True)
with open('pack_me/data.csv', 'w') as f:
    f.write('id,name\n1,Alice')

# 创建不同格式的归档
zip_archive = shutil.make_archive('data_zip', 'zip', base_dir='pack_me')
gztar_archive = shutil.make_archive('data_gz', 'gztar', base_dir='pack_me')

# 自动识别格式解压
shutil.unpack_archive(zip_archive, 'zip_out')
shutil.unpack_archive(gztar_archive, 'gz_out')

print(f"ZIP解压: {os.path.exists('zip_out/data.csv')}")
print(f"GZTAR解压: {os.path.exists('gz_out/data.csv')}")

# 清理
for f in [zip_archive, gztar_archive]:
    os.remove(f)
for d in ['pack_me', 'zip_out', 'gz_out']:
    shutil.rmtree(d)

输出:

代码示例

ZIP解压: True
GZTAR解压: True

示例3:打包-解压完整流程

代码示例

import shutil
import os

# 创建项目
os.makedirs('project/src', exist_ok=True)
with open('project/src/app.py', 'w') as f:
    f.write('print("v2.0")')
with open('project/README.md', 'w') as f:
    f.write('# v2.0 Release')

# 打包
archive = shutil.make_archive('project_v2', 'zip', base_dir='project')
print(f"打包: {archive}")

# 模拟传输后解压
deploy_dir = 'deploy'
shutil.unpack_archive(archive, deploy_dir)

# 验证部署
print(f"部署文件: {sorted(os.listdir(deploy_dir))}")
with open(f'{deploy_dir}/src/app.py', 'r') as f:
    print(f"应用代码: {f.read().strip()}")

# 清理
os.remove(archive)
shutil.rmtree('project')
shutil.rmtree(deploy_dir)

输出:

代码示例

打包: e:\...\project_v2.zip
部署文件: ['README.md', 'src']
应用代码: print("v2.0")

四、实际应用场景

  • 部署解压:将打包好的发布文件解压到部署目录。

  • 数据恢复:从备份归档文件中恢复数据。

  • 安装包处理:解压下载的安装包或数据包。


五、注意事项

注意1format=None 时自动根据文件扩展名识别格式。如果扩展名不标准,需手动指定 format

注意2:解压会覆盖目标目录中的同名文件,注意数据安全。

注意3:解压恶意构造的归档文件可能导致路径遍历攻击,不要解压不信任来源的归档。

提示unpack_archive()make_archive() 是配对使用的,建议使用相同格式进行打包和解压。


六、解压方法对比

对比项 unpack_archive zipfile.extractall tarfile.extractall
格式支持 多种 仅ZIP 仅TAR系列
自动识别 支持 不适用 不适用
易用性 最高
灵活性
安全性 一般 可控制 可控制

七、小结

  • unpack_archive() 解压归档文件,支持多种格式自动识别

  • extract_dir 指定解压目标目录,默认为当前目录

  • make_archive() 配对使用,建议使用相同格式

  • 注意解压安全和同名文件覆盖问题


八、练习题

练习1

编写一个函数,先打包指定目录,然后解压到另一个目录,最后对比两个目录的文件是否一致。

练习2

使用 format 参数手动指定归档格式,测试当文件扩展名与实际格式不匹配时的行为。

练习3

编写一个安全的解压函数,在解压前检查归档中的文件路径,防止路径遍历攻击。


常见问题

unpack_archive 如何自动识别归档格式?

当 format=None(默认值)时,unpack_archive 会根据文件扩展名自动识别归档格式。例如 .zip 识别为 zip,.tar.gz 识别为 gztar。如果文件扩展名不标准或无法识别,会抛出 ValueError 异常。

解压时会覆盖已存在的文件吗?

是的。解压会覆盖目标目录中的同名文件。如果需要保留已有文件,建议在解压前检查目标目录是否为空,或将文件解压到一个新的空目录中。

什么是路径遍历攻击?如何防范?

路径遍历攻击是指恶意构造的归档文件中包含类似 ../../etc/passwd 的路径,解压时会写入到非预期目录。防范措施包括:使用 zipfile/tarfile 模块手动检查每个文件路径是否安全,确保所有解压路径都在目标目录内,不包含 .. 等危险字符。

unpack_archive 和 make_archive 有什么关系?

它们是一对互补的函数:make_archive 用于创建归档文件,unpack_archive 用于解压归档文件。两者支持相同的格式(zip、tar、gztar 等),建议配对使用相同的格式以确保兼容性。

解压后如何验证文件完整性?

可以在解压后通过对比文件数量、文件大小或使用哈希校验(如 MD5、SHA256)来验证文件完整性。如果需要更严格的校验,可以在打包时生成校验文件(如 .sha256),解压后进行校验对比。

标签: shutil unpack_archive 解压文件 ZIP解压 数据恢复 Python教程

本文涉及AI创作

内容由AI创作,请仔细甄别

list快速访问

上一篇: Python shutil.make_archive详解 - 目录打包归档教程 下一篇: Python tempfile模块详解 - 临时文件与目录创建指南

poll相关推荐