116
118
self.repository, self.revision_id))
118
120
def match(self, expected):
119
self.repository.lock_read()
121
with self.repository.lock_read():
121
122
graph = self.repository.get_graph()
122
123
got = [r for r, p in graph.iter_ancestry([self.revision_id])]
123
124
if _mod_revision.NULL_REVISION in got:
124
125
got.remove(_mod_revision.NULL_REVISION)
126
self.repository.unlock()
127
126
if sorted(got) != sorted(expected):
128
127
return _AncestryMismatch(self.revision_id, sorted(got),
129
128
sorted(expected))
188
184
return Equals(entries).match(actual)
187
class HasPathRelations(Matcher):
188
"""Matcher verifies that paths have a relation to those in another tree.
190
:ivar previous_tree: tree to compare to
191
:ivar previous_entries: List of expected entries, as (path, previous_path) pairs.
194
def __init__(self, previous_tree, previous_entries):
195
Matcher.__init__(self)
196
self.previous_tree = previous_tree
197
self.previous_entries = previous_entries
199
def get_path_map(self, tree):
200
"""Get the (path, previous_path) pairs for the current tree."""
201
with tree.lock_read(), self.previous_tree.lock_read():
202
for path, ie in tree.iter_entries_by_dir():
203
if tree.supports_rename_tracking():
204
previous_path = find_previous_path(tree, self.previous_tree, path)
206
if self.previous_tree.is_versioned(path):
211
kind = self.previous_tree.kind(previous_path)
212
if kind == 'directory':
214
if ie.parent_id is None:
215
yield (u"", previous_path)
217
yield (path+ie.kind_character(), previous_path)
220
def _strip_unreferenced_directories(entries):
221
"""Strip all directories that don't (in)directly contain any files.
223
:param entries: List of path strings or (path, previous_path) tuples to process
225
directory_used = set()
227
for (path, previous_path) in entries:
228
if not path or path[-1] == "/":
230
directories.append((path, previous_path))
232
# Yield the referenced parent directories
233
for direntry in directories:
234
if osutils.is_inside(direntry[0], path):
235
directory_used.add(direntry[0])
236
for (path, previous_path) in entries:
237
if (not path.endswith("/")) or path in directory_used:
238
yield (path, previous_path)
241
return 'HasPathRelations(%r, %r)' % (self.previous_tree, self.previous_entries)
243
def match(self, tree):
244
actual = list(self.get_path_map(tree))
245
if not tree.has_versioned_directories():
246
entries = list(self._strip_unreferenced_directories(self.previous_entries))
248
entries = self.previous_entries
249
if not tree.supports_rename_tracking():
251
(path, path if self.previous_tree.is_versioned(path) else None)
252
for (path, previous_path) in entries]
253
return Equals(entries).match(actual)
191
256
class RevisionHistoryMatches(Matcher):
192
257
"""A matcher that checks if a branch has a specific revision history.