是否可以从python中的tar包中提取单个文件

时间:2013-12-06 22:44:20

标签: python git svn

我需要从一个庞大的svn repo中获取几个文件。整个回购需要花费近一个小时的时间。我正在寻找的文件是tar包的一部分。

是否可以从tar包中仅获取这两个文件,而无需通过Python代码提取整个包?

如果是这样,任何人都可以让我知道我应该怎么做?

3 个答案:

答案 0 :(得分:1)

也许你想要这样的东西?

#!/usr/local/cpython-3.3/bin/python

import tarfile as tarfile_mod

def main():
    tarfile = tarfile_mod.TarFile('tar-archive.tar', 'r')
    if False:
        file_ = tarfile.extractfile('etc/protocols')
        print(file_.read())
    else:
        tarfile.extract('etc/protocols')
    tarfile.close()

main()

答案 1 :(得分:1)

以下是从svn获取tar文件并从中提取一个文件的一种方法:

import tarfile
from subprocess import check_output
# Capture the tar file from subversion
tmp='/home/me/tempfile.tar'
open(tmp, 'wb').write(check_output(["svn", "cat", "svn://url/some.tar"]))
# Extract the file we want, saving to current directory
tarfile.open(tmp).extract('dir1/fname.ext', path='dir2')

其中'dir1 / fname.ext'是tar存档中所需文件的完整路径。它将保存在'dir2 / dir1 / fname.ext'中。如果省略path参数,它将保存在当前目录下的“dir1 / fname.ext”中。

以上可以理解如下。在普通的shell命令行中,svn cat url告诉subversion将url定义的文件发送到stdout(有关详细信息,请参阅svn help cat)。 url可以是svn理解的任何类型的网址,例如svn://...svn+ssh://...file://...。我们使用子进程模块在python控件下运行此命令。为此,svn cat url命令被分解为一个列表:["svn", "cat", "url"]。此svn命令的输出将保存到tmp变量定义的本地文件中。然后,我们使用tarfile模块来提取所需的文件。

或者,您可以使用extractfile方法将文件数据捕获到python变量:

handle = t.extractfile('dir1/fname.ext')
print handle.readlines() # show file contents

根据文档,tarfile应该接受子进程的stdout作为文件句柄。这将简化代码并消除在本地保存tar文件的需要。但是,由于某个错误Issue 10436,这将无效。

答案 2 :(得分:1)

听起来你的问题有两个部分:

  1. 从SVN repo中获取单个tar包,而没有其余的repo文件。
  2. 使用Python从检索到的包中提取两个文件。
  3. 对于第一部分,我只需参考svn export上的this post和稀疏结帐。

    对于第二部分,这是一个从检索到的tarball中提取两个文件的解决方案:

    import tarfile
    
    files_i_want = ['path/to/file1','path/to/file2']
    
    tar = tarfile.open("bundle.tar")
    tar.extractall(members=[x for x in tar.getmembers() if x.name in files_i_want])