Fix use of varlist in CommandGeneratorAction, ListAction and LazyAction
authorstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Thu, 14 Jan 2010 07:02:42 +0000 (07:02 +0000)
committerstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Thu, 14 Jan 2010 07:02:42 +0000 (07:02 +0000)
by adding a .get_varlist() accessor method that lets those wrapping
classes fetch the varlist from their wrapped Action object(s).

git-svn-id: http://scons.tigris.org/svn/scons/trunk@4615 fdb21ef1-2011-0410-befe-b5e4ea1792b1

src/engine/SCons/Action.py
src/engine/SCons/ActionTests.py

index da041c6618c0108be01a181b6d8e513e0f5b132a..41c73add1f237e2400efe4a1ab8aabd5304e26ad 100644 (file)
@@ -430,7 +430,7 @@ class ActionBase:
         # This should never happen, as the Action() factory should wrap
         # the varlist, but just in case an action is created directly,
         # we duplicate this check here.
-        vl = self.varlist
+        vl = self.get_varlist(target, source, env)
         if is_String(vl): vl = (vl,)
         for v in vl:
             result.append(env.subst('${'+v+'}'))
@@ -454,6 +454,9 @@ class ActionBase:
         self.presub_env = None      # don't need this any more
         return lines
 
+    def get_varlist(self, target, source, env, executor=None):
+        return self.varlist
+
     def get_targets(self, env, executor):
         """
         Returns the type of targets ($TARGETS, $CHANGED_TARGETS) used
@@ -897,6 +900,9 @@ class CommandGeneratorAction(ActionBase):
     def get_implicit_deps(self, target, source, env, executor=None):
         return self._generate(target, source, env, 1, executor).get_implicit_deps(target, source, env)
 
+    def get_varlist(self, target, source, env, executor=None):
+        return self._generate(target, source, env, 1, executor).get_varlist(target, source, env, executor)
+
     def get_targets(self, env, executor):
         return self._generate(None, None, env, 1, executor).get_targets(env, executor)
 
@@ -958,6 +964,9 @@ class LazyAction(CommandGeneratorAction, CommandAction):
         c = self.get_parent_class(env)
         return c.get_presig(self, target, source, env)
 
+    def get_varlist(self, target, source, env, executor=None):
+        c = self.get_parent_class(env)
+        return c.get_varlist(self, target, source, env, executor)
 
 
 class FunctionAction(_ActionAction):
@@ -1139,6 +1148,13 @@ class ListAction(ActionBase):
             result.extend(act.get_implicit_deps(target, source, env))
         return result
 
+    def get_varlist(self, target, source, env, executor=None):
+        result = SCons.Util.OrderedDict()
+        for act in self.list:
+            for var in act.get_varlist(target, source, env, executor):
+                result[var] = True
+        return result.keys()
+
 class ActionCaller:
     """A class for delaying calling an Action function with specific
     (positional and keyword) arguments until the Action is actually
index b3f52217d0473b51d08de2b2cdc5a09dc63ea0f1..4c2198b6fbe6b6de975d47e883d64c87b6abb312 100644 (file)
@@ -1485,6 +1485,55 @@ class CommandGeneratorActionTestCase(unittest.TestCase):
         c = a.get_contents(target=[], source=[], env=env)
         assert c == "guux FFF BBB test", c
 
+    def test_get_contents_of_function_action(self):
+        """Test contents of a CommandGeneratorAction-generated FunctionAction
+        """
+
+        def LocalFunc():
+            pass
+
+        func_matches = [
+            "0,0,0,0,(),(),(d\000\000S),(),()",
+            "0,0,0,0,(),(),(d\x00\x00S),(),()",
+            ]
+        
+        meth_matches = [
+            "1,1,0,0,(),(),(d\000\000S),(),()",
+            "1,1,0,0,(),(),(d\x00\x00S),(),()",
+        ]
+
+        def f_global(target, source, env, for_signature):
+            return SCons.Action.Action(GlobalFunc)
+
+        def f_local(target, source, env, for_signature):
+            return SCons.Action.Action(LocalFunc)
+
+        env = Environment(XYZ = 'foo')
+
+        a = self.factory(f_global)
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in func_matches, repr(c)
+
+        a = self.factory(f_local)
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in func_matches, repr(c)
+
+        def f_global(target, source, env, for_signature):
+            return SCons.Action.Action(GlobalFunc, varlist=['XYZ'])
+
+        def f_local(target, source, env, for_signature):
+            return SCons.Action.Action(LocalFunc, varlist=['XYZ'])
+
+        matches_foo = map(lambda x: x + "foo", func_matches)
+
+        a = self.factory(f_global)
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in matches_foo, repr(c)
+
+        a = self.factory(f_local)
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in matches_foo, repr(c)
+
 
 class FunctionActionTestCase(unittest.TestCase):
 
@@ -1808,6 +1857,47 @@ class LazyActionTestCase(unittest.TestCase):
         c = a.get_contents(target=[], source=[], env=env)
         assert c == "This is a test", c
 
+    def test_get_contents_of_function_action(self):
+        """Test fetching the contents of a lazy-evaluation FunctionAction
+        """
+
+        def LocalFunc():
+            pass
+
+        func_matches = [
+            "0,0,0,0,(),(),(d\000\000S),(),()",
+            "0,0,0,0,(),(),(d\x00\x00S),(),()",
+            ]
+        
+        meth_matches = [
+            "1,1,0,0,(),(),(d\000\000S),(),()",
+            "1,1,0,0,(),(),(d\x00\x00S),(),()",
+        ]
+
+        def factory(act, **kw):
+            return SCons.Action.FunctionAction(act, kw)
+
+
+        a = SCons.Action.Action("${FOO}")
+
+        env = Environment(FOO = factory(GlobalFunc))
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in func_matches, repr(c)
+
+        env = Environment(FOO = factory(LocalFunc))
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in func_matches, repr(c)
+
+        matches_foo = map(lambda x: x + "foo", func_matches)
+
+        env = Environment(FOO = factory(GlobalFunc, varlist=['XYZ']))
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in func_matches, repr(c)
+
+        env['XYZ'] = 'foo'
+        c = a.get_contents(target=[], source=[], env=env)
+        assert c in matches_foo, repr(c)
+
 class ActionCallerTestCase(unittest.TestCase):
     def test___init__(self):
         """Test creation of an ActionCaller"""