/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
5361.3.7 by John Arbash Meinel
Merge bzr.dev 5390
1
# Copyright (C) 2006-2010 Canonical Ltd
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
2
# Authors: Robert Collins <robert.collins@canonical.com>
2241.1.1 by Martin Pool
Change RepositoryFormat to use a Registry rather than ad-hoc dictionary
3
#          and others
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
4
#
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
5
# This program is free software; you can redistribute it and/or modify
6
# it under the terms of the GNU General Public License as published by
7
# the Free Software Foundation; either version 2 of the License, or
8
# (at your option) any later version.
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
9
#
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
10
# This program is distributed in the hope that it will be useful,
11
# but WITHOUT ANY WARRANTY; without even the implied warranty of
12
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
# GNU General Public License for more details.
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
14
#
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
15
# You should have received a copy of the GNU General Public License
16
# along with this program; if not, write to the Free Software
4183.7.1 by Sabin Iacob
update FSF mailing address
17
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
18
19
1904.2.5 by Martin Pool
Fix format warning inside test suite and add test
20
"""Repository implementation tests for bzr.
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
21
22
These test the conformance of all the repository variations to the expected API.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
23
Specific tests for individual formats are in the tests/test_repository.py file
4523.1.1 by Martin Pool
Rename tests.branch_implementations to per_branch
24
rather than in tests/per_branch/*.py.
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
25
"""
26
2241.1.2 by Martin Pool
change to using external Repository format registry
27
from bzrlib import (
28
    repository,
29
    )
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
30
from bzrlib.revision import NULL_REVISION
5651.3.1 by Jelmer Vernooij
Add RepositoryFormatRegistry.
31
from bzrlib.remote import RemoteRepositoryFormat
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
32
from bzrlib.tests import (
5017.3.24 by Vincent Ladeuil
selftest -s bt.test_selftest passing
33
    default_transport,
34
    multiply_scenarios,
35
    multiply_tests,
36
    test_server,
37
    )
5363.2.18 by Jelmer Vernooij
Rename TestCaseWithBzrDir -> TestCaseWithControlDir.
38
from bzrlib.tests.per_controldir.test_controldir import TestCaseWithControlDir
5017.3.45 by Vincent Ladeuil
Move MemoryServer back into bzrlib.transport.memory as it's needed as soon as a MemoryTransport is used. Add a NEWS entry.
39
from bzrlib.transport import memory
1534.4.40 by Robert Collins
Add RepositoryFormats and allow bzrdir.open or create _repository to be used.
40
41
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
42
def formats_to_scenarios(formats, transport_server, transport_readonly_server,
43
    vfs_transport_factory=None):
44
    """Transform the input formats to a list of scenarios.
2553.2.2 by Robert Collins
Move RepositoryTestProviderAdapter into the tests part of the code base.
45
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
46
    :param formats: A list of (scenario_name_suffix, repo_format)
3543.1.3 by Martin Pool
Better docstring for formats_to_scenarios
47
        where the scenario_name_suffix is to be appended to the format
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
48
        name, and the repo_format is a RepositoryFormat subclass
3543.1.3 by Martin Pool
Better docstring for formats_to_scenarios
49
        instance.
50
    :returns: Scenarios of [(scenario_name, {parameter_name: value})]
2553.2.2 by Robert Collins
Move RepositoryTestProviderAdapter into the tests part of the code base.
51
    """
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
52
    result = []
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
53
    for scenario_name_suffix, repository_format in formats:
3453.5.3 by Andrew Bennetts
Merge make-branch-and-tree-fix.
54
        scenario_name = repository_format.__class__.__name__
55
        scenario_name += scenario_name_suffix
56
        scenario = (scenario_name,
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
57
            {"transport_server":transport_server,
58
             "transport_readonly_server":transport_readonly_server,
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
59
             "bzrdir_format":repository_format._matchingbzrdir,
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
60
             "repository_format":repository_format,
61
             })
62
        # Only override the test's vfs_transport_factory if one was
63
        # specified, otherwise just leave the default in place.
64
        if vfs_transport_factory:
65
            scenario[1]['vfs_transport_factory'] = vfs_transport_factory
66
        result.append(scenario)
67
    return result
68
69
70
def all_repository_format_scenarios():
3474.2.1 by Martin Pool
Merge and cleanup pre-external-reference-repository tests
71
    """Return a list of test scenarios for parameterising repository tests.
72
    """
5651.4.1 by Jelmer Vernooij
Add docstrings.
73
    all_formats = repository.format_registry._get_all()
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
74
    # format_scenarios is all the implementations of Repository; i.e. all disk
75
    # formats plus RemoteRepository.
76
    format_scenarios = formats_to_scenarios(
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
77
        [('', format) for format in all_formats],
3825.4.3 by Andrew Bennetts
Conditionally replace LocalURLServer in the test rather than changing the default_transport behaviour of per_repository tests.
78
        default_transport,
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
79
        # None here will cause a readonly decorator to be created
80
        # by the TestCaseWithTransport.get_readonly_transport method.
81
        None)
82
    format_scenarios.extend(formats_to_scenarios(
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
83
        [('-default', RemoteRepositoryFormat())],
5017.3.24 by Vincent Ladeuil
selftest -s bt.test_selftest passing
84
        test_server.SmartTCPServer_for_testing,
85
        test_server.ReadonlySmartTCPServer_for_testing,
5017.3.45 by Vincent Ladeuil
Move MemoryServer back into bzrlib.transport.memory as it's needed as soon as a MemoryTransport is used. Add a NEWS entry.
86
        memory.MemoryServer))
3453.5.3 by Andrew Bennetts
Merge make-branch-and-tree-fix.
87
    format_scenarios.extend(formats_to_scenarios(
3543.1.1 by Michael Hudson
change the scenario multiplication to get the bzrdir format from the tree and
88
        [('-v2', RemoteRepositoryFormat())],
5017.3.24 by Vincent Ladeuil
selftest -s bt.test_selftest passing
89
        test_server.SmartTCPServer_for_testing_v2_only,
90
        test_server.ReadonlySmartTCPServer_for_testing_v2_only,
5017.3.45 by Vincent Ladeuil
Move MemoryServer back into bzrlib.transport.memory as it's needed as soon as a MemoryTransport is used. Add a NEWS entry.
91
        memory.MemoryServer))
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
92
    return format_scenarios
