Add Repository Install() and InstallAs() functionality.
authorstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Mon, 5 Aug 2002 20:36:58 +0000 (20:36 +0000)
committerstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Mon, 5 Aug 2002 20:36:58 +0000 (20:36 +0000)
git-svn-id: http://scons.tigris.org/svn/scons/trunk@429 fdb21ef1-2011-0410-befe-b5e4ea1792b1

src/CHANGES.txt
src/engine/SCons/Environment.py
src/engine/SCons/Node/Alias.py
src/engine/SCons/Node/FS.py
src/engine/SCons/Node/NodeTests.py
src/engine/SCons/Node/__init__.py
test/Repository/Install.py [new file with mode: 0644]
test/Repository/InstallAs.py [new file with mode: 0644]

index 6e24752d4defef8fb0bc4e6673268613b14e24be..a4d91fc22690f476560bac60a4a65c9174161421 100644 (file)
 
 RELEASE 0.09 - 
 
+ From Steven Knight:
+
+ - Add Repository() functionality.
+
  From Anthony Roach:
 
  - Fixed use of command lines with spaces in their arguments,
index fea60c3fdca0bb1f1e8bc97825f2d6efbc1cd62b..99eff2e26767fdae11543f462992b111e64c5b9e 100644 (file)
@@ -334,7 +334,7 @@ class Environment:
 
     def Install(self, dir, source):
         """Install specified files in the given directory."""
-        sources = SCons.Node.arg2nodes(source, self.fs.File)
+        sources = SCons.Node.arg2Rnodes(source, self.fs.File)
         dnodes = SCons.Node.arg2nodes(dir, self.fs.Dir)
         tgt = []
         for dnode in dnodes:
@@ -347,7 +347,7 @@ class Environment:
 
     def InstallAs(self, target, source):
         """Install sources as targets."""
-        sources = SCons.Node.arg2nodes(source, self.fs.File)
+        sources = SCons.Node.arg2Rnodes(source, self.fs.File)
         targets = SCons.Node.arg2nodes(target, self.fs.File)
         ret = []
         for src, tgt in map(lambda x, y: (x, y), sources, targets):
index 276750f2ca3c7ccbdb630b397faadaf325dd75e3..73fd706f919c263fef28a7cf2b7f81f5cb6093f1 100644 (file)
@@ -99,3 +99,4 @@ class Alias(SCons.Node.Node):
 default_ans = AliasNameSpace()
 
 SCons.Node.arg2nodes_lookups.append(default_ans.lookup)
+SCons.Node.arg2Rnodes_lookups.append(default_ans.lookup)
index 8bdfeb65b23ffb031fb9a80a1e1a1a382a1f19f7..d756276057b745b4cd662264ed408a8403d67e8a 100644 (file)
@@ -109,6 +109,7 @@ class FS:
         self.Root = {}
         self.Top = None
         self.Repositories = []
+        SCons.Node.arg2Rnodes_lookups.append(self.Rsearch)
 
     def set_toplevel_dir(self, path):
         assert not self.Top, "You can only set the top-level path on an FS object that has not had its File, Dir, or Entry methods called yet."
index cbd54730acd78f7087a467915a7e0b205be00395..963fffe0ee9c8e7daa800ae4559a44c07bdec436 100644 (file)
@@ -651,6 +651,124 @@ class NodeTestCase(unittest.TestCase):
         assert not hasattr(nodes[2], 'a'), nodes[1]
         assert not hasattr(nodes[2], 'b'), nodes[1]
 
