您可以创建一个 SCons Builder 来完成此任务。我们可以使用标准的 Python zipfile 来制作 zip 文件。我们利用zipfile.write
,它允许我们指定要添加的文件,以及在 zip 中应该调用的文件:
zf.write('foo/bar', 'bar') # save foo/bar as bar
为了获得正确的路径,我们使用os.path.relpath
基础文件的路径来查找整个文件的路径。
最后,我们使用os.walk
遍历要添加的目录的内容,并调用前面的两个函数将它们正确地添加到最终的 zip 中。
import os.path
import zipfile
def zipbetter(target, source, env):
# Open the zip file with appending, so multiple calls will add more files
zf = zipfile.ZipFile(str(target[0]), 'a', zipfile.ZIP_DEFLATED)
for s in source:
# Find the path of the base file
basedir = os.path.dirname(str(s))
if s.isdir():
# If the source is a directory, walk through its files
for dirpath, dirnames, filenames in os.walk(str(s)):
for fname in filenames:
path = os.path.join(dirpath, fname)
if os.path.isfile(path):
# If this is a file, write it with its relative path
zf.write(path, os.path.relpath(path, basedir))
else:
# Otherwise, just write it to the file
flatname = os.path.basename(str(s))
zf.write(str(s), flatname)
zf.close()
# Make a builder using the zipbetter function, that takes SCons files
zipbetter_bld = Builder(action = zipbetter,
target_factory = SCons.Node.FS.default_fs.Entry,
source_factory = SCons.Node.FS.default_fs.Entry)
# Add the builder to the environment
env.Append(BUILDERS = {'ZipBetter' : zipbetter_bld})
像普通的 SCons 一样调用它Zip
:
env.ZipBetter('foo.zip', 'foo/')