cantera/site_scons/site_tools/recursiveInstall.py

84 lines
2.1 KiB
Python

import os
import re
def RecursiveInstall(env, target, dir, exclude=None):
"""
This tool adds the builder:
env.RecursiveInstall(target, path)
This is useful for doing:
k = env.RecursiveInstall(dir_target, dir_source)
and if any thing in dir_source is updated the install is rerun
'exclude' is a list of regular expression patterns for files
to skip, e.g. ['\\.o$', '^~']
It behaves similar to the env.Install builtin. However it expects
two directories and correctly sets up the dependencies between each
sub file instead of just between the two directories.
Note in also traverses the in memory node tree for the source
directory and can detect things that are not built yet. Internally
we use the env.Glob function for this support.
You can see the effect of this function by doing:
scons --tree=all,prune
and see the one to one correspondence between source and target
files within each directory.
"""
if exclude:
excludePatterns = [re.compile(e) for e in exclude]
else:
excludePatterns = []
nodes = _recursive_install(env, dir, excludePatterns)
dir = env.Dir(dir).abspath
target = env.Dir(target).abspath
l = len(dir) + 1
relnodes = [n.abspath[l:] for n in nodes]
out = []
for n in relnodes:
t = os.path.join(target, n)
s = os.path.join(dir, n)
out.extend(env.InstallAs(env.File(t), env.File(s)))
return out
def _recursive_install(env, path, exclude):
""" Helper function for RecursiveInstall """
nodes = env.Glob(os.path.join(path, '*'), strings=False)
nodes.extend(env.Glob(os.path.join(path, '*.*'), strings=False))
out = []
for n in nodes:
skip = False
for e in exclude:
if e.search(n.name):
skip = True
break
if skip:
continue
if n.isdir():
out.extend(_recursive_install(env, n.abspath, exclude))
else:
out.append(n)
return out
def generate(env, **kw):
env.AddMethod(RecursiveInstall)
def exists(env):
return True