2553.2.2 by Robert Collins
Move RepositoryTestProviderAdapter into the tests part of the code base.
93
94
5363.2.18 by Jelmer Vernooij
Rename TestCaseWithBzrDir -> TestCaseWithControlDir.
95
class TestCaseWithRepository(TestCaseWithControlDir):
2485.7.1 by Robert Collins
Relocate TestCaseWithRepository to be more central.
96
3697.6.2 by Andrew Bennetts
Add test for preserving shared repository format when sprouting from a smart server.
97
    def make_repository(self, relpath, shared=False, format=None):
2485.7.1 by Robert Collins
Relocate TestCaseWithRepository to be more central.
98
        if format is None:
99
            # Create a repository of the type we are trying to test.
100
            made_control = self.make_bzrdir(relpath)
3697.6.2 by Andrew Bennetts
Add test for preserving shared repository format when sprouting from a smart server.
101
            repo = self.repository_format.initialize(made_control,
102
                    shared=shared)
2553.2.2 by Robert Collins
Move RepositoryTestProviderAdapter into the tests part of the code base.
103
            if getattr(self, "repository_to_test_repository", None):
2553.2.1 by Robert Collins
Overhaul RepositoryTestAdapter to be cleaner and more modular.
104
                repo = self.repository_to_test_repository(repo)
105
            return repo
2485.7.1 by Robert Collins
Relocate TestCaseWithRepository to be more central.
106
        else:
107
            return super(TestCaseWithRepository, self).make_repository(
3697.6.2 by Andrew Bennetts
Add test for preserving shared repository format when sprouting from a smart server.
108
                relpath, shared=shared, format=format)
2485.7.1 by Robert Collins
Relocate TestCaseWithRepository to be more central.
109
110
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
111
class BrokenRepoScenario(object):
112
    """Base class for defining scenarios for testing check and reconcile.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
113
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
114
    A subclass needs to define the following methods:
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
115
        :populate_repository: a method to use to populate a repository with
116
            sample revisions, inventories and file versions.
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
117
        :all_versions_after_reconcile: all the versions in repository after
118
            reconcile.  run_test verifies that the text of each of these
119
            versions of the file is unchanged by the reconcile.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
120
        :populated_parents: a list of (parents list, revision).  Each version
121
            of the file is verified to have the given parents before running
122
            the reconcile.  i.e. this is used to assert that the repo from the
123
            factory is what we expect.
124
        :corrected_parents: a list of (parents list, revision).  Each version
125
            of the file is verified to have the given parents after the
126
            reconcile.  i.e. this is used to assert that reconcile made the
127
            changes we expect it to make.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
128
2927.2.5 by Andrew Bennetts
Remove corrected_inventories, add proper description of corrected_fulltexts.
129
    A subclass may define the following optional method as well:
130
        :corrected_fulltexts: a list of file versions that should be stored as
131
            fulltexts (not deltas) after reconcile.  run_test will verify that
132
            this occurs.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
133
    """
134
135
    def __init__(self, test_case):
136
        self.test_case = test_case
137
138
    def make_one_file_inventory(self, repo, revision, parents,
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
139
                                inv_revision=None, root_revision=None,
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
140
                                file_contents=None, make_file_version=True):
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
141
        return self.test_case.make_one_file_inventory(
142
            repo, revision, parents, inv_revision=inv_revision,
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
143
            root_revision=root_revision, file_contents=file_contents,
144
            make_file_version=make_file_version)
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
145
146
    def add_revision(self, repo, revision_id, inv, parent_ids):
147
        return self.test_case.add_revision(repo, revision_id, inv, parent_ids)
148
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
149
    def corrected_fulltexts(self):
150
        return []
151
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
152
    def repository_text_key_index(self):
153
        result = {}
154
        if self.versioned_root:
155
            result.update(self.versioned_repository_text_keys())
156
        result.update(self.repository_text_keys())
157
        return result
158
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
159
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
160
class UndamagedRepositoryScenario(BrokenRepoScenario):
161
    """A scenario where the repository has no damage.
162
163
    It has a single revision, 'rev1a', with a single file.
164
    """
