shutil.make_archive 线程安全吗?

Posted

技术标签:

【中文标题】shutil.make_archive 线程安全吗?【英文标题】:Is shutil.make_archive thread safe? 【发布时间】:2017-01-13 00:51:56 【问题描述】:

我正在尝试使用 python 中的线程使用 shutil.make_archive 压缩多个文件夹。我看到较小的文件夹完全压缩,同时另一个线程也停止压缩。

那么,

【问题讨论】:

【参考方案1】:

shutil.make_archive() 不是线程安全的。

它的原因是它改变了当前工作目录,该目录对进程来说是全局的。线程没有自己的工作目录。见 Python 2.7 中的相关代码:

save_cwd = os.getcwd()
if root_dir is not None:
    if logger is not None:
        logger.debug("changing into '%s'", root_dir)
    base_name = os.path.abspath(base_name)
    if not dry_run:
        os.chdir(root_dir)

if base_dir is None:
    base_dir = os.curdir
...

该函数在执行开始时保存当前工作目录并在返回之前恢复它,但这对于线程安全来说是不够的。

【讨论】:

shutil.make_archive 是否有任何线程安全的替代方案? @Andrey 我用线程安全的替代方法发布了一个答案【参考方案2】:

这是基于this answer 的shutil.make_archive线程安全替代方案

import zipfile
import os

def make_archive_threadsafe(zip_name: str, path: str):
    with zipfile.ZipFile(zip_name, 'w', zipfile.ZIP_DEFLATED) as zip:
        for root, dirs, files in os.walk(path):
            for file in files:
                zip.write(os.path.join(root, file), os.path.relpath(os.path.join(root, file), path))

make_archive_threadsafe('/root/backup.zip', '/root/some_data/')

请注意,make_archive 在内部也使用ZipFile,所以这应该是可靠的。

这不包括文件夹到 zip 到 zip(“单个***文件夹”),这与我链接的答案不同 - 个人喜好。

代码是 Python 3,但如果您删除类型注释,则可以在 Python 2 中使用。

【讨论】:

以上是关于shutil.make_archive 线程安全吗?的主要内容,如果未能解决你的问题,请参考以下文章

shutil make_archive导致嵌套的.zip文件[重复]

shutil make_archive 导致嵌套的 .zip 文件 [重复]

python内置库--shutil

shutil模块——压缩目录文件

python_shutil模块

如何使用 Python 创建文件路径的 zip 文件,包括空目录?