+        def lookup_bbbb(str, F=Factory):
+            if str == 'bbbb':
+                n = F(str)
+                n.bbbb = 1
+                return n
+            else:
+                return None
+
+        def lookup_c(str, F=Factory):
+            if str[0] == 'c':
+                n = F(str)
+                n.c = 1
+                return n
+            else:
+                return None
+
+        nodes = SCons.Node.arg2nodes(['bbbb', 'ccc'], Factory,
+                                     [lookup_c, lookup_bbbb, lookup_b])
+        assert len(nodes) == 2, nodes
+
+        assert nodes[0].name == 'bbbb'
+        assert not hasattr(nodes[0], 'a'), nodes[1]
+        assert not hasattr(nodes[0], 'b'), nodes[1]
+        assert nodes[0].bbbb == 1, nodes[1]
+        assert not hasattr(nodes[0], 'c'), nodes[0]
+
+        assert nodes[1].name == 'ccc'
+        assert not hasattr(nodes[1], 'a'), nodes[1]
+        assert not hasattr(nodes[1], 'b'), nodes[1]
+        assert not hasattr(nodes[1], 'bbbb'), nodes[0]
+        assert nodes[1].c == 1, nodes[1]
+
+    def test_arg2Rnodes(self):
+        """Test the arg2Rnodes function."""
+        dict = {}
+        class X(SCons.Node.Node):
+            pass
+        def Factory(name, directory = None, create = 1, dict=dict, X=X):
+            if not dict.has_key(name):
+                dict[name] = X()
+                dict[name].name = name
+            return dict[name]
+
+        nodes = SCons.Node.arg2Rnodes("Util.py UtilTests.py", Factory)
+        assert len(nodes) == 1, nodes
+        assert isinstance(nodes[0], X)
+        assert nodes[0].name == "Util.py UtilTests.py"
+
+        if hasattr(types, 'UnicodeType'):
+            code = """if 1:
+                nodes = SCons.Node.arg2Rnodes(u"Util.py UtilTests.py", Factory)
+                assert len(nodes) == 1, nodes
+                assert isinstance(nodes[0], X)
+                assert nodes[0].name == u"Util.py UtilTests.py"
+                \n"""
+            exec code in globals(), locals()
+
+        nodes = SCons.Node.arg2Rnodes(["Util.py", "UtilTests.py"], Factory)
+        assert len(nodes) == 2, nodes
+        assert isinstance(nodes[0], X)
+        assert isinstance(nodes[1], X)
+        assert nodes[0].name == "Util.py"
+        assert nodes[1].name == "UtilTests.py"
+
+        n1 = Factory("Util.py")
+        nodes = SCons.Node.arg2Rnodes([n1, "UtilTests.py"], Factory)
+        assert len(nodes) == 2, nodes
+        assert isinstance(nodes[0], X)
+        assert isinstance(nodes[1], X)
+        assert nodes[0].name == "Util.py"
+        assert nodes[1].name == "UtilTests.py"
+
+        class SConsNode(SCons.Node.Node):
+            pass
+        nodes = SCons.Node.arg2Rnodes(SConsNode())
+        assert len(nodes) == 1, nodes
+        assert isinstance(nodes[0], SConsNode), node
+
+        class OtherNode:
+            pass
+        nodes = SCons.Node.arg2Rnodes(OtherNode())
+        assert len(nodes) == 1, nodes
+        assert isinstance(nodes[0], OtherNode), node
+
+        def lookup_a(str, F=Factory):
+            if str[0] == 'a':
+                n = F(str)
+                n.a = 1
+                return n
+            else:
+                return None
+
+        def lookup_b(str, F=Factory):
+            if str[0] == 'b':
+                n = F(str)
+                n.b = 1
+                return n
+            else:
+                return None
+
+        SCons.Node.arg2Rnodes_lookups.append(lookup_a)
+        SCons.Node.arg2Rnodes_lookups.append(lookup_b)
+
+        nodes = SCons.Node.arg2Rnodes(['aaa', 'bbb', 'ccc'], Factory)
+        assert len(nodes) == 3, nodes
+
+        assert nodes[0].name == 'aaa', nodes[0]
+        assert nodes[0].a == 1, nodes[0]
+        assert not hasattr(nodes[0], 'b'), nodes[0]
+
+        assert nodes[1].name == 'bbb'
+        assert not hasattr(nodes[1], 'a'), nodes[1]
+        assert nodes[1].b == 1, nodes[1]
+
+        assert nodes[2].name == 'ccc'
+        assert not hasattr(nodes[2], 'a'), nodes[1]
+        assert not hasattr(nodes[2], 'b'), nodes[1]
+
 
 
 if __name__ == "__main__":
index a65310d8cf22b2e4f2bfd1884749265a4b24b074..3054d5e38b204dec013e0ccf1002abd906214e07 100644 (file)
@@ -465,7 +465,9 @@ class Walker:
 
 arg2nodes_lookups = []
 