165
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
166
    def all_versions_after_reconcile(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
167
        return ('rev1a', )
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
168
169
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
170
        return (((), 'rev1a'), )
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
171
172
    def corrected_parents(self):
173
        # Same as the populated parents, because there was nothing wrong.
174
        return self.populated_parents()
175
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
176
    def check_regexes(self, repo):
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
177
        return ["0 unreferenced text versions"]
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
178
179
    def populate_repository(self, repo):
180
        # make rev1a: A well-formed revision, containing 'a-file'
181
        inv = self.make_one_file_inventory(
182
            repo, 'rev1a', [], root_revision='rev1a')
183
        self.add_revision(repo, 'rev1a', inv, [])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
184
        self.versioned_root = repo.supports_rich_root()
185
186
    def repository_text_key_references(self):
187
        result = {}
188
        if self.versioned_root:
189
            result.update({('TREE_ROOT', 'rev1a'): True})
190
        result.update({('a-file-id', 'rev1a'): True})
191
        return result
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
192
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
193
    def repository_text_keys(self):
194
        return {('a-file-id', 'rev1a'):[NULL_REVISION]}
195
196
    def versioned_repository_text_keys(self):
197
        return {('TREE_ROOT', 'rev1a'):[NULL_REVISION]}
198
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
199
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
200
class FileParentIsNotInRevisionAncestryScenario(BrokenRepoScenario):
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
201
    """A scenario where a revision 'rev2' has 'a-file' with a
202
    parent 'rev1b' that is not in the revision ancestry.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
203
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
204
    Reconcile should remove 'rev1b' from the parents list of 'a-file' in
205
    'rev2', preserving 'rev1a' as a parent.
206
    """
207
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
208
    def all_versions_after_reconcile(self):
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
209
        return ('rev1a', 'rev2')
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
210
211
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
212
        return (
213
            ((), 'rev1a'),
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
214
            ((), 'rev1b'), # Will be gc'd
215
            (('rev1a', 'rev1b'), 'rev2')) # Will have parents trimmed
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
216
217
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
218
        return (
219
            ((), 'rev1a'),
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
220
            (None, 'rev1b'),
2592.3.214 by Robert Collins
Merge bzr.dev.
221
            (('rev1a',), 'rev2'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
222
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
223
    def check_regexes(self, repo):
2592.3.214 by Robert Collins
Merge bzr.dev.
224
        return [r"\* a-file-id version rev2 has parents \('rev1a', 'rev1b'\) "
225
                r"but should have \('rev1a',\)",
3036.1.4 by Robert Collins
Fix failing test due to correct check code.
226
                "1 unreferenced text versions",
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
227
                ]
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
228
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
229
    def populate_repository(self, repo):
230
        # make rev1a: A well-formed revision, containing 'a-file'
231
        inv = self.make_one_file_inventory(
232
            repo, 'rev1a', [], root_revision='rev1a')
233
        self.add_revision(repo, 'rev1a', inv, [])
234
235
        # make rev1b, which has no Revision, but has an Inventory, and
236
        # a-file
237
        inv = self.make_one_file_inventory(
238
            repo, 'rev1b', [], root_revision='rev1b')
239
        repo.add_inventory('rev1b', inv, [])
240
241
        # make rev2, with a-file.
242
        # a-file has 'rev1b' as an ancestor, even though this is not
243
        # mentioned by 'rev1a', making it an unreferenced ancestor
244
        inv = self.make_one_file_inventory(
245
            repo, 'rev2', ['rev1a', 'rev1b'])
246
        self.add_revision(repo, 'rev2', inv, ['rev1a'])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
247
        self.versioned_root = repo.supports_rich_root()
248
249
    def repository_text_key_references(self):
250
        result = {}
251
        if self.versioned_root:
252
            result.update({('TREE_ROOT', 'rev1a'): True,
253
                           ('TREE_ROOT', 'rev2'): True})
254
        result.update({('a-file-id', 'rev1a'): True,
255
                       ('a-file-id', 'rev2'): True})
256
        return result
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
257
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
258
    def repository_text_keys(self):
259
        return {('a-file-id', 'rev1a'):[NULL_REVISION],
260
                ('a-file-id', 'rev2'):[('a-file-id', 'rev1a')]}
261
262
    def versioned_repository_text_keys(self):
263
        return {('TREE_ROOT', 'rev1a'):[NULL_REVISION],
264
                ('TREE_ROOT', 'rev2'):[('TREE_ROOT', 'rev1a')]}
265
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
266
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
267
class FileParentHasInaccessibleInventoryScenario(BrokenRepoScenario):
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
268
    """A scenario where a revision 'rev3' containing 'a-file' modified in
269
    'rev3', and with a parent which is in the revision ancestory, but whose
270
    inventory cannot be accessed at all.
271
272
    Reconcile should remove the file version parent whose inventory is
273
    inaccessbile (i.e. remove 'rev1c' from the parents of a-file's rev3).
274
    """
275
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
276
    def all_versions_after_reconcile(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
277
        return ('rev2', 'rev3')
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
278
279
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
280
        return (
281
            ((), 'rev2'),
282
            (('rev1c',), 'rev3'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
283
284
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
285
        return (
286
            ((), 'rev2'),
287
            ((), 'rev3'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
288
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
289
    def check_regexes(self, repo):
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
290
        return [r"\* a-file-id version rev3 has parents "
2592.3.214 by Robert Collins
Merge bzr.dev.
291
                r"\('rev1c',\) but should have \(\)",
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
292
                ]
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
293
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
294
    def populate_repository(self, repo):
295
        # make rev2, with a-file
296
        # a-file is sane
297
        inv = self.make_one_file_inventory(repo, 'rev2', [])
298
        self.add_revision(repo, 'rev2', inv, [])
299
300
        # make ghost revision rev1c, with a version of a-file present so
301
        # that we generate a knit delta against this version.  In real life
302
        # the ghost might never have been present or rev3 might have been
303
        # generated against a revision that was present at the time.  So
304
        # currently we have the full history of a-file present even though
305
        # the inventory and revision objects are not.
306
        self.make_one_file_inventory(repo, 'rev1c', [])
307
308
        # make rev3 with a-file
309
        # a-file refers to 'rev1c', which is a ghost in this repository, so
310
        # a-file cannot have rev1c as its ancestor.
311
        inv = self.make_one_file_inventory(repo, 'rev3', ['rev1c'])
312
        self.add_revision(repo, 'rev3', inv, ['rev1c', 'rev1a'])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
313
        self.versioned_root = repo.supports_rich_root()
314
315
    def repository_text_key_references(self):
316
        result = {}
317
        if self.versioned_root:
318
            result.update({('TREE_ROOT', 'rev2'): True,
319
                           ('TREE_ROOT', 'rev3'): True})
320
        result.update({('a-file-id', 'rev2'): True,
321
                       ('a-file-id', 'rev3'): True})
322
        return result
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
323
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
324
    def repository_text_keys(self):
325
        return {('a-file-id', 'rev2'):[NULL_REVISION],
326
                ('a-file-id', 'rev3'):[NULL_REVISION]}
327
328
    def versioned_repository_text_keys(self):
329
        return {('TREE_ROOT', 'rev2'):[NULL_REVISION],
330
                ('TREE_ROOT', 'rev3'):[NULL_REVISION]}
331
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
332
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
333
class FileParentsNotReferencedByAnyInventoryScenario(BrokenRepoScenario):
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
334
    """A scenario where a repository with file 'a-file' which has extra
335
    per-file versions that are not referenced by any inventory (even though
336
    they have the same ID as actual revisions).  The inventory of 'rev2'
337
    references 'rev1a' of 'a-file', but there is a 'rev2' of 'some-file' stored
338
    and erroneously referenced by later per-file versions (revisions 'rev4' and
339
    'rev5').
340
341
    Reconcile should remove the file parents that are not referenced by any
342
    inventory.
343
    """
344
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
345
    def all_versions_after_reconcile(self):
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
346
        return ('rev1a', 'rev2c', 'rev4', 'rev5')
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
347
348
    def populated_parents(self):
349
        return [
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
350
            (('rev1a',), 'rev2'),
351
            (('rev1a',), 'rev2b'),
2592.3.214 by Robert Collins
Merge bzr.dev.
352
            (('rev2',), 'rev3'),
353
            (('rev2',), 'rev4'),
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
354
            (('rev2', 'rev2c'), 'rev5')]
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
355
356
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
357
        return (
2927.2.8 by Andrew Bennetts
Remove totally unreferenced file versions. All reconcile tests passing.
358
            # rev2 and rev2b have been removed.
359
            (None, 'rev2'),
360
            (None, 'rev2b'),
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
361
            # rev3's accessible parent inventories all have rev1a as the last
362
            # modifier.
2592.3.214 by Robert Collins
Merge bzr.dev.
363
            (('rev1a',), 'rev3'),
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
364
            # rev1a features in both rev4's parents but should only appear once
365
            # in the result
2592.3.214 by Robert Collins
Merge bzr.dev.
366
            (('rev1a',), 'rev4'),
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
367
            # rev2c is the head of rev1a and rev2c, the inventory provided
368
            # per-file last-modified revisions.
2592.3.214 by Robert Collins
Merge bzr.dev.
369
            (('rev2c',), 'rev5'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
370
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
371
    def check_regexes(self, repo):
372
        if repo.supports_rich_root():
373
            # TREE_ROOT will be wrong; but we're not testing it. so just adjust
374
            # the expected count of errors.
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
375
            count = 9
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
376
        else:
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
377
            count = 3
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
378
        return [
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
379
            # will be gc'd
380
            r"unreferenced version: {rev2} in a-file-id",
381
            r"unreferenced version: {rev2b} in a-file-id",
382
            # will be corrected
2592.3.214 by Robert Collins
Merge bzr.dev.
383
            r"a-file-id version rev3 has parents \('rev2',\) "
384
            r"but should have \('rev1a',\)",
385
            r"a-file-id version rev5 has parents \('rev2', 'rev2c'\) "
386
            r"but should have \('rev2c',\)",
387
            r"a-file-id version rev4 has parents \('rev2',\) "
388
            r"but should have \('rev1a',\)",
3350.6.4 by Robert Collins
First cut at pluralised VersionedFiles. Some rather massive API incompatabilities, primarily because of the difficulty of coherence among competing stores.
389
            "%d inconsistent parents" % count,
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
390
            ]
391
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
392
    def populate_repository(self, repo):
393
        # make rev1a: A well-formed revision, containing 'a-file'
394
        inv = self.make_one_file_inventory(
395
            repo, 'rev1a', [], root_revision='rev1a')
396
        self.add_revision(repo, 'rev1a', inv, [])
397
398
        # make rev2, with a-file.
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
399
        # a-file is unmodified from rev1a, and an unreferenced rev2 file
400
        # version is present in the repository.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
401
        self.make_one_file_inventory(
402
            repo, 'rev2', ['rev1a'], inv_revision='rev1a')
403
        self.add_revision(repo, 'rev2', inv, ['rev1a'])
404
405
        # make rev3 with a-file
406
        # a-file has 'rev2' as its ancestor, but the revision in 'rev2' was
407
        # rev1a so this is inconsistent with rev2's inventory - it should
408
        # be rev1a, and at the revision level 1c is not present - it is a
409
        # ghost, so only the details from rev1a are available for
410
        # determining whether a delta is acceptable, or a full is needed,
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
411
        # and what the correct parents are.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
412
        inv = self.make_one_file_inventory(repo, 'rev3', ['rev2'])
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
413
        self.add_revision(repo, 'rev3', inv, ['rev1c', 'rev1a'])
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
414
415
        # In rev2b, the true last-modifying-revision of a-file is rev1a,
416
        # inherited from rev2, but there is a version rev2b of the file, which
417
        # reconcile could remove, leaving no rev2b.  Most importantly,
418
        # revisions descending from rev2b should not have per-file parents of
419
        # a-file-rev2b.
420
        # ??? This is to test deduplication in fixing rev4
421
        inv = self.make_one_file_inventory(
422
            repo, 'rev2b', ['rev1a'], inv_revision='rev1a')
423
        self.add_revision(repo, 'rev2b', inv, ['rev1a'])
424
425
        # rev4 is for testing that when the last modified of a file in
426
        # multiple parent revisions is the same, that it only appears once
427
        # in the generated per file parents list: rev2 and rev2b both
428
        # descend from 1a and do not change the file a-file, so there should
429
        # be no version of a-file 'rev2' or 'rev2b', but rev4 does change
430
        # a-file, and is a merge of rev2 and rev2b, so it should end up with
431
        # a parent of just rev1a - the starting file parents list is simply
432
        # completely wrong.
433
        inv = self.make_one_file_inventory(repo, 'rev4', ['rev2'])
434
        self.add_revision(repo, 'rev4', inv, ['rev2', 'rev2b'])
435
436
        # rev2c changes a-file from rev1a, so the version it of a-file it
437
        # introduces is a head revision when rev5 is checked.
438
        inv = self.make_one_file_inventory(repo, 'rev2c', ['rev1a'])
439
        self.add_revision(repo, 'rev2c', inv, ['rev1a'])
440
441
        # rev5 descends from rev2 and rev2c; as rev2 does not alter a-file,
442
        # but rev2c does, this should use rev2c as the parent for the per
443
        # file history, even though more than one per-file parent is
444
        # available, because we use the heads of the revision parents for
445
        # the inventory modification revisions of the file to determine the
446
        # parents for the per file graph.
447
        inv = self.make_one_file_inventory(repo, 'rev5', ['rev2', 'rev2c'])
448
        self.add_revision(repo, 'rev5', inv, ['rev2', 'rev2c'])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
449
        self.versioned_root = repo.supports_rich_root()
450
451
    def repository_text_key_references(self):
452
        result = {}
453
        if self.versioned_root:
454
            result.update({('TREE_ROOT', 'rev1a'): True,
455
                           ('TREE_ROOT', 'rev2'): True,
456
                           ('TREE_ROOT', 'rev2b'): True,
457
                           ('TREE_ROOT', 'rev2c'): True,
458
                           ('TREE_ROOT', 'rev3'): True,
459
                           ('TREE_ROOT', 'rev4'): True,
460
                           ('TREE_ROOT', 'rev5'): True})
461
        result.update({('a-file-id', 'rev1a'): True,
462
                       ('a-file-id', 'rev2c'): True,
463
                       ('a-file-id', 'rev3'): True,
464
                       ('a-file-id', 'rev4'): True,
465
                       ('a-file-id', 'rev5'): True})
466
        return result
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
467
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
468
    def repository_text_keys(self):
469
        return {('a-file-id', 'rev1a'): [NULL_REVISION],
470
                 ('a-file-id', 'rev2c'): [('a-file-id', 'rev1a')],
471
                 ('a-file-id', 'rev3'): [('a-file-id', 'rev1a')],
472
                 ('a-file-id', 'rev4'): [('a-file-id', 'rev1a')],
473
                 ('a-file-id', 'rev5'): [('a-file-id', 'rev2c')]}
474
475
    def versioned_repository_text_keys(self):
476
        return {('TREE_ROOT', 'rev1a'): [NULL_REVISION],
477
                ('TREE_ROOT', 'rev2'): [('TREE_ROOT', 'rev1a')],
478
                ('TREE_ROOT', 'rev2b'): [('TREE_ROOT', 'rev1a')],
479
                ('TREE_ROOT', 'rev2c'): [('TREE_ROOT', 'rev1a')],
480
                ('TREE_ROOT', 'rev3'): [('TREE_ROOT', 'rev1a')],
481
                ('TREE_ROOT', 'rev4'):
482
                    [('TREE_ROOT', 'rev2'), ('TREE_ROOT', 'rev2b')],
483
                ('TREE_ROOT', 'rev5'):
484
                    [('TREE_ROOT', 'rev2'), ('TREE_ROOT', 'rev2c')]}
485
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
486
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
487
class UnreferencedFileParentsFromNoOpMergeScenario(BrokenRepoScenario):
488
    """
489
    rev1a and rev1b with identical contents
490
    rev2 revision has parents of [rev1a, rev1b]
491
    There is a a-file:rev2 file version, not referenced by the inventory.
492
    """
493
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
494
    def all_versions_after_reconcile(self):
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
495
        return ('rev1a', 'rev1b', 'rev2', 'rev4')
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
496
497
    def populated_parents(self):
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
498
        return (
499
            ((), 'rev1a'),
500
            ((), 'rev1b'),
501
            (('rev1a', 'rev1b'), 'rev2'),
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
502
            (None, 'rev3'),
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
503
            (('rev2',), 'rev4'),
504
            )
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
505
506
    def corrected_parents(self):
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
507
        return (
508
            ((), 'rev1a'),
509
            ((), 'rev1b'),
510
            ((), 'rev2'),
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
511
            (None, 'rev3'),
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
512
            (('rev2',), 'rev4'),
513
            )
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
514
515
    def corrected_fulltexts(self):
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
516
        return ['rev2']
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
517
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
518
    def check_regexes(self, repo):
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
519
        return []
520
521
    def populate_repository(self, repo):
522
        # make rev1a: A well-formed revision, containing 'a-file'
523
        inv1a = self.make_one_file_inventory(
524
            repo, 'rev1a', [], root_revision='rev1a')
525
        self.add_revision(repo, 'rev1a', inv1a, [])
526
527
        # make rev1b: A well-formed revision, containing 'a-file'
528
        # rev1b of a-file has the exact same contents as rev1a.
529
        file_contents = repo.revision_tree('rev1a').get_file_text('a-file-id')
530
        inv = self.make_one_file_inventory(
531
            repo, 'rev1b', [], root_revision='rev1b',
532
            file_contents=file_contents)
533
        self.add_revision(repo, 'rev1b', inv, [])
534
535
        # make rev2, a merge of rev1a and rev1b, with a-file.
536
        # a-file is unmodified from rev1a and rev1b, but a new version is
537
        # wrongly present anyway.
538
        inv = self.make_one_file_inventory(
539
            repo, 'rev2', ['rev1a', 'rev1b'], inv_revision='rev1a',
540
            file_contents=file_contents)
541
        self.add_revision(repo, 'rev2', inv, ['rev1a', 'rev1b'])
542
543
        # rev3: a-file unchanged from rev2, but wrongly referencing rev2 of the
544
        # file in its inventory.
545
        inv = self.make_one_file_inventory(
546
            repo, 'rev3', ['rev2'], inv_revision='rev2',
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
547
            file_contents=file_contents, make_file_version=False)
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
548
        self.add_revision(repo, 'rev3', inv, ['rev2'])
549
550
        # rev4: a modification of a-file on top of rev3.
2927.2.4 by Andrew Bennetts
Don't create a 'rev3' file version in the test.
551
        inv = self.make_one_file_inventory(repo, 'rev4', ['rev2'])
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
552
        self.add_revision(repo, 'rev4', inv, ['rev3'])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
553
        self.versioned_root = repo.supports_rich_root()
554
555
    def repository_text_key_references(self):
556
        result = {}
557
        if self.versioned_root:
558
            result.update({('TREE_ROOT', 'rev1a'): True,
559
                           ('TREE_ROOT', 'rev1b'): True,
560
                           ('TREE_ROOT', 'rev2'): True,
561
                           ('TREE_ROOT', 'rev3'): True,
562
                           ('TREE_ROOT', 'rev4'): True})
563
        result.update({('a-file-id', 'rev1a'): True,
564
                       ('a-file-id', 'rev1b'): True,
565
                       ('a-file-id', 'rev2'): False,
566
                       ('a-file-id', 'rev4'): True})
567
        return result
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
568
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
569
    def repository_text_keys(self):
570
        return {('a-file-id', 'rev1a'): [NULL_REVISION],
571
                ('a-file-id', 'rev1b'): [NULL_REVISION],
572
                ('a-file-id', 'rev2'): [NULL_REVISION],
573
                ('a-file-id', 'rev4'): [('a-file-id', 'rev2')]}
574
575
    def versioned_repository_text_keys(self):
576
        return {('TREE_ROOT', 'rev1a'): [NULL_REVISION],
577
                ('TREE_ROOT', 'rev1b'): [NULL_REVISION],
578
                ('TREE_ROOT', 'rev2'):
579
                    [('TREE_ROOT', 'rev1a'), ('TREE_ROOT', 'rev1b')],
580
                ('TREE_ROOT', 'rev3'): [('TREE_ROOT', 'rev2')],
581
                ('TREE_ROOT', 'rev4'): [('TREE_ROOT', 'rev3')]}
582
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
583
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
584
class TooManyParentsScenario(BrokenRepoScenario):
2745.6.39 by Andrew Bennetts
Use scenario in test_check too, and make check actually report inconsistent parents to the end user.
585
    """A scenario where 'broken-revision' of 'a-file' claims to have parents
586
    ['good-parent', 'bad-parent'].  However 'bad-parent' is in the ancestry of
587
    'good-parent', so the correct parent list for that file version are is just
588
    ['good-parent'].
589
    """
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
590
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
591
    def all_versions_after_reconcile(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
592
        return ('bad-parent', 'good-parent', 'broken-revision')
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
593
594
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
595
        return (
596
            ((), 'bad-parent'),
597
            (('bad-parent',), 'good-parent'),
598
            (('good-parent', 'bad-parent'), 'broken-revision'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
599
600
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
601
        return (
602
            ((), 'bad-parent'),
603
            (('bad-parent',), 'good-parent'),
604
            (('good-parent',), 'broken-revision'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
605
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
606
    def check_regexes(self, repo):
607
        if repo.supports_rich_root():
608
            # TREE_ROOT will be wrong; but we're not testing it. so just adjust
609
            # the expected count of errors.
610
            count = 3
611
        else:
612
            count = 1
2592.3.214 by Robert Collins
Merge bzr.dev.
613
        return (
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
614
            '     %d inconsistent parents' % count,
2745.6.39 by Andrew Bennetts
Use scenario in test_check too, and make check actually report inconsistent parents to the end user.
615
            (r"      \* a-file-id version broken-revision has parents "
2592.3.214 by Robert Collins
Merge bzr.dev.
616
             r"\('good-parent', 'bad-parent'\) but "
617
             r"should have \('good-parent',\)"))
2745.6.39 by Andrew Bennetts
Use scenario in test_check too, and make check actually report inconsistent parents to the end user.
618
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
619
    def populate_repository(self, repo):
620
        inv = self.make_one_file_inventory(
2592.3.214 by Robert Collins
Merge bzr.dev.
621
            repo, 'bad-parent', (), root_revision='bad-parent')
622
        self.add_revision(repo, 'bad-parent', inv, ())
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
623
2592.3.214 by Robert Collins
Merge bzr.dev.
624
        inv = self.make_one_file_inventory(
625
            repo, 'good-parent', ('bad-parent',))
626
        self.add_revision(repo, 'good-parent', inv, ('bad-parent',))
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
627
2592.3.214 by Robert Collins
Merge bzr.dev.
628
        inv = self.make_one_file_inventory(
629
            repo, 'broken-revision', ('good-parent', 'bad-parent'))
630
        self.add_revision(repo, 'broken-revision', inv, ('good-parent',))
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
631
        self.versioned_root = repo.supports_rich_root()
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
632
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
633
    def repository_text_key_references(self):
634
        result = {}
635
        if self.versioned_root:
636
            result.update({('TREE_ROOT', 'bad-parent'): True,
637
                           ('TREE_ROOT', 'broken-revision'): True,
638
                           ('TREE_ROOT', 'good-parent'): True})
639
        result.update({('a-file-id', 'bad-parent'): True,
640
                       ('a-file-id', 'broken-revision'): True,
641
                       ('a-file-id', 'good-parent'): True})
642
        return result
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
643
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
644
    def repository_text_keys(self):
645
        return {('a-file-id', 'bad-parent'): [NULL_REVISION],
646
                ('a-file-id', 'broken-revision'):
647
                    [('a-file-id', 'good-parent')],
648
                ('a-file-id', 'good-parent'): [('a-file-id', 'bad-parent')]}
649
650
    def versioned_repository_text_keys(self):
651
        return {('TREE_ROOT', 'bad-parent'): [NULL_REVISION],
652
                ('TREE_ROOT', 'broken-revision'):
653
                    [('TREE_ROOT', 'good-parent')],
654
                ('TREE_ROOT', 'good-parent'): [('TREE_ROOT', 'bad-parent')]}
655
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
656
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
657
class ClaimedFileParentDidNotModifyFileScenario(BrokenRepoScenario):
658
    """A scenario where the file parent is the same as the revision parent, but
659
    should not be because that revision did not modify the file.
660
661
    Specifically, the parent revision of 'current' is
662
    'modified-something-else', which does not modify 'a-file', but the
663
    'current' version of 'a-file' erroneously claims that
664
    'modified-something-else' is the parent file version.
665
    """
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
666
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
667
    def all_versions_after_reconcile(self):
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
668
        return ('basis', 'current')
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
669
670
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
671
        return (
672
            ((), 'basis'),
673
            (('basis',), 'modified-something-else'),
674
            (('modified-something-else',), 'current'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
675
676
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
677
        return (
678
            ((), 'basis'),
2927.2.8 by Andrew Bennetts
Remove totally unreferenced file versions. All reconcile tests passing.
679
            (None, 'modified-something-else'),
2592.3.214 by Robert Collins
Merge bzr.dev.
680
            (('basis',), 'current'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
681
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
682
    def check_regexes(self, repo):
683
        if repo.supports_rich_root():
684
            # TREE_ROOT will be wrong; but we're not testing it. so just adjust
685
            # the expected count of errors.
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
686
            count = 3
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
687
        else:
2988.1.8 by Robert Collins
Change check and reconcile to use the new _generate_text_key_index rather
688
            count = 1
2592.3.214 by Robert Collins
Merge bzr.dev.
689
        return (
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
690
            "%d inconsistent parents" % count,
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
691
            r"\* a-file-id version current has parents "
2927.2.11 by Andrew Bennetts
Merge from bzr.dev.
692
            r"\('modified-something-else',\) but should have \('basis',\)",
693
            )
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
694
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
695
    def populate_repository(self, repo):
2592.3.214 by Robert Collins
Merge bzr.dev.
696
        inv = self.make_one_file_inventory(repo, 'basis', ())
697
        self.add_revision(repo, 'basis', inv, ())
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
698
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
699
        # 'modified-something-else' is a correctly recorded revision, but it
700
        # does not modify the file we are looking at, so the inventory for that
701
        # file in this revision points to 'basis'.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
702
        inv = self.make_one_file_inventory(
2592.3.214 by Robert Collins
Merge bzr.dev.
703
            repo, 'modified-something-else', ('basis',), inv_revision='basis')
704
        self.add_revision(repo, 'modified-something-else', inv, ('basis',))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
705
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
706
        # The 'current' revision has 'modified-something-else' as its parent,
707
        # but the 'current' version of 'a-file' should have 'basis' as its
708
        # parent.
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
709
        inv = self.make_one_file_inventory(
2592.3.214 by Robert Collins
Merge bzr.dev.
710
            repo, 'current', ('modified-something-else',))
711
        self.add_revision(repo, 'current', inv, ('modified-something-else',))
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
712
        self.versioned_root = repo.supports_rich_root()
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
713
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
714
    def repository_text_key_references(self):
715
        result = {}
716
        if self.versioned_root:
717
            result.update({('TREE_ROOT', 'basis'): True,
718
                           ('TREE_ROOT', 'current'): True,
719
                           ('TREE_ROOT', 'modified-something-else'): True})
720
        result.update({('a-file-id', 'basis'): True,
721
                       ('a-file-id', 'current'): True})
722
        return result
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
723
724
    def repository_text_keys(self):
725
        return {('a-file-id', 'basis'): [NULL_REVISION],
726
                ('a-file-id', 'current'): [('a-file-id', 'basis')]}
727
728
    def versioned_repository_text_keys(self):
729
        return {('TREE_ROOT', 'basis'): ['null:'],
730
                ('TREE_ROOT', 'current'):
731
                    [('TREE_ROOT', 'modified-something-else')],
732
                ('TREE_ROOT', 'modified-something-else'):
733
                    [('TREE_ROOT', 'basis')]}
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
734
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
735
2745.6.43 by Andrew Bennetts
Tidy imports, docstrings, comments and variable names.
736
class IncorrectlyOrderedParentsScenario(BrokenRepoScenario):
737
    """A scenario where the set parents of a version of a file are correct, but
738
    the order of those parents is incorrect.
739
740
    This defines a 'broken-revision-1-2' and a 'broken-revision-2-1' which both
741
    have their file version parents reversed compared to the revision parents,
742
    which is invalid.  (We use two revisions with opposite orderings of the
743
    same parents to make sure that accidentally relying on dictionary/set
744
    ordering cannot make the test pass; the assumption is that while dict/set
745
    iteration order is arbitrary, it is also consistent within a single test).
746
    """
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
747
2927.2.14 by Andrew Bennetts
Tweaks suggested by review.
748
    def all_versions_after_reconcile(self):
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
749
        return ['parent-1', 'parent-2', 'broken-revision-1-2',
750
                'broken-revision-2-1']
751
752
    def populated_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
753
        return (
754
            ((), 'parent-1'),
755
            ((), 'parent-2'),
756
            (('parent-2', 'parent-1'), 'broken-revision-1-2'),
757
            (('parent-1', 'parent-2'), 'broken-revision-2-1'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
758
759
    def corrected_parents(self):
2592.3.214 by Robert Collins
Merge bzr.dev.
760
        return (
761
            ((), 'parent-1'),
762
            ((), 'parent-2'),
763
            (('parent-1', 'parent-2'), 'broken-revision-1-2'),
764
            (('parent-2', 'parent-1'), 'broken-revision-2-1'))
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
765
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
766
    def check_regexes(self, repo):
767
        if repo.supports_rich_root():
768
            # TREE_ROOT will be wrong; but we're not testing it. so just adjust
769
            # the expected count of errors.
770
            count = 4
771
        else:
772
            count = 2
2592.3.214 by Robert Collins
Merge bzr.dev.
773
        return (
2951.1.6 by Robert Collins
All check/reconcile tests passing now.
774
            "%d inconsistent parents" % count,
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
775
            r"\* a-file-id version broken-revision-1-2 has parents "
2592.3.214 by Robert Collins
Merge bzr.dev.
776
            r"\('parent-2', 'parent-1'\) but should have "
777
            r"\('parent-1', 'parent-2'\)",
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
778
            r"\* a-file-id version broken-revision-2-1 has parents "
2592.3.214 by Robert Collins
Merge bzr.dev.
779
            r"\('parent-1', 'parent-2'\) but should have "
780
            r"\('parent-2', 'parent-1'\)")
2745.6.41 by Andrew Bennetts
Test repo.check against all_scenarios.
781
2745.6.38 by Andrew Bennetts
Create explicit scenario objects for test_reconcile.
782
    def populate_repository(self, repo):
783
        inv = self.make_one_file_inventory(repo, 'parent-1', [])
784
        self.add_revision(repo, 'parent-1', inv, [])
785
786
        inv = self.make_one_file_inventory(repo, 'parent-2', [])
787
        self.add_revision(repo, 'parent-2', inv, [])
788
789
        inv = self.make_one_file_inventory(
790
            repo, 'broken-revision-1-2', ['parent-2', 'parent-1'])
791
        self.add_revision(
792
            repo, 'broken-revision-1-2', inv, ['parent-1', 'parent-2'])
793
794
        inv = self.make_one_file_inventory(
795
            repo, 'broken-revision-2-1', ['parent-1', 'parent-2'])
796
        self.add_revision(
797
            repo, 'broken-revision-2-1', inv, ['parent-2', 'parent-1'])
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
798
        self.versioned_root = repo.supports_rich_root()
2745.6.32 by Andrew Bennetts
Some testing notes, test reorganisation, XXX comments and some failing tests.
799
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
800
    def repository_text_key_references(self):
801
        result = {}
802
        if self.versioned_root:
803
            result.update({('TREE_ROOT', 'broken-revision-1-2'): True,
804
                           ('TREE_ROOT', 'broken-revision-2-1'): True,
805
                           ('TREE_ROOT', 'parent-1'): True,
806
                           ('TREE_ROOT', 'parent-2'): True})
807
        result.update({('a-file-id', 'broken-revision-1-2'): True,
808
                       ('a-file-id', 'broken-revision-2-1'): True,
809
                       ('a-file-id', 'parent-1'): True,
810
                       ('a-file-id', 'parent-2'): True})
811
        return result
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
812
813
    def repository_text_keys(self):
814
        return {('a-file-id', 'broken-revision-1-2'):
815
                    [('a-file-id', 'parent-1'), ('a-file-id', 'parent-2')],
816
                ('a-file-id', 'broken-revision-2-1'):
817
                    [('a-file-id', 'parent-2'), ('a-file-id', 'parent-1')],
818
                ('a-file-id', 'parent-1'): [NULL_REVISION],
819
                ('a-file-id', 'parent-2'): [NULL_REVISION]}
820
821
    def versioned_repository_text_keys(self):
822
        return {('TREE_ROOT', 'broken-revision-1-2'):
823
                    [('TREE_ROOT', 'parent-1'), ('TREE_ROOT', 'parent-2')],
824
                ('TREE_ROOT', 'broken-revision-2-1'):
825
                    [('TREE_ROOT', 'parent-2'), ('TREE_ROOT', 'parent-1')],
826
                ('TREE_ROOT', 'parent-1'): [NULL_REVISION],
827
                ('TREE_ROOT', 'parent-2'): [NULL_REVISION]}
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
828
2485.7.1 by Robert Collins
Relocate TestCaseWithRepository to be more central.
829
2745.6.58 by Andrew Bennetts
Slightly neater test parameterisation in repository_implementations; extract a 'multiply_scenarios' function.
830
all_broken_scenario_classes = [
2745.6.54 by Andrew Bennetts
Tidy test parameterisation in repository_implementations.
831
    UndamagedRepositoryScenario,
832
    FileParentIsNotInRevisionAncestryScenario,
833
    FileParentHasInaccessibleInventoryScenario,
834
    FileParentsNotReferencedByAnyInventoryScenario,
835
    TooManyParentsScenario,
836
    ClaimedFileParentDidNotModifyFileScenario,
837
    IncorrectlyOrderedParentsScenario,
2927.2.3 by Andrew Bennetts
Add fulltexts to avoid bug 155730.
838
    UnreferencedFileParentsFromNoOpMergeScenario,
2745.6.54 by Andrew Bennetts
Tidy test parameterisation in repository_implementations.
839
    ]
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
840
2745.6.42 by Andrew Bennetts
Use TestScenarioApplier to more cleanly parameterise check and reconcile tests.
841
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
842
def load_tests(standard_tests, module, loader):
3689.1.1 by John Arbash Meinel
Rename repository_implementations tests into per_repository tests
843
    prefix = 'bzrlib.tests.per_repository.'
2745.6.58 by Andrew Bennetts
Slightly neater test parameterisation in repository_implementations; extract a 'multiply_scenarios' function.
844
    test_repository_modules = [
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
845
        'test_add_fallback_repository',
3879.2.2 by John Arbash Meinel
Rename add_inventory_delta to add_inventory_by_delta.
846
        'test_add_inventory_by_delta',
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
847
        'test_break_lock',
848
        'test_check',
2745.6.58 by Andrew Bennetts
Slightly neater test parameterisation in repository_implementations; extract a 'multiply_scenarios' function.
849
        # test_check_reconcile is intentionally omitted, see below.
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
850
        'test_commit_builder',
851
        'test_fetch',
852
        'test_fileid_involved',
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
853
        'test_find_text_key_references',
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
854
        'test__generate_text_key_index',
3373.5.2 by John Arbash Meinel
Add repository_implementation tests for get_parent_map
855
        'test_get_parent_map',
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
856
        'test_has_same_location',
3172.3.1 by Robert Collins
Repository has a new method ``has_revisions`` which signals the presence
857
        'test_has_revisions',
2904.1.2 by Robert Collins
Merge bzr.dev
858
        'test_is_write_locked',
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
859
        'test_iter_reverse_revision_history',
4543.2.3 by John Arbash Meinel
Change the name to test_merge_directive
860
        'test_merge_directive',
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
861
        'test_pack',
862
        'test_reconcile',
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
863
        'test_refresh_data',
2745.6.57 by Andrew Bennetts
Some improvements suggested by Martin's review.
864
        'test_repository',
865
        'test_revision',
866
        'test_statistics',
867
        'test_write_group',
2745.6.54 by Andrew Bennetts
Tidy test parameterisation in repository_implementations.
868
        ]
3689.1.1 by John Arbash Meinel
Rename repository_implementations tests into per_repository tests
869
    # Parameterize per_repository test modules by format.
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
870
    submod_tests = loader.loadTestsFromModuleNames(
871
        [prefix + module_name for module_name in test_repository_modules])
3221.10.1 by Robert Collins
Add add_inventory external reference interface tests and tweak broken test support function adapt_tests.
872
    format_scenarios = all_repository_format_scenarios()
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
873
    multiply_tests(submod_tests, format_scenarios, standard_tests)
2745.6.58 by Andrew Bennetts
Slightly neater test parameterisation in repository_implementations; extract a 'multiply_scenarios' function.
874
3128.1.3 by Vincent Ladeuil
Since we are there s/parameteris.*/parameteriz&/.
875
    # test_check_reconcile needs to be parameterized by format *and* by broken
2745.6.58 by Andrew Bennetts
Slightly neater test parameterisation in repository_implementations; extract a 'multiply_scenarios' function.
876
    # repository scenario.
877
    broken_scenarios = [(s.__name__, {'scenario_class': s})
878
                        for s in all_broken_scenario_classes]
879
    broken_scenarios_for_all_formats = multiply_scenarios(
880
        format_scenarios, broken_scenarios)
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
881
    return multiply_tests(
882
        loader.loadTestsFromModuleNames([prefix + 'test_check_reconcile']),
883
        broken_scenarios_for_all_formats, standard_tests)