Fix a Glob() exception (with stack trace) when an explicit Node
authorstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Tue, 2 Dec 2008 18:58:29 +0000 (18:58 +0000)
committerstevenknight <stevenknight@fdb21ef1-2011-0410-befe-b5e4ea1792b1>
Tue, 2 Dec 2008 18:58:29 +0000 (18:58 +0000)
exists in a repository directory without a corresponding on-disk
file or directory.

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

src/CHANGES.txt
src/engine/SCons/Node/FS.py
src/engine/SCons/Node/FSTests.py
test/Glob/Repository.py

index 7fd865e27c2f50575a5de3a939cc70e2cd1b5dac..d7b1fac36d7d5de0dbcaefedabb3278afa12bd8f 100644 (file)
@@ -54,6 +54,9 @@ RELEASE 1.X - XXX
     - Add support for using the Python "in" keyword on construction
       environments (for example, if "CPPPATH" in env: ...).
 
+    - Fix use of Glob() when a repository or source directory contains
+      an in-memory Node without a corresponding on-disk file or directory.
+
   From Rob Managan:
 
     - Scan for TeX files in the paths specified in the $TEXINPUTS
index 03275da75ddbd65ea723461dbad82f378dfd958f..790d840df36ee951be597da61b139922a39ed6aa 100644 (file)
@@ -1892,6 +1892,7 @@ class Dir(Base):
         for srcdir in self.srcdir_list():
             search_dir_list.extend(srcdir.get_all_rdirs())
 
+        selfEntry = self.Entry
         names = []
         for dir in search_dir_list:
             # We use the .name attribute from the Node because the keys of
@@ -1901,6 +1902,10 @@ class Dir(Base):
             entry_names = filter(lambda n: n not in ('.', '..'), dir.entries.keys())
             node_names = map(lambda n, e=dir.entries: e[n].name, entry_names)
             names.extend(node_names)
+            if not strings:
+                # Make sure the working directory (self) actually has
+                # entries for all Nodes in repositories or variant dirs.
+                map(selfEntry, node_names)
             if ondisk:
                 try:
                     disk_names = os.listdir(dir.abspath)
@@ -1921,7 +1926,6 @@ class Dir(Base):
                         disk_names = filter(lambda x: x[0] != '.', disk_names)
                     disk_names = fnmatch.filter(disk_names, pattern)
                     dirEntry = dir.Entry
-                    selfEntry = self.Entry
                     for name in disk_names:
                         # Add './' before disk filename so that '#' at
                         # beginning of filename isn't interpreted.
index 6566d59eacd33f7c013b1fbb3d7315f41e1225b6..bf6a300fe8beca7cfeb69f772f941f4ce3d664f4 100644 (file)
@@ -2206,12 +2206,24 @@ class GlobTestCase(_tempdirTestCase):
             r = apply(self.fs.Glob, (input,), kwargs)
             if node_expect:
                 r.sort(lambda a,b: cmp(a.path, b.path))
-                result = node_expect
+                result = []
+                for n in node_expect:
+                    if type(n) == type(''):
+                        n = self.fs.Entry(n)
+                    result.append(n)
+                fmt = lambda n: "%s %s" % (repr(n), repr(str(n)))
             else:
                 r = map(str, r)
                 r.sort()
                 result = string_expect
-            assert r == result, "Glob(%s) expected %s, got %s" % (input, map(str, result), map(str, r))
+                fmt = lambda n: n
+            if r != result:
+                import pprint
+                print "Glob(%s) expected:" % repr(input)
+                pprint.pprint(map(fmt, result))
+                print "Glob(%s) got:" % repr(input)
+                pprint.pprint(map(fmt, r))
+                self.fail()
 
     def test_exact_match(self):
         """Test globbing for exact Node matches"""
@@ -2249,8 +2261,8 @@ class GlobTestCase(_tempdirTestCase):
 
         self.do_cases(cases)
 
-    def test_asterisk(self):
-        """Test globbing for simple asterisk Node matches"""
+    def test_asterisk1(self):
+        """Test globbing for simple asterisk Node matches (1)"""
         cases = (
             ('h*',
              ['hhh'],
@@ -2263,14 +2275,16 @@ class GlobTestCase(_tempdirTestCase):
               'ggg', 'hhh', 'iii',
               'sub', 'subdir1', 'subdir2'],
              [self._both_hash, self._hash,
-              self.both_aaa, self.both_bbb, self.both_ccc,
+              self.both_aaa, self.both_bbb, self.both_ccc, 'both-hash',
               self.both_sub1, self.both_sub2,
-              self.ggg, self.hhh, self.iii,
+              self.ggg, 'hash', self.hhh, self.iii,
               self.sub, self.subdir1, self.subdir2]),
         )
 
         self.do_cases(cases, ondisk=False)
 
+    def test_asterisk2(self):
+        """Test globbing for simple asterisk Node matches (2)"""
         cases = (
             ('disk-b*',
              ['disk-bbb'],
@@ -2283,7 +2297,12 @@ class GlobTestCase(_tempdirTestCase):
               'disk-aaa', 'disk-bbb', 'disk-ccc', 'disk-sub',
               'ggg', 'hhh', 'iii',
               'sub', 'subdir1', 'subdir2'],
-             None),
+             ['./#both-hash', './#disk-hash', './#hash',
+              'both-aaa', 'both-bbb', 'both-ccc', 'both-hash',
+              'both-sub1', 'both-sub2',
+              'disk-aaa', 'disk-bbb', 'disk-ccc', 'disk-sub',
+              'ggg', 'hash', 'hhh', 'iii',
+              'sub', 'subdir1', 'subdir2']),
         )
 
         self.do_cases(cases)
index 6cef4431048dffbd8224bb343ac3322e164b4e57..bef9bdacd7742a9566045761f8e2a7f63d929580 100644 (file)
@@ -55,6 +55,12 @@ def cat(env, source, target):
         f.write(open(src, "rb").read())
     f.close()
 
+# Verify that we can glob a repository-only Node that exists
+# only in memory, not on disk.
+File('../repository/mmm.in')
+m = Glob('m*.in')
+assert str(m[0]) == 'mmm.in'
+
 env = Environment(BUILDERS={'Build':Builder(action=cat)})
 env.Build('aaa.out', Glob('a*.in'))
 env.Build('bbb.out', Glob('b*.in'))