-def arg2nodes(args, node_factory=None):
+arg2Rnodes_lookups = []
+
+def arg2nodes(args, node_factory=None, lookup_list=arg2nodes_lookups):
     """This function converts a string or list into a list of Node
     instances.  It accepts the following inputs:
         - A single string,
@@ -483,11 +485,13 @@ def arg2nodes(args, node_factory=None):
     for v in args:
         if SCons.Util.is_String(v):
             n = None
-            for l in arg2nodes_lookups:
+            for l in lookup_list:
                 n = l(v)
                 if not n is None:
                     break
             if not n is None:
+                if SCons.Util.is_String(n) and node_factory:
+                    n = node_factory(n)
                 nodes.append(n)
             elif node_factory:
                 nodes.append(node_factory(v))
@@ -500,3 +504,6 @@ def arg2nodes(args, node_factory=None):
             nodes.append(v)
 
     return nodes
+
+def arg2Rnodes(args, node_factory=None):
+    return arg2nodes(args, node_factory, arg2Rnodes_lookups)
diff --git a/test/Repository/Install.py b/test/Repository/Install.py
new file mode 100644 (file)
index 0000000..44e7c97
--- /dev/null
@@ -0,0 +1,59 @@
+#!/usr/bin/env python
+#
+# Copyright (c) 2001, 2002 Steven Knight
+#
+# Permission is hereby granted, free of charge, to any person obtaining
+# a copy of this software and associated documentation files (the
+# "Software"), to deal in the Software without restriction, including
+# without limitation the rights to use, copy, modify, merge, publish,
+# distribute, sublicense, and/or sell copies of the Software, and to
+# permit persons to whom the Software is furnished to do so, subject to
+# the following conditions:
+#
+# The above copyright notice and this permission notice shall be included
+# in all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY
+# KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+# WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+
+__revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__"
+
+import os.path
+import sys
+import TestSCons
+
+test = TestSCons.TestSCons()
+
+test.subdir('install', 'repository', 'work')
+
+install = test.workpath('install')
+install_file = test.workpath('install', 'file')
+
+opts = "-Y " + test.workpath('repository')
+
+#
+test.write(['repository', 'SConstruct'], r"""
+env = Environment()
+env.Install(r'%s', 'file')
+""" % install)
+
+test.write(['repository', 'file'], "repository/file\n")
+
+# Make the entire repository non-writable, so we'll detect
+# if we try to write into it accidentally.
+test.writable('repository', 0)
+
+test.run(chdir = 'work', options = opts, arguments = install)
+
+test.fail_test(test.read(install_file) != "repository/file\n")
+
+test.up_to_date(chdir = 'work', options = opts, arguments = install)
+
+#
+test.pass_test()
diff --git a/test/Repository/InstallAs.py b/test/Repository/InstallAs.py
new file mode 100644 (file)
index 0000000..a4ff0cc
--- /dev/null
@@ -0,0 +1,66 @@
+#!/usr/bin/env python
+#
+# Copyright (c) 2001, 2002 Steven Knight
+#
+# Permission is hereby granted, free of charge, to any person obtaining
+# a copy of this software and associated documentation files (the
+# "Software"), to deal in the Software without restriction, including
+# without limitation the rights to use, copy, modify, merge, publish,
+# distribute, sublicense, and/or sell copies of the Software, and to
+# permit persons to whom the Software is furnished to do so, subject to
+# the following conditions:
+#
+# The above copyright notice and this permission notice shall be included
+# in all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY
+# KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+# WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+
+__revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__"
+
+import os.path
+import sys
+import TestSCons
+
+test = TestSCons.TestSCons()
+
+test.subdir('install', 'repository', 'work')
+
+install = test.workpath('install')
+install_file1_out = test.workpath('install', 'file1.out')
+install_file2_out = test.workpath('install', 'file2.out')
+install_file3_out = test.workpath('install', 'file3.out')
+
+opts = "-Y " + test.workpath('repository')
+
+#
+test.write(['repository', 'SConstruct'], r"""
+env = Environment()
+env.InstallAs(r'%s', 'file1.in')
+env.InstallAs([r'%s', r'%s'], ['file2.in', 'file3.in'])
+""" % (install_file1_out, install_file2_out, install_file3_out))
+
+test.write(['repository', 'file1.in'], "repository/file1.in\n")
+test.write(['repository', 'file2.in'], "repository/file2.in\n")
+test.write(['repository', 'file3.in'], "repository/file3.in\n")
+
+# Make the entire repository non-writable, so we'll detect
+# if we try to write into it accidentally.
+test.writable('repository', 0)
+
+test.run(chdir = 'work', options = opts, arguments = install)
+
+test.fail_test(test.read(install_file1_out) != "repository/file1.in\n")
+test.fail_test(test.read(install_file2_out) != "repository/file2.in\n")
+test.fail_test(test.read(install_file3_out) != "repository/file3.in\n")
+
+test.up_to_date(chdir = 'work', options = opts, arguments = install)
+
+#
+test.pass_test()