file_template =
[
{
- pattern = [ "src/scons/*__init__.py" ];
+ pattern = [ "src/engine/*__init__.py" ];
body = "${read_file ${source template/__init__.py abs}}";
},
{
- pattern = [ "src/scons/*Tests.py" ];
+ pattern = [ "src/engine/*Tests.py" ];
body = "${read_file ${source template/Tests.py abs}}";
},
{
- pattern = [ "src/scons/*.py" ];
+ pattern = [ "src/engine/*.py" ];
body = "${read_file ${source template/file.py abs}}";
},
{
SCons/Sig/__init__.py
SCons/Sig/MD5.py
SCons/Sig/TimeStamp.py
+SCons/Util.py
setup.py
import copy
import re
import types
+import SCons.Util
_cv = re.compile(r'%([_a-zA-Z]\w*|{[_a-zA-Z]\w*})')
-_self = None
"""
self.Dictionary.update(copy.deepcopy(kw))
+ def Depends(self, target, dependency):
+ """Explicity specify that 'target's depend on 'dependency'."""
+ tlist = SCons.Util.scons_str2nodes(target)
+ dlist = SCons.Util.scons_str2nodes(dependency)
+ for t in tlist:
+ t.add_dependency(dlist)
+
+ if len(tlist) == 1:
+ tlist = tlist[0]
+ return tlist
+
def subst(self, string):
"""Recursively interpolates construction variables from the
Environment into the specified string, returning the expanded
may be surrounded by curly braces to separate the name from
trailing characters.
"""
- global _self
- _self = self # XXX NOT THREAD SAFE, BUT HOW ELSE DO WE DO THIS?
- def repl(m):
+ def repl(m, _self=self):
key = m.group(1)
if key[:1] == '{' and key[-1:] == '}':
key = key[1:-1]
env2 = Environment(AAA = 'a', BBB = 'bbb', CCC = 'c')
assert env1 != env2
+ def test_Depends(self):
+ """Test the explicit Depends method."""
+ env = Environment()
+ t = env.Depends(target='EnvironmentTest.py', dependency='Environment.py')
+ assert t.__class__.__name__ == 'File'
+ assert t.path == 'EnvironmentTest.py'
+ assert len(t.depends) == 1
+ d = t.depends[0]
+ assert d.__class__.__name__ == 'File'
+ assert d.path == 'Environment.py'
+
def test_subst(self):
"""Test substituting construction variables within strings
"""
def __init__(self, name, directory = None):
+ Node.__init__(self)
+
self.entries = PathDict()
self.entries['.'] = self
"""
def __init__(self, name, directory):
+ Node.__init__(self)
+
self.abspath = os.path.join(directory.abspath, name)
if str(directory.path) == '.':
self.path = name
built_it = None
assert not built_it
d1.path = "d" # XXX FAKE SUBCLASS ATTRIBUTE
- d1.sources = "d" # XXX FAKE SUBCLASS ATTRIBUTE
+ d1.add_source(["d"]) # XXX FAKE SUBCLASS ATTRIBUTE
d1.builder_set(Builder())
d1.build()
assert built_it
built_it = None
assert not built_it
f1.path = "f" # XXX FAKE SUBCLASS ATTRIBUTE
- f1.sources = "f" # XXX FAKE SUBCLASS ATTRIBUTE
+ f1.add_source(["f"]) # XXX FAKE SUBCLASS ATTRIBUTE
f1.builder_set(Builder())
f1.build()
assert built_it
"""The base Node class, for entities that we know how to
build, or use to build other Nodes.
"""
+
+ def __init__(self):
+ self.depends = []
+ self.sources = []
+ self.env = None
+
def build(self):
self.builder.execute(target = self.path, source = self.sources)
def get_signature(self):
return self.signature
+ def add_dependency(self, depend):
+ """Adds dependencies. The depends argument must be a list."""
+ self.depends.extend(depend)
+
+ def add_source(self, source):
+ """Adds sources. The source argument must be a list."""
+ self.sources.extend(source)
--- /dev/null
+"""SCons.Util
+
+Various utility functions go here.
+
+"""
+
+__revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__"
+
+
+import types
+import string
+import SCons.Node.FS
+
+def scons_str2nodes(arg, fs=SCons.Node.FS.default_fs):
+ """This function converts a string or list into a list of Node instances.
+ It follows the rules outlined in the SCons design document by accepting
+ any of the following inputs:
+ - A single string containing names separated by spaces. These will be
+ split apart at the spaces.
+ - A single Node instance,
+ - A list containingg either strings or Node instances. Any strings
+ in the list are not split at spaces.
+ In all cases, the function returns a list of Node instances."""
+
+ narg = arg
+ if type(arg) is types.StringType:
+ narg = string.split(arg)
+ elif type(arg) is not types.ListType:
+ narg = [arg]
+
+ nodes = []
+ for v in narg:
+ if type(v) is types.StringType:
+ nodes.append(fs.File(v))
+ elif issubclass(v.__class__, SCons.Node.Node):
+ nodes.append(v)
+ else:
+ raise TypeError
+
+ return nodes
--- /dev/null
+__revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__"
+
+import sys
+import unittest
+import SCons.Node.FS
+from SCons.Util import scons_str2nodes
+
+
+class UtilTestCase(unittest.TestCase):
+ def test_str2nodes(self):
+ """Test the str2nodes function."""
+ nodes = scons_str2nodes("Util.py UtilTests.py")
+ assert len(nodes) == 2
+ assert isinstance(nodes[0], SCons.Node.FS.File)
+ assert isinstance(nodes[1], SCons.Node.FS.File)
+ assert nodes[0].path == "Util.py"
+ assert nodes[1].path == "UtilTests.py"
+
+ nodes = scons_str2nodes("Util.py UtilTests.py", SCons.Node.FS.FS())
+ assert len(nodes) == 2
+ assert isinstance(nodes[0], SCons.Node.FS.File)
+ assert isinstance(nodes[1], SCons.Node.FS.File)
+ assert nodes[0].path == "Util.py"
+ assert nodes[1].path == "UtilTests.py"
+
+ nodes = scons_str2nodes(["Util.py", "UtilTests.py"])
+ assert len(nodes) == 2
+ assert isinstance(nodes[0], SCons.Node.FS.File)
+ assert isinstance(nodes[1], SCons.Node.FS.File)
+ assert nodes[0].path == "Util.py"
+ assert nodes[1].path == "UtilTests.py"
+
+ n1 = SCons.Node.FS.default_fs.File("Util.py")
+ nodes = scons_str2nodes([n1, "UtilTests.py"])
+ assert len(nodes) == 2
+ assert isinstance(nodes[0], SCons.Node.FS.File)
+ assert isinstance(nodes[1], SCons.Node.FS.File)
+ assert nodes[0].path == "Util.py"
+ assert nodes[1].path == "UtilTests.py"
+
+
+if __name__ == "__main__":
+ suite = unittest.makeSuite(UtilTestCase, 'test_')
+ if not unittest.TextTestRunner().run(suite).wasSuccessful():
+ sys.exit(1)