20
20
"""Versioned text file storage api."""
23
from copy import deepcopy
24
from unittest import TestSuite
27
import bzrlib.errors as errors
22
from bzrlib.lazy_import import lazy_import
23
lazy_import(globals(), """
32
from bzrlib.transport.memory import MemoryTransport
28
35
from bzrlib.inter import InterObject
29
36
from bzrlib.textmerge import TextMerge
30
from bzrlib.transport.memory import MemoryTransport
31
from bzrlib.tsort import topo_sort
33
37
from bzrlib.symbol_versioning import (deprecated_function,
54
58
self.finished = False
55
59
self._access_mode = access_mode
62
def check_not_reserved_id(version_id):
63
revision.check_not_reserved_id(version_id)
57
65
def copy_to(self, name, transport):
58
66
"""Copy this versioned file to name on transport."""
59
67
raise NotImplementedError(self.copy_to)
87
95
:param sha1: The sha1 of the full text.
88
96
:param delta: The delta instructions. See get_delta for details.
98
version_id = osutils.safe_revision_id(version_id)
99
parents = [osutils.safe_revision_id(v) for v in parents]
90
100
self._check_write_ok()
91
101
if self.has_version(version_id):
92
102
raise errors.RevisionAlreadyPresent(version_id, self)
129
139
provided back to future add_lines calls in the parent_texts
142
version_id = osutils.safe_revision_id(version_id)
143
parents = [osutils.safe_revision_id(v) for v in parents]
132
144
self._check_write_ok()
133
145
return self._add_lines(version_id, parents, lines, parent_texts)
143
155
This takes the same parameters as add_lines.
157
version_id = osutils.safe_revision_id(version_id)
158
parents = [osutils.safe_revision_id(v) for v in parents]
145
159
self._check_write_ok()
146
160
return self._add_lines_with_ghosts(version_id, parents, lines,
196
210
Must raise RevisionAlreadyPresent if the new version is
197
211
already present in file history."""
212
new_version_id = osutils.safe_revision_id(new_version_id)
213
old_version_id = osutils.safe_revision_id(old_version_id)
198
214
self._check_write_ok()
199
215
return self._clone_text(new_version_id, old_version_id, parents)
212
228
raise NotImplementedError(self.create_empty)
214
def fix_parents(self, version, new_parents):
230
def fix_parents(self, version_id, new_parents):
215
231
"""Fix the parents list for version.
217
233
This is done by appending a new version to the index
219
235
the parents list must be a superset of the current
238
version_id = osutils.safe_revision_id(version_id)
239
new_parents = [osutils.safe_revision_id(p) for p in new_parents]
222
240
self._check_write_ok()
223
return self._fix_parents(version, new_parents)
241
return self._fix_parents(version_id, new_parents)
225
def _fix_parents(self, version, new_parents):
243
def _fix_parents(self, version_id, new_parents):
226
244
"""Helper for fix_parents."""
227
245
raise NotImplementedError(self.fix_parents)
235
253
raise NotImplementedError(self.get_delta)
237
def get_deltas(self, versions):
255
def get_deltas(self, version_ids):
238
256
"""Get multiple deltas at once for constructing versions.
240
258
:return: dict(version_id:(delta_parent, sha1, noeol, delta))
242
260
version_id is the version_id created by that delta.
245
for version in versions:
246
result[version] = self.get_delta(version)
263
for version_id in version_ids:
264
result[version_id] = self.get_delta(version_id)
249
267
def get_sha1(self, version_id):
283
301
raise NotImplementedError(self.get_lines)
285
def get_ancestry(self, version_ids):
303
def get_ancestry(self, version_ids, topo_sorted=True):
286
304
"""Return a list of all ancestors of given version(s). This
287
305
will not include the null revision.
307
This list will not be topologically sorted if topo_sorted=False is
289
310
Must raise RevisionNotPresent if any of the given versions are
290
311
not present in file history."""
291
312
if isinstance(version_ids, basestring):
474
495
raise NotImplementedError(VersionedFile.plan_merge)
476
def weave_merge(self, plan, a_marker=TextMerge.A_MARKER,
497
def weave_merge(self, plan, a_marker=TextMerge.A_MARKER,
477
498
b_marker=TextMerge.B_MARKER):
478
499
return PlanWeaveMerge(plan, a_marker, b_marker).merge_lines()[0]
590
611
target = temp_source
591
612
version_ids = self._get_source_version_ids(version_ids, ignore_missing)
592
613
graph = self.source.get_graph(version_ids)
593
order = topo_sort(graph.items())
614
order = tsort.topo_sort(graph.items())
594
615
pb = ui.ui_factory.nested_progress_bar()
595
616
parent_texts = {}
661
683
new_version_ids.add(version)
662
684
return new_version_ids
665
class InterVersionedFileTestProviderAdapter(object):
666
"""A tool to generate a suite testing multiple inter versioned-file classes.
668
This is done by copying the test once for each InterVersionedFile provider
669
and injecting the transport_server, transport_readonly_server,
670
versionedfile_factory and versionedfile_factory_to classes into each copy.
671
Each copy is also given a new id() to make it easy to identify.
674
def __init__(self, transport_server, transport_readonly_server, formats):
675
self._transport_server = transport_server
676
self._transport_readonly_server = transport_readonly_server
677
self._formats = formats
679
def adapt(self, test):
681
for (interversionedfile_class,
682
versionedfile_factory,
683
versionedfile_factory_to) in self._formats:
684
new_test = deepcopy(test)
685
new_test.transport_server = self._transport_server
686
new_test.transport_readonly_server = self._transport_readonly_server
687
new_test.interversionedfile_class = interversionedfile_class
688
new_test.versionedfile_factory = versionedfile_factory
689
new_test.versionedfile_factory_to = versionedfile_factory_to
690
def make_new_test_id():
691
new_id = "%s(%s)" % (new_test.id(), interversionedfile_class.__name__)
692
return lambda: new_id
693
new_test.id = make_new_test_id()
694
result.addTest(new_test)
698
def default_test_list():
699
"""Generate the default list of interversionedfile permutations to test."""
700
from bzrlib.weave import WeaveFile
701
from bzrlib.knit import KnitVersionedFile
703
# test the fallback InterVersionedFile from annotated knits to weave
704
result.append((InterVersionedFile,
707
for optimiser in InterVersionedFile._optimisers:
708
result.append((optimiser,
709
optimiser._matching_file_from_factory,
710
optimiser._matching_file_to_factory
712
# if there are specific combinations we want to use, we can add them