我试图将源文件目录中的多个头文件复制到' includes'使用scons在我的构建目录中的目录。我的目标是一个静态库,我想将它与相关的标题一起分发。预期的最终结果:
build
|-- objects -> .o output files for constructing libmclib.a
|-- includes
| |-- foo.h
| `-- bar.h
`-- libmclib.a
我的SConstruct:
#!python
target = 'mock'
env = Environment(LINKCOM = "$LINK -o $TARGET $SOURCES $LINKFLAGS $CCFLAGS")
Export('env', 'target')
build_base = 'build'
SConscript('SConscript', variant_dir=build_base, duplicate=0)
# remove build directory
if GetOption('clean'):
import subprocess
subprocess.call(['rm', '-rf', build_base])
我的SConscript:
#!python
Import('env')
# ...
# other stuff to build 'mclib_target'
# ...
def copy_header_files(target, source, env):
Mkdir(target)
header_files = []
for d in env['CPPPATH']:
header_files += Glob(d + "/*.h")
for f in header_files:
Copy(target, f)
# copy all relevant header files
env.Command("includes", mclib_target, copy_header_files)
Scons确实致电' copy_header_files'有参数' [" build / includes"],[" build / libmclib.a"]',但出于某种原因' Mkdir'不会创建包含目录。另外'复制'好像什么也没做。但是,如果我这样称呼Mkdir:
env.Command("includes", mclib_target, [Mkdir('$TARGET')])
它似乎运作良好。如何解决/解决这个问题?我对Scons也很陌生,所以欢迎任何替代方案来完成这项任务。我使用scons 2.5.0。
答案 0 :(得分:6)
您可能希望使用“Install()
”代替“Copy()
”。此外,Mkdir()
不是必需的,SCons会自动为其目标创建所有中间文件夹。
最后,请允许我对您的一般方法提出一些意见:我宁愿不将“建筑”与“安装/准备包装”混在一起。 “variant_dir
”选项可以帮助您从相同的源文件构建多个“变体”(发布,优化,调试,特定于ARM,...)(假设您有一个名为“src”的文件夹) “)。通过将当前“build”目录的名称传递到“src”SConscript中,您将特定于变体的知识嵌入到本地构建描述中,这意味着您必须使用您添加的每个变体来触摸它。
相反,您应该将“Install/Package
”步骤移动到顶级SConstruct ......您可以全面了解构建哪些变体。从那里你可以将最终文件复制(=安装)到一个单独的子文件夹,例如distribution
,并将其存档。
有关如何在SCons中处理变体的简单示例,请查看repo https://bitbucket.org/dirkbaechle/scons_talks以及“pyconde_2013/examples/exvar
”文件夹。
答案 1 :(得分:1)
您正在使用的 Mkdir 和 Copy 操作是用于命令定义的Action工厂,如Platform-Independent File System Manipulation中所述:
SCons提供了许多与平台无关的功能,称为 工厂,执行常见的文件系统操作,如复制, 移动或删除文件和目录,或制作目录。的这些 功能是工厂,因为他们不会在工作中执行操作 他们被调用的时间,他们每个都返回一个可以的Action对象 在适当的时间执行。
我一直在尝试在自己的动作函数中使用这些函数时遇到问题。也许我错过了一些东西,但我不认为这些函数可以在命令构建器中的操作列表之外使用。
相反,我使用python中与平台无关的函数来创建目录和复制文件,例如os.makedirs
和shutil.copy
。