42
42
from bzrlib.bundle import serializer
43
43
from bzrlib.recordcounter import RecordCounter
44
from bzrlib.revisiontree import InventoryRevisionTree
44
from bzrlib.revisiontree import RevisionTree
45
45
from bzrlib.store.versioned import VersionedFileStore
46
46
from bzrlib.testament import Testament
94
94
def __init__(self, repository, parents, config, timestamp=None,
95
95
timezone=None, committer=None, revprops=None,
96
revision_id=None, lossy=False):
97
97
"""Initiate a CommitBuilder.
99
99
:param repository: Repository to commit to.
103
103
:param committer: Optional committer to set for commit.
104
104
:param revprops: Optional dictionary of revision properties.
105
105
:param revision_id: Optional revision id.
106
:param lossy: Whether to discard data that can not be natively
107
represented, when pushing to a foreign VCS
109
107
self._config = config
112
109
if committer is None:
113
110
self._committer = self._config.username()
236
233
def revision_tree(self):
237
234
"""Return the tree that was just committed.
239
After calling commit() this can be called to get a
240
InventoryRevisionTree representing the newly committed tree. This is
241
preferred to calling Repository.revision_tree() because that may
242
require deserializing the inventory, while we already have a copy in
236
After calling commit() this can be called to get a RevisionTree
237
representing the newly committed tree. This is preferred to
238
calling Repository.revision_tree() because that may require
239
deserializing the inventory, while we already have a copy in
245
242
if self.new_inventory is None:
246
243
self.new_inventory = self.repository.get_inventory(
247
244
self._new_revision_id)
248
return InventoryRevisionTree(self.repository, self.new_inventory,
245
return RevisionTree(self.repository, self.new_inventory,
249
246
self._new_revision_id)
251
248
def finish_inventory(self):
1163
1160
if config is not None and config.signature_needed():
1164
1161
if inv is None:
1165
1162
inv = self.get_inventory(revision_id)
1166
tree = InventoryRevisionTree(self, inv, revision_id)
1167
testament = Testament(rev, tree)
1168
plaintext = testament.as_short_text()
1163
plaintext = Testament(rev, inv).as_short_text()
1169
1164
self.store_revision_signature(
1170
1165
gpg.GPGStrategy(config), plaintext, revision_id)
1171
1166
# check inventory present
1788
1783
def get_commit_builder(self, branch, parents, config, timestamp=None,
1789
1784
timezone=None, committer=None, revprops=None,
1790
revision_id=None, lossy=False):
1791
1786
"""Obtain a CommitBuilder for this repository.
1793
1788
:param branch: Branch to commit to.
1798
1793
:param committer: Optional committer to set for commit.
1799
1794
:param revprops: Optional dictionary of revision properties.
1800
1795
:param revision_id: Optional revision id.
1801
:param lossy: Whether to discard data that can not be natively
1802
represented, when pushing to a foreign VCS
1804
1797
if self._fallback_repositories and not self._format.supports_chks:
1805
1798
raise errors.BzrError("Cannot commit directly to a stacked branch"
1806
1799
" in pre-2a formats. See "
1807
1800
"https://bugs.launchpad.net/bzr/+bug/375013 for details.")
1808
1801
result = self._commit_builder_class(self, parents, config,
1809
timestamp, timezone, committer, revprops, revision_id,
1802
timestamp, timezone, committer, revprops, revision_id)
1811
1803
self.start_write_group()
2515
2507
# TODO: refactor this to use an existing revision object
2516
2508
# so we don't need to read it in twice.
2517
2509
if revision_id == _mod_revision.NULL_REVISION:
2518
return InventoryRevisionTree(self,
2519
Inventory(root_id=None), _mod_revision.NULL_REVISION)
2510
return RevisionTree(self, Inventory(root_id=None),
2511
_mod_revision.NULL_REVISION)
2521
2513
inv = self.get_inventory(revision_id)
2522
return InventoryRevisionTree(self, inv, revision_id)
2514
return RevisionTree(self, inv, revision_id)
2524
2516
def revision_trees(self, revision_ids):
2525
2517
"""Return Trees for revisions in this repository.
2530
2522
inventories = self.iter_inventories(revision_ids)
2531
2523
for inv in inventories:
2532
yield InventoryRevisionTree(self, inv, inv.revision_id)
2524
yield RevisionTree(self, inv, inv.revision_id)
2534
2526
def _filtered_revision_trees(self, revision_ids, file_ids):
2535
2527
"""Return Tree for a revision on this branch with only some files.
2545
2537
# Should we introduce a FilteredRevisionTree class rather
2546
2538
# than pre-filter the inventory here?
2547
2539
filtered_inv = inv.filter(file_ids)
2548
yield InventoryRevisionTree(self, filtered_inv, filtered_inv.revision_id)
2540
yield RevisionTree(self, filtered_inv, filtered_inv.revision_id)
2550
2542
@needs_read_lock
2551
2543
def get_ancestry(self, revision_id, topo_sorted=True):
2773
2765
except UnicodeDecodeError:
2774
2766
raise errors.NonAsciiRevisionId(method, self)
2776
def _find_inconsistent_revision_parents(self, revisions_iterator=None):
2777
"""Find revisions with different parent lists in the revision object
2778
and in the index graph.
2780
:param revisions_iterator: None, or an iterator of (revid,
2781
Revision-or-None). This iterator controls the revisions checked.
2782
:returns: an iterator yielding tuples of (revison-id, parents-in-index,
2783
parents-in-revision).
2785
if not self.is_locked():
2786
raise AssertionError()
2788
if revisions_iterator is None:
2789
revisions_iterator = self._iter_revisions(None)
2790
for revid, revision in revisions_iterator:
2791
if revision is None:
2793
parent_map = vf.get_parent_map([(revid,)])
2794
parents_according_to_index = tuple(parent[-1] for parent in
2795
parent_map[(revid,)])
2796
parents_according_to_revision = tuple(revision.parent_ids)
2797
if parents_according_to_index != parents_according_to_revision:
2798
yield (revid, parents_according_to_index,
2799
parents_according_to_revision)
2801
def _check_for_inconsistent_revision_parents(self):
2802
inconsistencies = list(self._find_inconsistent_revision_parents())
2804
raise errors.BzrCheckError(
2805
"Revision knit has inconsistent parents.")
2808
2769
def install_revision(repository, rev, revision_tree):
2809
2770
"""Install all revision data into a repository."""
2867
2828
for revision, tree in parent_trees.iteritems():
2868
2829
if ie.file_id not in tree:
2870
parent_id = tree.get_file_revision(ie.file_id)
2831
parent_id = tree.inventory[ie.file_id].revision
2871
2832
if parent_id in text_parents:
2873
2834
text_parents.append((ie.file_id, parent_id))
3106
3067
"""Return the short description for this format."""
3107
3068
raise NotImplementedError(self.get_format_description)
3070
# TODO: this shouldn't be in the base class, it's specific to things that
3071
# use weaves or knits -- mbp 20070207
3072
def _get_versioned_file_store(self,
3077
versionedfile_class=None,
3078
versionedfile_kwargs={},
3080
if versionedfile_class is None:
3081
versionedfile_class = self._versionedfile_class
3082
weave_transport = control_files._transport.clone(name)
3083
dir_mode = control_files._dir_mode
3084
file_mode = control_files._file_mode
3085
return VersionedFileStore(weave_transport, prefixed=prefixed,
3087
file_mode=file_mode,
3088
versionedfile_class=versionedfile_class,
3089
versionedfile_kwargs=versionedfile_kwargs,
3109
3092
def initialize(self, a_bzrdir, shared=False):
3110
3093
"""Initialize a repository of this format in a_bzrdir.