##// END OF EJS Templates
test-manifest: create constant for empty manifest...
Martin von Zweigbergk -
r24569:5491248e default
parent child Browse files
Show More
@@ -1,389 +1,391 b''
1 import binascii
1 import binascii
2 import unittest
2 import unittest
3 import itertools
3 import itertools
4
4
5 import silenttestrunner
5 import silenttestrunner
6
6
7 from mercurial import manifest as manifestmod
7 from mercurial import manifest as manifestmod
8 from mercurial import match as matchmod
8 from mercurial import match as matchmod
9
9
10 EMTPY_MANIFEST = ''
11
10 HASH_1 = '1' * 40
12 HASH_1 = '1' * 40
11 HASH_2 = 'f' * 40
13 HASH_2 = 'f' * 40
12 HASH_3 = '1234567890abcdef0987654321deadbeef0fcafe'
14 HASH_3 = '1234567890abcdef0987654321deadbeef0fcafe'
13 A_SHORT_MANIFEST = (
15 A_SHORT_MANIFEST = (
14 'bar/baz/qux.py\0%(hash2)s%(flag2)s\n'
16 'bar/baz/qux.py\0%(hash2)s%(flag2)s\n'
15 'foo\0%(hash1)s%(flag1)s\n'
17 'foo\0%(hash1)s%(flag1)s\n'
16 ) % {'hash1': HASH_1,
18 ) % {'hash1': HASH_1,
17 'flag1': '',
19 'flag1': '',
18 'hash2': HASH_2,
20 'hash2': HASH_2,
19 'flag2': 'l',
21 'flag2': 'l',
20 }
22 }
21
23
22 A_DEEPER_MANIFEST = (
24 A_DEEPER_MANIFEST = (
23 'a/b/c/bar.py\0%(hash3)s%(flag1)s\n'
25 'a/b/c/bar.py\0%(hash3)s%(flag1)s\n'
24 'a/b/c/bar.txt\0%(hash1)s%(flag1)s\n'
26 'a/b/c/bar.txt\0%(hash1)s%(flag1)s\n'
25 'a/b/c/foo.py\0%(hash3)s%(flag1)s\n'
27 'a/b/c/foo.py\0%(hash3)s%(flag1)s\n'
26 'a/b/c/foo.txt\0%(hash2)s%(flag2)s\n'
28 'a/b/c/foo.txt\0%(hash2)s%(flag2)s\n'
27 'a/b/d/baz.py\0%(hash3)s%(flag1)s\n'
29 'a/b/d/baz.py\0%(hash3)s%(flag1)s\n'
28 'a/b/d/qux.py\0%(hash1)s%(flag2)s\n'
30 'a/b/d/qux.py\0%(hash1)s%(flag2)s\n'
29 'a/b/d/ten.txt\0%(hash3)s%(flag2)s\n'
31 'a/b/d/ten.txt\0%(hash3)s%(flag2)s\n'
30 'a/b/dog.py\0%(hash3)s%(flag1)s\n'
32 'a/b/dog.py\0%(hash3)s%(flag1)s\n'
31 'a/b/fish.py\0%(hash2)s%(flag1)s\n'
33 'a/b/fish.py\0%(hash2)s%(flag1)s\n'
32 'a/c/london.py\0%(hash3)s%(flag2)s\n'
34 'a/c/london.py\0%(hash3)s%(flag2)s\n'
33 'a/c/paper.txt\0%(hash2)s%(flag2)s\n'
35 'a/c/paper.txt\0%(hash2)s%(flag2)s\n'
34 'a/c/paris.py\0%(hash2)s%(flag1)s\n'
36 'a/c/paris.py\0%(hash2)s%(flag1)s\n'
35 'a/d/apple.py\0%(hash3)s%(flag1)s\n'
37 'a/d/apple.py\0%(hash3)s%(flag1)s\n'
36 'a/d/pizza.py\0%(hash3)s%(flag2)s\n'
38 'a/d/pizza.py\0%(hash3)s%(flag2)s\n'
37 'a/green.py\0%(hash1)s%(flag2)s\n'
39 'a/green.py\0%(hash1)s%(flag2)s\n'
38 'a/purple.py\0%(hash2)s%(flag1)s\n'
40 'a/purple.py\0%(hash2)s%(flag1)s\n'
39 'app.py\0%(hash3)s%(flag1)s\n'
41 'app.py\0%(hash3)s%(flag1)s\n'
40 'readme.txt\0%(hash2)s%(flag1)s\n'
42 'readme.txt\0%(hash2)s%(flag1)s\n'
41 ) % {'hash1': HASH_1,
43 ) % {'hash1': HASH_1,
42 'flag1': '',
44 'flag1': '',
43 'hash2': HASH_2,
45 'hash2': HASH_2,
44 'flag2': 'l',
46 'flag2': 'l',
45 'hash3': HASH_3,
47 'hash3': HASH_3,
46 }
48 }
47
49
48 HUGE_MANIFEST_ENTRIES = 200001
50 HUGE_MANIFEST_ENTRIES = 200001
49
51
50 A_HUGE_MANIFEST = ''.join(sorted(
52 A_HUGE_MANIFEST = ''.join(sorted(
51 'file%d\0%s%s\n' % (i, h, f) for i, h, f in
53 'file%d\0%s%s\n' % (i, h, f) for i, h, f in
52 itertools.izip(xrange(200001),
54 itertools.izip(xrange(200001),
53 itertools.cycle((HASH_1, HASH_2)),
55 itertools.cycle((HASH_1, HASH_2)),
54 itertools.cycle(('', 'x', 'l')))))
56 itertools.cycle(('', 'x', 'l')))))
55
57
56 def parsemanifest(text):
58 def parsemanifest(text):
57 return manifestmod.manifestdict(text)
59 return manifestmod.manifestdict(text)
58
60
59 class testmanifest(unittest.TestCase):
61 class testmanifest(unittest.TestCase):
60
62
61 def assertIn(self, thing, container, msg=None):
63 def assertIn(self, thing, container, msg=None):
62 # assertIn new in 2.7, use it if available, otherwise polyfill
64 # assertIn new in 2.7, use it if available, otherwise polyfill
63 sup = getattr(unittest.TestCase, 'assertIn', False)
65 sup = getattr(unittest.TestCase, 'assertIn', False)
64 if sup:
66 if sup:
65 return sup(self, thing, container, msg=msg)
67 return sup(self, thing, container, msg=msg)
66 if not msg:
68 if not msg:
67 msg = 'Expected %r in %r' % (thing, container)
69 msg = 'Expected %r in %r' % (thing, container)
68 self.assert_(thing in container, msg)
70 self.assert_(thing in container, msg)
69
71
70 def testEmptyManifest(self):
72 def testEmptyManifest(self):
71 m = parsemanifest('')
73 m = parsemanifest(EMTPY_MANIFEST)
72 self.assertEqual(0, len(m))
74 self.assertEqual(0, len(m))
73 self.assertEqual([], list(m))
75 self.assertEqual([], list(m))
74
76
75 def testManifest(self):
77 def testManifest(self):
76 m = parsemanifest(A_SHORT_MANIFEST)
78 m = parsemanifest(A_SHORT_MANIFEST)
77 self.assertEqual(['bar/baz/qux.py', 'foo'], list(m))
79 self.assertEqual(['bar/baz/qux.py', 'foo'], list(m))
78 self.assertEqual(binascii.unhexlify(HASH_2), m['bar/baz/qux.py'])
80 self.assertEqual(binascii.unhexlify(HASH_2), m['bar/baz/qux.py'])
79 self.assertEqual('l', m.flags('bar/baz/qux.py'))
81 self.assertEqual('l', m.flags('bar/baz/qux.py'))
80 self.assertEqual(binascii.unhexlify(HASH_1), m['foo'])
82 self.assertEqual(binascii.unhexlify(HASH_1), m['foo'])
81 self.assertEqual('', m.flags('foo'))
83 self.assertEqual('', m.flags('foo'))
82 self.assertRaises(KeyError, lambda : m['wat'])
84 self.assertRaises(KeyError, lambda : m['wat'])
83
85
84 def testSetItem(self):
86 def testSetItem(self):
85 want = binascii.unhexlify(HASH_1)
87 want = binascii.unhexlify(HASH_1)
86
88
87 m = parsemanifest('')
89 m = parsemanifest(EMTPY_MANIFEST)
88 m['a'] = want
90 m['a'] = want
89 self.assertIn('a', m)
91 self.assertIn('a', m)
90 self.assertEqual(want, m['a'])
92 self.assertEqual(want, m['a'])
91 self.assertEqual('a\0' + HASH_1 + '\n', m.text())
93 self.assertEqual('a\0' + HASH_1 + '\n', m.text())
92
94
93 m = parsemanifest(A_SHORT_MANIFEST)
95 m = parsemanifest(A_SHORT_MANIFEST)
94 m['a'] = want
96 m['a'] = want
95 self.assertEqual(want, m['a'])
97 self.assertEqual(want, m['a'])
96 self.assertEqual('a\0' + HASH_1 + '\n' + A_SHORT_MANIFEST,
98 self.assertEqual('a\0' + HASH_1 + '\n' + A_SHORT_MANIFEST,
97 m.text())
99 m.text())
98
100
99 def testSetFlag(self):
101 def testSetFlag(self):
100 want = 'x'
102 want = 'x'
101
103
102 m = parsemanifest('')
104 m = parsemanifest(EMTPY_MANIFEST)
103 # first add a file; a file-less flag makes no sense
105 # first add a file; a file-less flag makes no sense
104 m['a'] = binascii.unhexlify(HASH_1)
106 m['a'] = binascii.unhexlify(HASH_1)
105 m.setflag('a', want)
107 m.setflag('a', want)
106 self.assertEqual(want, m.flags('a'))
108 self.assertEqual(want, m.flags('a'))
107 self.assertEqual('a\0' + HASH_1 + want + '\n', m.text())
109 self.assertEqual('a\0' + HASH_1 + want + '\n', m.text())
108
110
109 m = parsemanifest(A_SHORT_MANIFEST)
111 m = parsemanifest(A_SHORT_MANIFEST)
110 # first add a file; a file-less flag makes no sense
112 # first add a file; a file-less flag makes no sense
111 m['a'] = binascii.unhexlify(HASH_1)
113 m['a'] = binascii.unhexlify(HASH_1)
112 m.setflag('a', want)
114 m.setflag('a', want)
113 self.assertEqual(want, m.flags('a'))
115 self.assertEqual(want, m.flags('a'))
114 self.assertEqual('a\0' + HASH_1 + want + '\n' + A_SHORT_MANIFEST,
116 self.assertEqual('a\0' + HASH_1 + want + '\n' + A_SHORT_MANIFEST,
115 m.text())
117 m.text())
116
118
117 def testCopy(self):
119 def testCopy(self):
118 m = parsemanifest(A_SHORT_MANIFEST)
120 m = parsemanifest(A_SHORT_MANIFEST)
119 m['a'] = binascii.unhexlify(HASH_1)
121 m['a'] = binascii.unhexlify(HASH_1)
120 m2 = m.copy()
122 m2 = m.copy()
121 del m
123 del m
122 del m2 # make sure we don't double free() anything
124 del m2 # make sure we don't double free() anything
123
125
124 def testCompaction(self):
126 def testCompaction(self):
125 unhex = binascii.unhexlify
127 unhex = binascii.unhexlify
126 h1, h2 = unhex(HASH_1), unhex(HASH_2)
128 h1, h2 = unhex(HASH_1), unhex(HASH_2)
127 m = parsemanifest(A_SHORT_MANIFEST)
129 m = parsemanifest(A_SHORT_MANIFEST)
128 m['alpha'] = h1
130 m['alpha'] = h1
129 m['beta'] = h2
131 m['beta'] = h2
130 del m['foo']
132 del m['foo']
131 want = 'alpha\0%s\nbar/baz/qux.py\0%sl\nbeta\0%s\n' % (
133 want = 'alpha\0%s\nbar/baz/qux.py\0%sl\nbeta\0%s\n' % (
132 HASH_1, HASH_2, HASH_2)
134 HASH_1, HASH_2, HASH_2)
133 self.assertEqual(want, m.text())
135 self.assertEqual(want, m.text())
134 self.assertEqual(3, len(m))
136 self.assertEqual(3, len(m))
135 self.assertEqual(['alpha', 'bar/baz/qux.py', 'beta'], list(m))
137 self.assertEqual(['alpha', 'bar/baz/qux.py', 'beta'], list(m))
136 self.assertEqual(h1, m['alpha'])
138 self.assertEqual(h1, m['alpha'])
137 self.assertEqual(h2, m['bar/baz/qux.py'])
139 self.assertEqual(h2, m['bar/baz/qux.py'])
138 self.assertEqual(h2, m['beta'])
140 self.assertEqual(h2, m['beta'])
139 self.assertEqual('', m.flags('alpha'))
141 self.assertEqual('', m.flags('alpha'))
140 self.assertEqual('l', m.flags('bar/baz/qux.py'))
142 self.assertEqual('l', m.flags('bar/baz/qux.py'))
141 self.assertEqual('', m.flags('beta'))
143 self.assertEqual('', m.flags('beta'))
142 self.assertRaises(KeyError, lambda : m['foo'])
144 self.assertRaises(KeyError, lambda : m['foo'])
143
145
144 def testSetGetNodeSuffix(self):
146 def testSetGetNodeSuffix(self):
145 clean = parsemanifest(A_SHORT_MANIFEST)
147 clean = parsemanifest(A_SHORT_MANIFEST)
146 m = parsemanifest(A_SHORT_MANIFEST)
148 m = parsemanifest(A_SHORT_MANIFEST)
147 h = m['foo']
149 h = m['foo']
148 f = m.flags('foo')
150 f = m.flags('foo')
149 want = h + 'a'
151 want = h + 'a'
150 # Merge code wants to set 21-byte fake hashes at times
152 # Merge code wants to set 21-byte fake hashes at times
151 m['foo'] = want
153 m['foo'] = want
152 self.assertEqual(want, m['foo'])
154 self.assertEqual(want, m['foo'])
153 self.assertEqual([('bar/baz/qux.py', binascii.unhexlify(HASH_2)),
155 self.assertEqual([('bar/baz/qux.py', binascii.unhexlify(HASH_2)),
154 ('foo', binascii.unhexlify(HASH_1) + 'a')],
156 ('foo', binascii.unhexlify(HASH_1) + 'a')],
155 list(m.iteritems()))
157 list(m.iteritems()))
156 # Sometimes it even tries a 22-byte fake hash, but we can
158 # Sometimes it even tries a 22-byte fake hash, but we can
157 # return 21 and it'll work out
159 # return 21 and it'll work out
158 m['foo'] = want + '+'
160 m['foo'] = want + '+'
159 self.assertEqual(want, m['foo'])
161 self.assertEqual(want, m['foo'])
160 # make sure the suffix survives a copy
162 # make sure the suffix survives a copy
161 match = matchmod.match('', '', ['re:foo'])
163 match = matchmod.match('', '', ['re:foo'])
162 m2 = m.matches(match)
164 m2 = m.matches(match)
163 self.assertEqual(want, m2['foo'])
165 self.assertEqual(want, m2['foo'])
164 self.assertEqual(1, len(m2))
166 self.assertEqual(1, len(m2))
165 m2 = m.copy()
167 m2 = m.copy()
166 self.assertEqual(want, m2['foo'])
168 self.assertEqual(want, m2['foo'])
167 # suffix with iteration
169 # suffix with iteration
168 self.assertEqual([('bar/baz/qux.py', binascii.unhexlify(HASH_2)),
170 self.assertEqual([('bar/baz/qux.py', binascii.unhexlify(HASH_2)),
169 ('foo', want)],
171 ('foo', want)],
170 list(m.iteritems()))
172 list(m.iteritems()))
171
173
172 # shows up in diff
174 # shows up in diff
173 self.assertEqual({'foo': ((want, f), (h, ''))}, m.diff(clean))
175 self.assertEqual({'foo': ((want, f), (h, ''))}, m.diff(clean))
174 self.assertEqual({'foo': ((h, ''), (want, f))}, clean.diff(m))
176 self.assertEqual({'foo': ((h, ''), (want, f))}, clean.diff(m))
175
177
176 def testMatchException(self):
178 def testMatchException(self):
177 m = parsemanifest(A_SHORT_MANIFEST)
179 m = parsemanifest(A_SHORT_MANIFEST)
178 match = matchmod.match('', '', ['re:.*'])
180 match = matchmod.match('', '', ['re:.*'])
179 def filt(path):
181 def filt(path):
180 if path == 'foo':
182 if path == 'foo':
181 assert False
183 assert False
182 return True
184 return True
183 match.matchfn = filt
185 match.matchfn = filt
184 self.assertRaises(AssertionError, m.matches, match)
186 self.assertRaises(AssertionError, m.matches, match)
185
187
186 def testRemoveItem(self):
188 def testRemoveItem(self):
187 m = parsemanifest(A_SHORT_MANIFEST)
189 m = parsemanifest(A_SHORT_MANIFEST)
188 del m['foo']
190 del m['foo']
189 self.assertRaises(KeyError, lambda : m['foo'])
191 self.assertRaises(KeyError, lambda : m['foo'])
190 self.assertEqual(1, len(m))
192 self.assertEqual(1, len(m))
191 self.assertEqual(1, len(list(m)))
193 self.assertEqual(1, len(list(m)))
192 # now restore and make sure everything works right
194 # now restore and make sure everything works right
193 m['foo'] = 'a' * 20
195 m['foo'] = 'a' * 20
194 self.assertEqual(2, len(m))
196 self.assertEqual(2, len(m))
195 self.assertEqual(2, len(list(m)))
197 self.assertEqual(2, len(list(m)))
196
198
197 def testManifestDiff(self):
199 def testManifestDiff(self):
198 MISSING = (None, '')
200 MISSING = (None, '')
199 addl = 'z-only-in-left\0' + HASH_1 + '\n'
201 addl = 'z-only-in-left\0' + HASH_1 + '\n'
200 addr = 'z-only-in-right\0' + HASH_2 + 'x\n'
202 addr = 'z-only-in-right\0' + HASH_2 + 'x\n'
201 left = parsemanifest(
203 left = parsemanifest(
202 A_SHORT_MANIFEST.replace(HASH_1, HASH_3 + 'x') + addl)
204 A_SHORT_MANIFEST.replace(HASH_1, HASH_3 + 'x') + addl)
203 right = parsemanifest(A_SHORT_MANIFEST + addr)
205 right = parsemanifest(A_SHORT_MANIFEST + addr)
204 want = {
206 want = {
205 'foo': ((binascii.unhexlify(HASH_3), 'x'),
207 'foo': ((binascii.unhexlify(HASH_3), 'x'),
206 (binascii.unhexlify(HASH_1), '')),
208 (binascii.unhexlify(HASH_1), '')),
207 'z-only-in-left': ((binascii.unhexlify(HASH_1), ''), MISSING),
209 'z-only-in-left': ((binascii.unhexlify(HASH_1), ''), MISSING),
208 'z-only-in-right': (MISSING, (binascii.unhexlify(HASH_2), 'x')),
210 'z-only-in-right': (MISSING, (binascii.unhexlify(HASH_2), 'x')),
209 }
211 }
210 self.assertEqual(want, left.diff(right))
212 self.assertEqual(want, left.diff(right))
211
213
212 want = {
214 want = {
213 'bar/baz/qux.py': (MISSING, (binascii.unhexlify(HASH_2), 'l')),
215 'bar/baz/qux.py': (MISSING, (binascii.unhexlify(HASH_2), 'l')),
214 'foo': (MISSING, (binascii.unhexlify(HASH_3), 'x')),
216 'foo': (MISSING, (binascii.unhexlify(HASH_3), 'x')),
215 'z-only-in-left': (MISSING, (binascii.unhexlify(HASH_1), '')),
217 'z-only-in-left': (MISSING, (binascii.unhexlify(HASH_1), '')),
216 }
218 }
217 self.assertEqual(want, parsemanifest('').diff(left))
219 self.assertEqual(want, parsemanifest(EMTPY_MANIFEST).diff(left))
218
220
219 want = {
221 want = {
220 'bar/baz/qux.py': ((binascii.unhexlify(HASH_2), 'l'), MISSING),
222 'bar/baz/qux.py': ((binascii.unhexlify(HASH_2), 'l'), MISSING),
221 'foo': ((binascii.unhexlify(HASH_3), 'x'), MISSING),
223 'foo': ((binascii.unhexlify(HASH_3), 'x'), MISSING),
222 'z-only-in-left': ((binascii.unhexlify(HASH_1), ''), MISSING),
224 'z-only-in-left': ((binascii.unhexlify(HASH_1), ''), MISSING),
223 }
225 }
224 self.assertEqual(want, left.diff(parsemanifest('')))
226 self.assertEqual(want, left.diff(parsemanifest(EMTPY_MANIFEST)))
225 copy = right.copy()
227 copy = right.copy()
226 del copy['z-only-in-right']
228 del copy['z-only-in-right']
227 del right['foo']
229 del right['foo']
228 want = {
230 want = {
229 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
231 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
230 'z-only-in-right': ((binascii.unhexlify(HASH_2), 'x'), MISSING),
232 'z-only-in-right': ((binascii.unhexlify(HASH_2), 'x'), MISSING),
231 }
233 }
232 self.assertEqual(want, right.diff(copy))
234 self.assertEqual(want, right.diff(copy))
233
235
234 short = parsemanifest(A_SHORT_MANIFEST)
236 short = parsemanifest(A_SHORT_MANIFEST)
235 pruned = short.copy()
237 pruned = short.copy()
236 del pruned['foo']
238 del pruned['foo']
237 want = {
239 want = {
238 'foo': ((binascii.unhexlify(HASH_1), ''), MISSING),
240 'foo': ((binascii.unhexlify(HASH_1), ''), MISSING),
239 }
241 }
240 self.assertEqual(want, short.diff(pruned))
242 self.assertEqual(want, short.diff(pruned))
241 want = {
243 want = {
242 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
244 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
243 }
245 }
244 self.assertEqual(want, pruned.diff(short))
246 self.assertEqual(want, pruned.diff(short))
245 want = {
247 want = {
246 'bar/baz/qux.py': None,
248 'bar/baz/qux.py': None,
247 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
249 'foo': (MISSING, (binascii.unhexlify(HASH_1), '')),
248 }
250 }
249 self.assertEqual(want, pruned.diff(short, True))
251 self.assertEqual(want, pruned.diff(short, True))
250
252
251 def testReversedLines(self):
253 def testReversedLines(self):
252 backwards = ''.join(
254 backwards = ''.join(
253 l + '\n' for l in reversed(A_SHORT_MANIFEST.split('\n')) if l)
255 l + '\n' for l in reversed(A_SHORT_MANIFEST.split('\n')) if l)
254 try:
256 try:
255 parsemanifest(backwards)
257 parsemanifest(backwards)
256 self.fail('Should have raised ValueError')
258 self.fail('Should have raised ValueError')
257 except ValueError, v:
259 except ValueError, v:
258 self.assertIn('Manifest lines not in sorted order.', str(v))
260 self.assertIn('Manifest lines not in sorted order.', str(v))
259
261
260 def testNoTerminalNewline(self):
262 def testNoTerminalNewline(self):
261 try:
263 try:
262 parsemanifest(A_SHORT_MANIFEST + 'wat')
264 parsemanifest(A_SHORT_MANIFEST + 'wat')
263 self.fail('Should have raised ValueError')
265 self.fail('Should have raised ValueError')
264 except ValueError, v:
266 except ValueError, v:
265 self.assertIn('Manifest did not end in a newline.', str(v))
267 self.assertIn('Manifest did not end in a newline.', str(v))
266
268
267 def testNoNewLineAtAll(self):
269 def testNoNewLineAtAll(self):
268 try:
270 try:
269 parsemanifest('wat')
271 parsemanifest('wat')
270 self.fail('Should have raised ValueError')
272 self.fail('Should have raised ValueError')
271 except ValueError, v:
273 except ValueError, v:
272 self.assertIn('Manifest did not end in a newline.', str(v))
274 self.assertIn('Manifest did not end in a newline.', str(v))
273
275
274 def testHugeManifest(self):
276 def testHugeManifest(self):
275 m = parsemanifest(A_HUGE_MANIFEST)
277 m = parsemanifest(A_HUGE_MANIFEST)
276 self.assertEqual(HUGE_MANIFEST_ENTRIES, len(m))
278 self.assertEqual(HUGE_MANIFEST_ENTRIES, len(m))
277 self.assertEqual(len(m), len(list(m)))
279 self.assertEqual(len(m), len(list(m)))
278
280
279 def testMatchesMetadata(self):
281 def testMatchesMetadata(self):
280 '''Tests matches() for a few specific files to make sure that both
282 '''Tests matches() for a few specific files to make sure that both
281 the set of files as well as their flags and nodeids are correct in
283 the set of files as well as their flags and nodeids are correct in
282 the resulting manifest.'''
284 the resulting manifest.'''
283 m = parsemanifest(A_HUGE_MANIFEST)
285 m = parsemanifest(A_HUGE_MANIFEST)
284
286
285 match = matchmod.match('/', '',
287 match = matchmod.match('/', '',
286 ['file1', 'file200', 'file300'], exact=True)
288 ['file1', 'file200', 'file300'], exact=True)
287 m2 = m.matches(match)
289 m2 = m.matches(match)
288
290
289 w = ('file1\0%sx\n'
291 w = ('file1\0%sx\n'
290 'file200\0%sl\n'
292 'file200\0%sl\n'
291 'file300\0%s\n') % (HASH_2, HASH_1, HASH_1)
293 'file300\0%s\n') % (HASH_2, HASH_1, HASH_1)
292 self.assertEqual(w, m2.text())
294 self.assertEqual(w, m2.text())
293
295
294 def testMatchesNonexistentFile(self):
296 def testMatchesNonexistentFile(self):
295 '''Tests matches() for a small set of specific files, including one
297 '''Tests matches() for a small set of specific files, including one
296 nonexistent file to make sure in only matches against existing files.
298 nonexistent file to make sure in only matches against existing files.
297 '''
299 '''
298 m = parsemanifest(A_DEEPER_MANIFEST)
300 m = parsemanifest(A_DEEPER_MANIFEST)
299
301
300 match = matchmod.match('/', '',
302 match = matchmod.match('/', '',
301 ['a/b/c/bar.txt', 'a/b/d/qux.py', 'readme.txt', 'nonexistent'],
303 ['a/b/c/bar.txt', 'a/b/d/qux.py', 'readme.txt', 'nonexistent'],
302 exact=True)
304 exact=True)
303 m2 = m.matches(match)
305 m2 = m.matches(match)
304
306
305 self.assertEqual(
307 self.assertEqual(
306 ['a/b/c/bar.txt', 'a/b/d/qux.py', 'readme.txt'],
308 ['a/b/c/bar.txt', 'a/b/d/qux.py', 'readme.txt'],
307 m2.keys())
309 m2.keys())
308
310
309 def testMatchesNonexistentDirectory(self):
311 def testMatchesNonexistentDirectory(self):
310 '''Tests matches() for a relpath match on a directory that doesn't
312 '''Tests matches() for a relpath match on a directory that doesn't
311 actually exist.'''
313 actually exist.'''
312 m = parsemanifest(A_DEEPER_MANIFEST)
314 m = parsemanifest(A_DEEPER_MANIFEST)
313
315
314 match = matchmod.match('/', '', ['a/f'], default='relpath')
316 match = matchmod.match('/', '', ['a/f'], default='relpath')
315 m2 = m.matches(match)
317 m2 = m.matches(match)
316
318
317 self.assertEqual([], m2.keys())
319 self.assertEqual([], m2.keys())
318
320
319 def testMatchesExactLarge(self):
321 def testMatchesExactLarge(self):
320 '''Tests matches() for files matching a large list of exact files.
322 '''Tests matches() for files matching a large list of exact files.
321 '''
323 '''
322 m = parsemanifest(A_HUGE_MANIFEST)
324 m = parsemanifest(A_HUGE_MANIFEST)
323
325
324 flist = m.keys()[80:300]
326 flist = m.keys()[80:300]
325 match = matchmod.match('/', '', flist, exact=True)
327 match = matchmod.match('/', '', flist, exact=True)
326 m2 = m.matches(match)
328 m2 = m.matches(match)
327
329
328 self.assertEqual(flist, m2.keys())
330 self.assertEqual(flist, m2.keys())
329
331
330 def testMatchesFull(self):
332 def testMatchesFull(self):
331 '''Tests matches() for what should be a full match.'''
333 '''Tests matches() for what should be a full match.'''
332 m = parsemanifest(A_DEEPER_MANIFEST)
334 m = parsemanifest(A_DEEPER_MANIFEST)
333
335
334 match = matchmod.match('/', '', [''])
336 match = matchmod.match('/', '', [''])
335 m2 = m.matches(match)
337 m2 = m.matches(match)
336
338
337 self.assertEqual(m.keys(), m2.keys())
339 self.assertEqual(m.keys(), m2.keys())
338
340
339 def testMatchesDirectory(self):
341 def testMatchesDirectory(self):
340 '''Tests matches() on a relpath match on a directory, which should
342 '''Tests matches() on a relpath match on a directory, which should
341 match against all files within said directory.'''
343 match against all files within said directory.'''
342 m = parsemanifest(A_DEEPER_MANIFEST)
344 m = parsemanifest(A_DEEPER_MANIFEST)
343
345
344 match = matchmod.match('/', '', ['a/b'], default='relpath')
346 match = matchmod.match('/', '', ['a/b'], default='relpath')
345 m2 = m.matches(match)
347 m2 = m.matches(match)
346
348
347 self.assertEqual([
349 self.assertEqual([
348 'a/b/c/bar.py', 'a/b/c/bar.txt', 'a/b/c/foo.py', 'a/b/c/foo.txt',
350 'a/b/c/bar.py', 'a/b/c/bar.txt', 'a/b/c/foo.py', 'a/b/c/foo.txt',
349 'a/b/d/baz.py', 'a/b/d/qux.py', 'a/b/d/ten.txt', 'a/b/dog.py',
351 'a/b/d/baz.py', 'a/b/d/qux.py', 'a/b/d/ten.txt', 'a/b/dog.py',
350 'a/b/fish.py'], m2.keys())
352 'a/b/fish.py'], m2.keys())
351
353
352 def testMatchesExactPath(self):
354 def testMatchesExactPath(self):
353 '''Tests matches() on an exact match on a directory, which should
355 '''Tests matches() on an exact match on a directory, which should
354 result in an empty manifest because you can't perform an exact match
356 result in an empty manifest because you can't perform an exact match
355 against a directory.'''
357 against a directory.'''
356 m = parsemanifest(A_DEEPER_MANIFEST)
358 m = parsemanifest(A_DEEPER_MANIFEST)
357
359
358 match = matchmod.match('/', '', ['a/b'], exact=True)
360 match = matchmod.match('/', '', ['a/b'], exact=True)
359 m2 = m.matches(match)
361 m2 = m.matches(match)
360
362
361 self.assertEqual([], m2.keys())
363 self.assertEqual([], m2.keys())
362
364
363 def testMatchesCwd(self):
365 def testMatchesCwd(self):
364 '''Tests matches() on a relpath match with the current directory ('.')
366 '''Tests matches() on a relpath match with the current directory ('.')
365 when not in the root directory.'''
367 when not in the root directory.'''
366 m = parsemanifest(A_DEEPER_MANIFEST)
368 m = parsemanifest(A_DEEPER_MANIFEST)
367
369
368 match = matchmod.match('/', 'a/b', ['.'], default='relpath')
370 match = matchmod.match('/', 'a/b', ['.'], default='relpath')
369 m2 = m.matches(match)
371 m2 = m.matches(match)
370
372
371 self.assertEqual([
373 self.assertEqual([
372 'a/b/c/bar.py', 'a/b/c/bar.txt', 'a/b/c/foo.py', 'a/b/c/foo.txt',
374 'a/b/c/bar.py', 'a/b/c/bar.txt', 'a/b/c/foo.py', 'a/b/c/foo.txt',
373 'a/b/d/baz.py', 'a/b/d/qux.py', 'a/b/d/ten.txt', 'a/b/dog.py',
375 'a/b/d/baz.py', 'a/b/d/qux.py', 'a/b/d/ten.txt', 'a/b/dog.py',
374 'a/b/fish.py'], m2.keys())
376 'a/b/fish.py'], m2.keys())
375
377
376 def testMatchesWithPattern(self):
378 def testMatchesWithPattern(self):
377 '''Tests matches() for files matching a pattern that reside
379 '''Tests matches() for files matching a pattern that reside
378 deeper than the specified directory.'''
380 deeper than the specified directory.'''
379 m = parsemanifest(A_DEEPER_MANIFEST)
381 m = parsemanifest(A_DEEPER_MANIFEST)
380
382
381 match = matchmod.match('/', '', ['a/b/*/*.txt'])
383 match = matchmod.match('/', '', ['a/b/*/*.txt'])
382 m2 = m.matches(match)
384 m2 = m.matches(match)
383
385
384 self.assertEqual(
386 self.assertEqual(
385 ['a/b/c/bar.txt', 'a/b/c/foo.txt', 'a/b/d/ten.txt'],
387 ['a/b/c/bar.txt', 'a/b/c/foo.txt', 'a/b/d/ten.txt'],
386 m2.keys())
388 m2.keys())
387
389
388 if __name__ == '__main__':
390 if __name__ == '__main__':
389 silenttestrunner.main(__name__)
391 silenttestrunner.main(__name__)
General Comments 0
You need to be logged in to leave comments. Login now