##// END OF EJS Templates
match: make sure `root` argument is always an absolute path (API)...
Martin von Zweigbergk -
r44401:8b1a9ba3 default
parent child Browse files
Show More
@@ -183,34 +183,34 b' def match('
183 '<something>' - a pattern of the specified default type
183 '<something>' - a pattern of the specified default type
184
184
185 Usually a patternmatcher is returned:
185 Usually a patternmatcher is returned:
186 >>> match(b'foo', b'.', [b're:.*\.c$', b'path:foo/a', b'*.py'])
186 >>> match(b'/foo', b'.', [b're:.*\.c$', b'path:foo/a', b'*.py'])
187 <patternmatcher patterns='.*\\.c$|foo/a(?:/|$)|[^/]*\\.py$'>
187 <patternmatcher patterns='.*\\.c$|foo/a(?:/|$)|[^/]*\\.py$'>
188
188
189 Combining 'patterns' with 'include' (resp. 'exclude') gives an
189 Combining 'patterns' with 'include' (resp. 'exclude') gives an
190 intersectionmatcher (resp. a differencematcher):
190 intersectionmatcher (resp. a differencematcher):
191 >>> type(match(b'foo', b'.', [b're:.*\.c$'], include=[b'path:lib']))
191 >>> type(match(b'/foo', b'.', [b're:.*\.c$'], include=[b'path:lib']))
192 <class 'mercurial.match.intersectionmatcher'>
192 <class 'mercurial.match.intersectionmatcher'>
193 >>> type(match(b'foo', b'.', [b're:.*\.c$'], exclude=[b'path:build']))
193 >>> type(match(b'/foo', b'.', [b're:.*\.c$'], exclude=[b'path:build']))
194 <class 'mercurial.match.differencematcher'>
194 <class 'mercurial.match.differencematcher'>
195
195
196 Notice that, if 'patterns' is empty, an alwaysmatcher is returned:
196 Notice that, if 'patterns' is empty, an alwaysmatcher is returned:
197 >>> match(b'foo', b'.', [])
197 >>> match(b'/foo', b'.', [])
198 <alwaysmatcher>
198 <alwaysmatcher>
199
199
200 The 'default' argument determines which kind of pattern is assumed if a
200 The 'default' argument determines which kind of pattern is assumed if a
201 pattern has no prefix:
201 pattern has no prefix:
202 >>> match(b'foo', b'.', [b'.*\.c$'], default=b're')
202 >>> match(b'/foo', b'.', [b'.*\.c$'], default=b're')
203 <patternmatcher patterns='.*\\.c$'>
203 <patternmatcher patterns='.*\\.c$'>
204 >>> match(b'foo', b'.', [b'main.py'], default=b'relpath')
204 >>> match(b'/foo', b'.', [b'main.py'], default=b'relpath')
205 <patternmatcher patterns='main\\.py(?:/|$)'>
205 <patternmatcher patterns='main\\.py(?:/|$)'>
206 >>> match(b'foo', b'.', [b'main.py'], default=b're')
206 >>> match(b'/foo', b'.', [b'main.py'], default=b're')
207 <patternmatcher patterns='main.py'>
207 <patternmatcher patterns='main.py'>
208
208
209 The primary use of matchers is to check whether a value (usually a file
209 The primary use of matchers is to check whether a value (usually a file
210 name) matches againset one of the patterns given at initialization. There
210 name) matches againset one of the patterns given at initialization. There
211 are two ways of doing this check.
211 are two ways of doing this check.
212
212
213 >>> m = match(b'foo', b'', [b're:.*\.c$', b'relpath:a'])
213 >>> m = match(b'/foo', b'', [b're:.*\.c$', b'relpath:a'])
214
214
215 1. Calling the matcher with a file name returns True if any pattern
215 1. Calling the matcher with a file name returns True if any pattern
216 matches that file name:
216 matches that file name:
@@ -228,6 +228,7 b' def match('
228 >>> m.exact(b'main.c')
228 >>> m.exact(b'main.c')
229 False
229 False
230 """
230 """
231 assert os.path.isabs(root)
231 normalize = _donormalize
232 normalize = _donormalize
232 if icasefs:
233 if icasefs:
233 dirstate = ctx.repo().dirstate
234 dirstate = ctx.repo().dirstate
@@ -940,7 +941,7 b' class subdirmatcher(basematcher):'
940 The paths are remapped to remove/insert the path as needed:
941 The paths are remapped to remove/insert the path as needed:
941
942
942 >>> from . import pycompat
943 >>> from . import pycompat
943 >>> m1 = match(b'root', b'', [b'a.txt', b'sub/b.txt'])
944 >>> m1 = match(b'/root', b'', [b'a.txt', b'sub/b.txt'])
944 >>> m2 = subdirmatcher(b'sub', m1)
945 >>> m2 = subdirmatcher(b'sub', m1)
945 >>> m2(b'a.txt')
946 >>> m2(b'a.txt')
946 False
947 False
@@ -1024,7 +1025,7 b' class prefixdirmatcher(basematcher):'
1024 The prefix path should usually be the relative path from the root of
1025 The prefix path should usually be the relative path from the root of
1025 this matcher to the root of the wrapped matcher.
1026 this matcher to the root of the wrapped matcher.
1026
1027
1027 >>> m1 = match(util.localpath(b'root/d/e'), b'f', [b'../a.txt', b'b.txt'])
1028 >>> m1 = match(util.localpath(b'/root/d/e'), b'f', [b'../a.txt', b'b.txt'], auditor=lambda name: None)
1028 >>> m2 = prefixdirmatcher(b'd/e', m1)
1029 >>> m2 = prefixdirmatcher(b'd/e', m1)
1029 >>> m2(b'a.txt')
1030 >>> m2(b'a.txt')
1030 False
1031 False
@@ -169,7 +169,7 b' class basemanifesttests(object):'
169 m[b'foo'] = want + b'+'
169 m[b'foo'] = want + b'+'
170 self.assertEqual(want, m[b'foo'])
170 self.assertEqual(want, m[b'foo'])
171 # make sure the suffix survives a copy
171 # make sure the suffix survives a copy
172 match = matchmod.match(b'', b'', [b're:foo'])
172 match = matchmod.match(b'/repo', b'', [b're:foo'])
173 m2 = m.matches(match)
173 m2 = m.matches(match)
174 self.assertEqual(want, m2[b'foo'])
174 self.assertEqual(want, m2[b'foo'])
175 self.assertEqual(1, len(m2))
175 self.assertEqual(1, len(m2))
@@ -186,7 +186,7 b' class basemanifesttests(object):'
186
186
187 def testMatchException(self):
187 def testMatchException(self):
188 m = self.parsemanifest(A_SHORT_MANIFEST)
188 m = self.parsemanifest(A_SHORT_MANIFEST)
189 match = matchmod.match(b'', b'', [b're:.*'])
189 match = matchmod.match(b'/repo', b'', [b're:.*'])
190
190
191 def filt(path):
191 def filt(path):
192 if path == b'foo':
192 if path == b'foo':
@@ -328,7 +328,7 b' class basemanifesttests(object):'
328 actually exist.'''
328 actually exist.'''
329 m = self.parsemanifest(A_DEEPER_MANIFEST)
329 m = self.parsemanifest(A_DEEPER_MANIFEST)
330
330
331 match = matchmod.match(b'/', b'', [b'a/f'], default=b'relpath')
331 match = matchmod.match(b'/repo', b'', [b'a/f'], default=b'relpath')
332 m2 = m.matches(match)
332 m2 = m.matches(match)
333
333
334 self.assertEqual([], m2.keys())
334 self.assertEqual([], m2.keys())
@@ -348,7 +348,7 b' class basemanifesttests(object):'
348 '''Tests matches() for what should be a full match.'''
348 '''Tests matches() for what should be a full match.'''
349 m = self.parsemanifest(A_DEEPER_MANIFEST)
349 m = self.parsemanifest(A_DEEPER_MANIFEST)
350
350
351 match = matchmod.match(b'/', b'', [b''])
351 match = matchmod.match(b'/repo', b'', [b''])
352 m2 = m.matches(match)
352 m2 = m.matches(match)
353
353
354 self.assertEqual(m.keys(), m2.keys())
354 self.assertEqual(m.keys(), m2.keys())
@@ -358,7 +358,7 b' class basemanifesttests(object):'
358 match against all files within said directory.'''
358 match against all files within said directory.'''
359 m = self.parsemanifest(A_DEEPER_MANIFEST)
359 m = self.parsemanifest(A_DEEPER_MANIFEST)
360
360
361 match = matchmod.match(b'/', b'', [b'a/b'], default=b'relpath')
361 match = matchmod.match(b'/repo', b'', [b'a/b'], default=b'relpath')
362 m2 = m.matches(match)
362 m2 = m.matches(match)
363
363
364 self.assertEqual(
364 self.assertEqual(
@@ -392,7 +392,7 b' class basemanifesttests(object):'
392 when not in the root directory.'''
392 when not in the root directory.'''
393 m = self.parsemanifest(A_DEEPER_MANIFEST)
393 m = self.parsemanifest(A_DEEPER_MANIFEST)
394
394
395 match = matchmod.match(b'/', b'a/b', [b'.'], default=b'relpath')
395 match = matchmod.match(b'/repo', b'a/b', [b'.'], default=b'relpath')
396 m2 = m.matches(match)
396 m2 = m.matches(match)
397
397
398 self.assertEqual(
398 self.assertEqual(
@@ -415,7 +415,7 b' class basemanifesttests(object):'
415 deeper than the specified directory.'''
415 deeper than the specified directory.'''
416 m = self.parsemanifest(A_DEEPER_MANIFEST)
416 m = self.parsemanifest(A_DEEPER_MANIFEST)
417
417
418 match = matchmod.match(b'/', b'', [b'a/b/*/*.txt'])
418 match = matchmod.match(b'/repo', b'', [b'a/b/*/*.txt'])
419 m2 = m.matches(match)
419 m2 = m.matches(match)
420
420
421 self.assertEqual(
421 self.assertEqual(
@@ -467,7 +467,7 b' class testtreemanifest(unittest.TestCase'
467 sorted(dirs),
467 sorted(dirs),
468 )
468 )
469
469
470 match = matchmod.match(b'/', b'', [b'path:a/b/'])
470 match = matchmod.match(b'/repo', b'', [b'path:a/b/'])
471 dirs = [s._dir for s in m.walksubtrees(matcher=match)]
471 dirs = [s._dir for s in m.walksubtrees(matcher=match)]
472 self.assertEqual(sorted([b'a/b/', b'a/b/c/', b'a/b/d/']), sorted(dirs))
472 self.assertEqual(sorted([b'a/b/', b'a/b/c/', b'a/b/d/']), sorted(dirs))
473
473
@@ -10,6 +10,9 b' from mercurial import ('
10 )
10 )
11
11
12
12
13 noop_auditor = lambda name: None
14
15
13 class BaseMatcherTests(unittest.TestCase):
16 class BaseMatcherTests(unittest.TestCase):
14 def testVisitdir(self):
17 def testVisitdir(self):
15 m = matchmod.basematcher()
18 m = matchmod.basematcher()
@@ -63,7 +66,7 b' class PredicateMatcherTests(unittest.Tes'
63
66
64 class PatternMatcherTests(unittest.TestCase):
67 class PatternMatcherTests(unittest.TestCase):
65 def testVisitdirPrefix(self):
68 def testVisitdirPrefix(self):
66 m = matchmod.match(b'x', b'', patterns=[b'path:dir/subdir'])
69 m = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
67 assert isinstance(m, matchmod.patternmatcher)
70 assert isinstance(m, matchmod.patternmatcher)
68 self.assertTrue(m.visitdir(b''))
71 self.assertTrue(m.visitdir(b''))
69 self.assertTrue(m.visitdir(b'dir'))
72 self.assertTrue(m.visitdir(b'dir'))
@@ -73,7 +76,7 b' class PatternMatcherTests(unittest.TestC'
73 self.assertFalse(m.visitdir(b'folder'))
76 self.assertFalse(m.visitdir(b'folder'))
74
77
75 def testVisitchildrensetPrefix(self):
78 def testVisitchildrensetPrefix(self):
76 m = matchmod.match(b'x', b'', patterns=[b'path:dir/subdir'])
79 m = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
77 assert isinstance(m, matchmod.patternmatcher)
80 assert isinstance(m, matchmod.patternmatcher)
78 self.assertEqual(m.visitchildrenset(b''), b'this')
81 self.assertEqual(m.visitchildrenset(b''), b'this')
79 self.assertEqual(m.visitchildrenset(b'dir'), b'this')
82 self.assertEqual(m.visitchildrenset(b'dir'), b'this')
@@ -83,7 +86,7 b' class PatternMatcherTests(unittest.TestC'
83 self.assertEqual(m.visitchildrenset(b'folder'), set())
86 self.assertEqual(m.visitchildrenset(b'folder'), set())
84
87
85 def testVisitdirRootfilesin(self):
88 def testVisitdirRootfilesin(self):
86 m = matchmod.match(b'x', b'', patterns=[b'rootfilesin:dir/subdir'])
89 m = matchmod.match(b'/repo', b'', patterns=[b'rootfilesin:dir/subdir'])
87 assert isinstance(m, matchmod.patternmatcher)
90 assert isinstance(m, matchmod.patternmatcher)
88 self.assertFalse(m.visitdir(b'dir/subdir/x'))
91 self.assertFalse(m.visitdir(b'dir/subdir/x'))
89 self.assertFalse(m.visitdir(b'folder'))
92 self.assertFalse(m.visitdir(b'folder'))
@@ -93,7 +96,7 b' class PatternMatcherTests(unittest.TestC'
93 self.assertFalse(m.visitdir(b'dir/subdir'))
96 self.assertFalse(m.visitdir(b'dir/subdir'))
94
97
95 def testVisitchildrensetRootfilesin(self):
98 def testVisitchildrensetRootfilesin(self):
96 m = matchmod.match(b'x', b'', patterns=[b'rootfilesin:dir/subdir'])
99 m = matchmod.match(b'/repo', b'', patterns=[b'rootfilesin:dir/subdir'])
97 assert isinstance(m, matchmod.patternmatcher)
100 assert isinstance(m, matchmod.patternmatcher)
98 self.assertEqual(m.visitchildrenset(b'dir/subdir/x'), set())
101 self.assertEqual(m.visitchildrenset(b'dir/subdir/x'), set())
99 self.assertEqual(m.visitchildrenset(b'folder'), set())
102 self.assertEqual(m.visitchildrenset(b'folder'), set())
@@ -104,7 +107,7 b' class PatternMatcherTests(unittest.TestC'
104 self.assertEqual(m.visitchildrenset(b'dir/subdir'), set())
107 self.assertEqual(m.visitchildrenset(b'dir/subdir'), set())
105
108
106 def testVisitdirGlob(self):
109 def testVisitdirGlob(self):
107 m = matchmod.match(b'x', b'', patterns=[b'glob:dir/z*'])
110 m = matchmod.match(b'/repo', b'', patterns=[b'glob:dir/z*'])
108 assert isinstance(m, matchmod.patternmatcher)
111 assert isinstance(m, matchmod.patternmatcher)
109 self.assertTrue(m.visitdir(b''))
112 self.assertTrue(m.visitdir(b''))
110 self.assertTrue(m.visitdir(b'dir'))
113 self.assertTrue(m.visitdir(b'dir'))
@@ -114,7 +117,7 b' class PatternMatcherTests(unittest.TestC'
114 self.assertTrue(m.visitdir(b'dir/subdir/x'))
117 self.assertTrue(m.visitdir(b'dir/subdir/x'))
115
118
116 def testVisitchildrensetGlob(self):
119 def testVisitchildrensetGlob(self):
117 m = matchmod.match(b'x', b'', patterns=[b'glob:dir/z*'])
120 m = matchmod.match(b'/repo', b'', patterns=[b'glob:dir/z*'])
118 assert isinstance(m, matchmod.patternmatcher)
121 assert isinstance(m, matchmod.patternmatcher)
119 self.assertEqual(m.visitchildrenset(b''), b'this')
122 self.assertEqual(m.visitchildrenset(b''), b'this')
120 self.assertEqual(m.visitchildrenset(b'folder'), set())
123 self.assertEqual(m.visitchildrenset(b'folder'), set())
@@ -126,7 +129,7 b' class PatternMatcherTests(unittest.TestC'
126
129
127 class IncludeMatcherTests(unittest.TestCase):
130 class IncludeMatcherTests(unittest.TestCase):
128 def testVisitdirPrefix(self):
131 def testVisitdirPrefix(self):
129 m = matchmod.match(b'x', b'', include=[b'path:dir/subdir'])
132 m = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
130 assert isinstance(m, matchmod.includematcher)
133 assert isinstance(m, matchmod.includematcher)
131 self.assertTrue(m.visitdir(b''))
134 self.assertTrue(m.visitdir(b''))
132 self.assertTrue(m.visitdir(b'dir'))
135 self.assertTrue(m.visitdir(b'dir'))
@@ -136,7 +139,7 b' class IncludeMatcherTests(unittest.TestC'
136 self.assertFalse(m.visitdir(b'folder'))
139 self.assertFalse(m.visitdir(b'folder'))
137
140
138 def testVisitchildrensetPrefix(self):
141 def testVisitchildrensetPrefix(self):
139 m = matchmod.match(b'x', b'', include=[b'path:dir/subdir'])
142 m = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
140 assert isinstance(m, matchmod.includematcher)
143 assert isinstance(m, matchmod.includematcher)
141 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
144 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
142 self.assertEqual(m.visitchildrenset(b'dir'), {b'subdir'})
145 self.assertEqual(m.visitchildrenset(b'dir'), {b'subdir'})
@@ -146,7 +149,7 b' class IncludeMatcherTests(unittest.TestC'
146 self.assertEqual(m.visitchildrenset(b'folder'), set())
149 self.assertEqual(m.visitchildrenset(b'folder'), set())
147
150
148 def testVisitdirRootfilesin(self):
151 def testVisitdirRootfilesin(self):
149 m = matchmod.match(b'x', b'', include=[b'rootfilesin:dir/subdir'])
152 m = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir/subdir'])
150 assert isinstance(m, matchmod.includematcher)
153 assert isinstance(m, matchmod.includematcher)
151 self.assertTrue(m.visitdir(b''))
154 self.assertTrue(m.visitdir(b''))
152 self.assertTrue(m.visitdir(b'dir'))
155 self.assertTrue(m.visitdir(b'dir'))
@@ -155,7 +158,7 b' class IncludeMatcherTests(unittest.TestC'
155 self.assertFalse(m.visitdir(b'folder'))
158 self.assertFalse(m.visitdir(b'folder'))
156
159
157 def testVisitchildrensetRootfilesin(self):
160 def testVisitchildrensetRootfilesin(self):
158 m = matchmod.match(b'x', b'', include=[b'rootfilesin:dir/subdir'])
161 m = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir/subdir'])
159 assert isinstance(m, matchmod.includematcher)
162 assert isinstance(m, matchmod.includematcher)
160 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
163 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
161 self.assertEqual(m.visitchildrenset(b'dir'), {b'subdir'})
164 self.assertEqual(m.visitchildrenset(b'dir'), {b'subdir'})
@@ -164,7 +167,7 b' class IncludeMatcherTests(unittest.TestC'
164 self.assertEqual(m.visitchildrenset(b'folder'), set())
167 self.assertEqual(m.visitchildrenset(b'folder'), set())
165
168
166 def testVisitdirGlob(self):
169 def testVisitdirGlob(self):
167 m = matchmod.match(b'x', b'', include=[b'glob:dir/z*'])
170 m = matchmod.match(b'/repo', b'', include=[b'glob:dir/z*'])
168 assert isinstance(m, matchmod.includematcher)
171 assert isinstance(m, matchmod.includematcher)
169 self.assertTrue(m.visitdir(b''))
172 self.assertTrue(m.visitdir(b''))
170 self.assertTrue(m.visitdir(b'dir'))
173 self.assertTrue(m.visitdir(b'dir'))
@@ -174,7 +177,7 b' class IncludeMatcherTests(unittest.TestC'
174 self.assertTrue(m.visitdir(b'dir/subdir/x'))
177 self.assertTrue(m.visitdir(b'dir/subdir/x'))
175
178
176 def testVisitchildrensetGlob(self):
179 def testVisitchildrensetGlob(self):
177 m = matchmod.match(b'x', b'', include=[b'glob:dir/z*'])
180 m = matchmod.match(b'/repo', b'', include=[b'glob:dir/z*'])
178 assert isinstance(m, matchmod.includematcher)
181 assert isinstance(m, matchmod.includematcher)
179 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
182 self.assertEqual(m.visitchildrenset(b''), {b'dir'})
180 self.assertEqual(m.visitchildrenset(b'folder'), set())
183 self.assertEqual(m.visitchildrenset(b'folder'), set())
@@ -286,7 +289,7 b' class DifferenceMatcherTests(unittest.Te'
286
289
287 def testVisitdirM2SubdirPrefix(self):
290 def testVisitdirM2SubdirPrefix(self):
288 m1 = matchmod.alwaysmatcher()
291 m1 = matchmod.alwaysmatcher()
289 m2 = matchmod.match(b'', b'', patterns=[b'path:dir/subdir'])
292 m2 = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
290 dm = matchmod.differencematcher(m1, m2)
293 dm = matchmod.differencematcher(m1, m2)
291 self.assertEqual(dm.visitdir(b''), True)
294 self.assertEqual(dm.visitdir(b''), True)
292 self.assertEqual(dm.visitdir(b'dir'), True)
295 self.assertEqual(dm.visitdir(b'dir'), True)
@@ -301,7 +304,7 b' class DifferenceMatcherTests(unittest.Te'
301
304
302 def testVisitchildrensetM2SubdirPrefix(self):
305 def testVisitchildrensetM2SubdirPrefix(self):
303 m1 = matchmod.alwaysmatcher()
306 m1 = matchmod.alwaysmatcher()
304 m2 = matchmod.match(b'', b'', patterns=[b'path:dir/subdir'])
307 m2 = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
305 dm = matchmod.differencematcher(m1, m2)
308 dm = matchmod.differencematcher(m1, m2)
306 self.assertEqual(dm.visitchildrenset(b''), b'this')
309 self.assertEqual(dm.visitchildrenset(b''), b'this')
307 self.assertEqual(dm.visitchildrenset(b'dir'), b'this')
310 self.assertEqual(dm.visitchildrenset(b'dir'), b'this')
@@ -317,8 +320,8 b' class DifferenceMatcherTests(unittest.Te'
317 # We're using includematcher instead of patterns because it behaves slightly
320 # We're using includematcher instead of patterns because it behaves slightly
318 # better (giving narrower results) than patternmatcher.
321 # better (giving narrower results) than patternmatcher.
319 def testVisitdirIncludeInclude(self):
322 def testVisitdirIncludeInclude(self):
320 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
323 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
321 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
324 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
322 dm = matchmod.differencematcher(m1, m2)
325 dm = matchmod.differencematcher(m1, m2)
323 self.assertEqual(dm.visitdir(b''), True)
326 self.assertEqual(dm.visitdir(b''), True)
324 self.assertEqual(dm.visitdir(b'dir'), True)
327 self.assertEqual(dm.visitdir(b'dir'), True)
@@ -332,8 +335,8 b' class DifferenceMatcherTests(unittest.Te'
332 self.assertEqual(dm.visitdir(b'dir/subdir/x'), True)
335 self.assertEqual(dm.visitdir(b'dir/subdir/x'), True)
333
336
334 def testVisitchildrensetIncludeInclude(self):
337 def testVisitchildrensetIncludeInclude(self):
335 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
338 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
336 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
339 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
337 dm = matchmod.differencematcher(m1, m2)
340 dm = matchmod.differencematcher(m1, m2)
338 self.assertEqual(dm.visitchildrenset(b''), {b'dir'})
341 self.assertEqual(dm.visitchildrenset(b''), {b'dir'})
339 self.assertEqual(dm.visitchildrenset(b'dir'), {b'subdir'})
342 self.assertEqual(dm.visitchildrenset(b'dir'), {b'subdir'})
@@ -402,7 +405,7 b' class IntersectionMatcherTests(unittest.'
402
405
403 def testVisitdirM2SubdirPrefix(self):
406 def testVisitdirM2SubdirPrefix(self):
404 m1 = matchmod.alwaysmatcher()
407 m1 = matchmod.alwaysmatcher()
405 m2 = matchmod.match(b'', b'', patterns=[b'path:dir/subdir'])
408 m2 = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
406 im = matchmod.intersectmatchers(m1, m2)
409 im = matchmod.intersectmatchers(m1, m2)
407 self.assertEqual(im.visitdir(b''), True)
410 self.assertEqual(im.visitdir(b''), True)
408 self.assertEqual(im.visitdir(b'dir'), True)
411 self.assertEqual(im.visitdir(b'dir'), True)
@@ -417,7 +420,7 b' class IntersectionMatcherTests(unittest.'
417
420
418 def testVisitchildrensetM2SubdirPrefix(self):
421 def testVisitchildrensetM2SubdirPrefix(self):
419 m1 = matchmod.alwaysmatcher()
422 m1 = matchmod.alwaysmatcher()
420 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
423 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
421 im = matchmod.intersectmatchers(m1, m2)
424 im = matchmod.intersectmatchers(m1, m2)
422 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
425 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
423 self.assertEqual(im.visitchildrenset(b'dir'), {b'subdir'})
426 self.assertEqual(im.visitchildrenset(b'dir'), {b'subdir'})
@@ -431,8 +434,8 b' class IntersectionMatcherTests(unittest.'
431 # We're using includematcher instead of patterns because it behaves slightly
434 # We're using includematcher instead of patterns because it behaves slightly
432 # better (giving narrower results) than patternmatcher.
435 # better (giving narrower results) than patternmatcher.
433 def testVisitdirIncludeInclude(self):
436 def testVisitdirIncludeInclude(self):
434 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
437 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
435 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
438 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
436 im = matchmod.intersectmatchers(m1, m2)
439 im = matchmod.intersectmatchers(m1, m2)
437 self.assertEqual(im.visitdir(b''), True)
440 self.assertEqual(im.visitdir(b''), True)
438 self.assertEqual(im.visitdir(b'dir'), True)
441 self.assertEqual(im.visitdir(b'dir'), True)
@@ -443,8 +446,8 b' class IntersectionMatcherTests(unittest.'
443 self.assertFalse(im.visitdir(b'dir/subdir/x'))
446 self.assertFalse(im.visitdir(b'dir/subdir/x'))
444
447
445 def testVisitchildrensetIncludeInclude(self):
448 def testVisitchildrensetIncludeInclude(self):
446 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
449 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
447 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
450 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
448 im = matchmod.intersectmatchers(m1, m2)
451 im = matchmod.intersectmatchers(m1, m2)
449 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
452 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
450 self.assertEqual(im.visitchildrenset(b'dir'), b'this')
453 self.assertEqual(im.visitchildrenset(b'dir'), b'this')
@@ -457,8 +460,8 b' class IntersectionMatcherTests(unittest.'
457 # We're using includematcher instead of patterns because it behaves slightly
460 # We're using includematcher instead of patterns because it behaves slightly
458 # better (giving narrower results) than patternmatcher.
461 # better (giving narrower results) than patternmatcher.
459 def testVisitdirIncludeInclude2(self):
462 def testVisitdirIncludeInclude2(self):
460 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
463 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
461 m2 = matchmod.match(b'', b'', include=[b'path:folder'])
464 m2 = matchmod.match(b'/repo', b'', include=[b'path:folder'])
462 im = matchmod.intersectmatchers(m1, m2)
465 im = matchmod.intersectmatchers(m1, m2)
463 # FIXME: is True correct here?
466 # FIXME: is True correct here?
464 self.assertEqual(im.visitdir(b''), True)
467 self.assertEqual(im.visitdir(b''), True)
@@ -470,8 +473,8 b' class IntersectionMatcherTests(unittest.'
470 self.assertFalse(im.visitdir(b'dir/subdir/x'))
473 self.assertFalse(im.visitdir(b'dir/subdir/x'))
471
474
472 def testVisitchildrensetIncludeInclude2(self):
475 def testVisitchildrensetIncludeInclude2(self):
473 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
476 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
474 m2 = matchmod.match(b'', b'', include=[b'path:folder'])
477 m2 = matchmod.match(b'/repo', b'', include=[b'path:folder'])
475 im = matchmod.intersectmatchers(m1, m2)
478 im = matchmod.intersectmatchers(m1, m2)
476 # FIXME: is set() correct here?
479 # FIXME: is set() correct here?
477 self.assertEqual(im.visitchildrenset(b''), set())
480 self.assertEqual(im.visitchildrenset(b''), set())
@@ -485,8 +488,8 b' class IntersectionMatcherTests(unittest.'
485 # We're using includematcher instead of patterns because it behaves slightly
488 # We're using includematcher instead of patterns because it behaves slightly
486 # better (giving narrower results) than patternmatcher.
489 # better (giving narrower results) than patternmatcher.
487 def testVisitdirIncludeInclude3(self):
490 def testVisitdirIncludeInclude3(self):
488 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
491 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
489 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
492 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
490 im = matchmod.intersectmatchers(m1, m2)
493 im = matchmod.intersectmatchers(m1, m2)
491 self.assertEqual(im.visitdir(b''), True)
494 self.assertEqual(im.visitdir(b''), True)
492 self.assertEqual(im.visitdir(b'dir'), True)
495 self.assertEqual(im.visitdir(b'dir'), True)
@@ -498,8 +501,8 b' class IntersectionMatcherTests(unittest.'
498 self.assertEqual(im.visitdir(b'dir/subdir/x'), True)
501 self.assertEqual(im.visitdir(b'dir/subdir/x'), True)
499
502
500 def testVisitchildrensetIncludeInclude3(self):
503 def testVisitchildrensetIncludeInclude3(self):
501 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
504 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
502 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
505 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
503 im = matchmod.intersectmatchers(m1, m2)
506 im = matchmod.intersectmatchers(m1, m2)
504 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
507 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
505 self.assertEqual(im.visitchildrenset(b'dir'), {b'subdir'})
508 self.assertEqual(im.visitchildrenset(b'dir'), {b'subdir'})
@@ -513,8 +516,8 b' class IntersectionMatcherTests(unittest.'
513 # We're using includematcher instead of patterns because it behaves slightly
516 # We're using includematcher instead of patterns because it behaves slightly
514 # better (giving narrower results) than patternmatcher.
517 # better (giving narrower results) than patternmatcher.
515 def testVisitdirIncludeInclude4(self):
518 def testVisitdirIncludeInclude4(self):
516 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
519 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
517 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir/z'])
520 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/z'])
518 im = matchmod.intersectmatchers(m1, m2)
521 im = matchmod.intersectmatchers(m1, m2)
519 # OPT: these next three could probably be False as well.
522 # OPT: these next three could probably be False as well.
520 self.assertEqual(im.visitdir(b''), True)
523 self.assertEqual(im.visitdir(b''), True)
@@ -526,8 +529,8 b' class IntersectionMatcherTests(unittest.'
526 self.assertFalse(im.visitdir(b'dir/subdir/x'))
529 self.assertFalse(im.visitdir(b'dir/subdir/x'))
527
530
528 def testVisitchildrensetIncludeInclude4(self):
531 def testVisitchildrensetIncludeInclude4(self):
529 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
532 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
530 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir/z'])
533 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/z'])
531 im = matchmod.intersectmatchers(m1, m2)
534 im = matchmod.intersectmatchers(m1, m2)
532 # OPT: these next two could probably be set() as well.
535 # OPT: these next two could probably be set() as well.
533 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
536 self.assertEqual(im.visitchildrenset(b''), {b'dir'})
@@ -620,7 +623,7 b' class UnionMatcherTests(unittest.TestCas'
620
623
621 def testVisitdirM2SubdirPrefix(self):
624 def testVisitdirM2SubdirPrefix(self):
622 m1 = matchmod.alwaysmatcher()
625 m1 = matchmod.alwaysmatcher()
623 m2 = matchmod.match(b'', b'', patterns=[b'path:dir/subdir'])
626 m2 = matchmod.match(b'/repo', b'', patterns=[b'path:dir/subdir'])
624 um = matchmod.unionmatcher([m1, m2])
627 um = matchmod.unionmatcher([m1, m2])
625 self.assertEqual(um.visitdir(b''), b'all')
628 self.assertEqual(um.visitdir(b''), b'all')
626 self.assertEqual(um.visitdir(b'dir'), b'all')
629 self.assertEqual(um.visitdir(b'dir'), b'all')
@@ -632,7 +635,7 b' class UnionMatcherTests(unittest.TestCas'
632
635
633 def testVisitchildrensetM2SubdirPrefix(self):
636 def testVisitchildrensetM2SubdirPrefix(self):
634 m1 = matchmod.alwaysmatcher()
637 m1 = matchmod.alwaysmatcher()
635 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
638 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
636 um = matchmod.unionmatcher([m1, m2])
639 um = matchmod.unionmatcher([m1, m2])
637 self.assertEqual(um.visitchildrenset(b''), b'all')
640 self.assertEqual(um.visitchildrenset(b''), b'all')
638 self.assertEqual(um.visitchildrenset(b'dir'), b'all')
641 self.assertEqual(um.visitchildrenset(b'dir'), b'all')
@@ -645,8 +648,8 b' class UnionMatcherTests(unittest.TestCas'
645 # We're using includematcher instead of patterns because it behaves slightly
648 # We're using includematcher instead of patterns because it behaves slightly
646 # better (giving narrower results) than patternmatcher.
649 # better (giving narrower results) than patternmatcher.
647 def testVisitdirIncludeInclude(self):
650 def testVisitdirIncludeInclude(self):
648 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
651 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
649 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
652 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
650 um = matchmod.unionmatcher([m1, m2])
653 um = matchmod.unionmatcher([m1, m2])
651 self.assertEqual(um.visitdir(b''), True)
654 self.assertEqual(um.visitdir(b''), True)
652 self.assertEqual(um.visitdir(b'dir'), True)
655 self.assertEqual(um.visitdir(b'dir'), True)
@@ -658,8 +661,8 b' class UnionMatcherTests(unittest.TestCas'
658 self.assertEqual(um.visitdir(b'dir/subdir/x'), True)
661 self.assertEqual(um.visitdir(b'dir/subdir/x'), True)
659
662
660 def testVisitchildrensetIncludeInclude(self):
663 def testVisitchildrensetIncludeInclude(self):
661 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
664 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
662 m2 = matchmod.match(b'', b'', include=[b'rootfilesin:dir'])
665 m2 = matchmod.match(b'/repo', b'', include=[b'rootfilesin:dir'])
663 um = matchmod.unionmatcher([m1, m2])
666 um = matchmod.unionmatcher([m1, m2])
664 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
667 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
665 self.assertEqual(um.visitchildrenset(b'dir'), b'this')
668 self.assertEqual(um.visitchildrenset(b'dir'), b'this')
@@ -673,8 +676,8 b' class UnionMatcherTests(unittest.TestCas'
673 # We're using includematcher instead of patterns because it behaves slightly
676 # We're using includematcher instead of patterns because it behaves slightly
674 # better (giving narrower results) than patternmatcher.
677 # better (giving narrower results) than patternmatcher.
675 def testVisitdirIncludeInclude2(self):
678 def testVisitdirIncludeInclude2(self):
676 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
679 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
677 m2 = matchmod.match(b'', b'', include=[b'path:folder'])
680 m2 = matchmod.match(b'/repo', b'', include=[b'path:folder'])
678 um = matchmod.unionmatcher([m1, m2])
681 um = matchmod.unionmatcher([m1, m2])
679 self.assertEqual(um.visitdir(b''), True)
682 self.assertEqual(um.visitdir(b''), True)
680 self.assertEqual(um.visitdir(b'dir'), True)
683 self.assertEqual(um.visitdir(b'dir'), True)
@@ -686,8 +689,8 b' class UnionMatcherTests(unittest.TestCas'
686 self.assertEqual(um.visitdir(b'dir/subdir/x'), True)
689 self.assertEqual(um.visitdir(b'dir/subdir/x'), True)
687
690
688 def testVisitchildrensetIncludeInclude2(self):
691 def testVisitchildrensetIncludeInclude2(self):
689 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
692 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
690 m2 = matchmod.match(b'', b'', include=[b'path:folder'])
693 m2 = matchmod.match(b'/repo', b'', include=[b'path:folder'])
691 um = matchmod.unionmatcher([m1, m2])
694 um = matchmod.unionmatcher([m1, m2])
692 self.assertEqual(um.visitchildrenset(b''), {b'folder', b'dir'})
695 self.assertEqual(um.visitchildrenset(b''), {b'folder', b'dir'})
693 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
696 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
@@ -701,8 +704,8 b' class UnionMatcherTests(unittest.TestCas'
701 # We're using includematcher instead of patterns because it behaves slightly
704 # We're using includematcher instead of patterns because it behaves slightly
702 # better (giving narrower results) than patternmatcher.
705 # better (giving narrower results) than patternmatcher.
703 def testVisitdirIncludeInclude3(self):
706 def testVisitdirIncludeInclude3(self):
704 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
707 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
705 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
708 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
706 um = matchmod.unionmatcher([m1, m2])
709 um = matchmod.unionmatcher([m1, m2])
707 self.assertEqual(um.visitdir(b''), True)
710 self.assertEqual(um.visitdir(b''), True)
708 self.assertEqual(um.visitdir(b'dir'), True)
711 self.assertEqual(um.visitdir(b'dir'), True)
@@ -714,8 +717,8 b' class UnionMatcherTests(unittest.TestCas'
714 self.assertEqual(um.visitdir(b'dir/subdir/z'), True)
717 self.assertEqual(um.visitdir(b'dir/subdir/z'), True)
715
718
716 def testVisitchildrensetIncludeInclude3(self):
719 def testVisitchildrensetIncludeInclude3(self):
717 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
720 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
718 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
721 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
719 um = matchmod.unionmatcher([m1, m2])
722 um = matchmod.unionmatcher([m1, m2])
720 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
723 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
721 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
724 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
@@ -729,8 +732,8 b' class UnionMatcherTests(unittest.TestCas'
729 # We're using includematcher instead of patterns because it behaves slightly
732 # We're using includematcher instead of patterns because it behaves slightly
730 # better (giving narrower results) than patternmatcher.
733 # better (giving narrower results) than patternmatcher.
731 def testVisitdirIncludeInclude4(self):
734 def testVisitdirIncludeInclude4(self):
732 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
735 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
733 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir/z'])
736 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/z'])
734 um = matchmod.unionmatcher([m1, m2])
737 um = matchmod.unionmatcher([m1, m2])
735 # OPT: these next three could probably be False as well.
738 # OPT: these next three could probably be False as well.
736 self.assertEqual(um.visitdir(b''), True)
739 self.assertEqual(um.visitdir(b''), True)
@@ -742,8 +745,8 b' class UnionMatcherTests(unittest.TestCas'
742 self.assertEqual(um.visitdir(b'dir/subdir/x'), b'all')
745 self.assertEqual(um.visitdir(b'dir/subdir/x'), b'all')
743
746
744 def testVisitchildrensetIncludeInclude4(self):
747 def testVisitchildrensetIncludeInclude4(self):
745 m1 = matchmod.match(b'', b'', include=[b'path:dir/subdir/x'])
748 m1 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/x'])
746 m2 = matchmod.match(b'', b'', include=[b'path:dir/subdir/z'])
749 m2 = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir/z'])
747 um = matchmod.unionmatcher([m1, m2])
750 um = matchmod.unionmatcher([m1, m2])
748 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
751 self.assertEqual(um.visitchildrenset(b''), {b'dir'})
749 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
752 self.assertEqual(um.visitchildrenset(b'dir'), {b'subdir'})
@@ -756,7 +759,7 b' class UnionMatcherTests(unittest.TestCas'
756
759
757 class SubdirMatcherTests(unittest.TestCase):
760 class SubdirMatcherTests(unittest.TestCase):
758 def testVisitdir(self):
761 def testVisitdir(self):
759 m = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
762 m = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
760 sm = matchmod.subdirmatcher(b'dir', m)
763 sm = matchmod.subdirmatcher(b'dir', m)
761
764
762 self.assertEqual(sm.visitdir(b''), True)
765 self.assertEqual(sm.visitdir(b''), True)
@@ -767,7 +770,7 b' class SubdirMatcherTests(unittest.TestCa'
767 self.assertFalse(sm.visitdir(b'foo'))
770 self.assertFalse(sm.visitdir(b'foo'))
768
771
769 def testVisitchildrenset(self):
772 def testVisitchildrenset(self):
770 m = matchmod.match(b'', b'', include=[b'path:dir/subdir'])
773 m = matchmod.match(b'/repo', b'', include=[b'path:dir/subdir'])
771 sm = matchmod.subdirmatcher(b'dir', m)
774 sm = matchmod.subdirmatcher(b'dir', m)
772
775
773 self.assertEqual(sm.visitchildrenset(b''), {b'subdir'})
776 self.assertEqual(sm.visitchildrenset(b''), {b'subdir'})
@@ -781,7 +784,10 b' class SubdirMatcherTests(unittest.TestCa'
781 class PrefixdirMatcherTests(unittest.TestCase):
784 class PrefixdirMatcherTests(unittest.TestCase):
782 def testVisitdir(self):
785 def testVisitdir(self):
783 m = matchmod.match(
786 m = matchmod.match(
784 util.localpath(b'root/d'), b'e/f', [b'../a.txt', b'b.txt']
787 util.localpath(b'/root/d'),
788 b'e/f',
789 [b'../a.txt', b'b.txt'],
790 auditor=noop_auditor,
785 )
791 )
786 pm = matchmod.prefixdirmatcher(b'd', m)
792 pm = matchmod.prefixdirmatcher(b'd', m)
787
793
@@ -814,7 +820,10 b' class PrefixdirMatcherTests(unittest.Tes'
814
820
815 def testVisitchildrenset(self):
821 def testVisitchildrenset(self):
816 m = matchmod.match(
822 m = matchmod.match(
817 util.localpath(b'root/d'), b'e/f', [b'../a.txt', b'b.txt']
823 util.localpath(b'/root/d'),
824 b'e/f',
825 [b'../a.txt', b'b.txt'],
826 auditor=noop_auditor,
818 )
827 )
819 pm = matchmod.prefixdirmatcher(b'd', m)
828 pm = matchmod.prefixdirmatcher(b'd', m)
820
829
General Comments 0
You need to be logged in to leave comments. Login now