14
14
# along with this program; if not, write to the Free Software
15
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17
from __future__ import absolute_import
17
19
from bzrlib.lazy_import import lazy_import
18
20
lazy_import(globals(), """
22
24
from bzrlib import (
78
80
# being committed to
79
81
updates_branch = False
81
def __init__(self, repository, parents, config, timestamp=None,
83
def __init__(self, repository, parents, config_stack, timestamp=None,
82
84
timezone=None, committer=None, revprops=None,
83
85
revision_id=None, lossy=False):
84
86
"""Initiate a CommitBuilder.
93
95
:param lossy: Whether to discard data that can not be natively
94
96
represented, when pushing to a foreign VCS
98
self._config_stack = config_stack
97
99
self._lossy = lossy
99
101
if committer is None:
100
self._committer = self._config.username()
102
self._committer = self._config_stack.get('email')
101
103
elif not isinstance(committer, unicode):
102
104
self._committer = committer.decode() # throw if non-ascii
711
713
def create_bundle(self, target, base, fileobj, format=None):
712
714
return serializer.write_bundle(self, target, base, fileobj, format)
714
def get_commit_builder(self, branch, parents, config, timestamp=None,
716
def get_commit_builder(self, branch, parents, config_stack, timestamp=None,
715
717
timezone=None, committer=None, revprops=None,
716
718
revision_id=None, lossy=False):
717
719
"""Obtain a CommitBuilder for this repository.
719
721
:param branch: Branch to commit to.
720
722
:param parents: Revision ids of the parents of the new revision.
721
:param config: Configuration to use.
723
:param config_stack: Configuration stack to use.
722
724
:param timestamp: Optional timestamp recorded for commit.
723
725
:param timezone: Optional timezone for timestamp.
724
726
:param committer: Optional committer to set for commit.
979
981
raise AssertionError('_iter_for_revno returned too much history')
980
982
return (True, partial_history[-1])
982
@symbol_versioning.deprecated_method(symbol_versioning.deprecated_in((2, 4, 0)))
983
def iter_reverse_revision_history(self, revision_id):
984
"""Iterate backwards through revision ids in the lefthand history
986
:param revision_id: The revision id to start with. All its lefthand
987
ancestors will be traversed.
989
graph = self.get_graph()
990
stop_revisions = (None, _mod_revision.NULL_REVISION)
991
return graph.iter_lefthand_ancestry(revision_id, stop_revisions)
993
984
def is_shared(self):
994
985
"""Return True if this repository is flagged as a shared repository."""
995
986
raise NotImplementedError(self.is_shared)
1033
1024
raise NotImplementedError(self.revision_trees)
1036
@symbol_versioning.deprecated_method(
1037
symbol_versioning.deprecated_in((2, 4, 0)))
1038
def get_ancestry(self, revision_id, topo_sorted=True):
1039
"""Return a list of revision-ids integrated by a revision.
1041
The first element of the list is always None, indicating the origin
1042
revision. This might change when we have history horizons, or
1043
perhaps we should have a new API.
1045
This is topologically sorted.
1047
if 'evil' in debug.debug_flags:
1048
mutter_callsite(2, "get_ancestry is linear with history.")
1049
if _mod_revision.is_null(revision_id):
1051
if not self.has_revision(revision_id):
1052
raise errors.NoSuchRevision(self, revision_id)
1053
graph = self.get_graph()
1055
search = graph._make_breadth_first_searcher([revision_id])
1058
found, ghosts = search.next_with_ghosts()
1059
except StopIteration:
1062
if _mod_revision.NULL_REVISION in keys:
1063
keys.remove(_mod_revision.NULL_REVISION)
1065
parent_map = graph.get_parent_map(keys)
1066
keys = tsort.topo_sort(parent_map)
1067
return [None] + list(keys)
1069
1026
def pack(self, hint=None, clean_obsolete_packs=False):
1070
1027
"""Compress the data within the repository.
1172
1129
@needs_read_lock
1173
1130
def verify_revision_signature(self, revision_id, gpg_strategy):
1174
1131
"""Verify the signature on a revision.
1176
1133
:param revision_id: the revision to verify
1177
1134
:gpg_strategy: the GPGStrategy object to used
1179
1136
:return: gpg.SIGNATURE_VALID or a failed SIGNATURE_ value
1181
1138
if not self.has_signature_for_revision_id(revision_id):
1188
1145
return gpg_strategy.verify(signature, plaintext)
1148
def verify_revision_signatures(self, revision_ids, gpg_strategy):
1149
"""Verify revision signatures for a number of revisions.
1151
:param revision_id: the revision to verify
1152
:gpg_strategy: the GPGStrategy object to used
1153
:return: Iterator over tuples with revision id, result and keys
1155
for revid in revision_ids:
1156
(result, key) = self.verify_revision_signature(revid, gpg_strategy)
1157
yield revid, result, key
1190
1159
def has_signature_for_revision_id(self, revision_id):
1191
1160
"""Query for a revision signature for revision_id in the repository."""
1192
1161
raise NotImplementedError(self.has_signature_for_revision_id)
1224
1193
if branch is None:
1225
conf = config.GlobalConfig()
1194
conf = config.GlobalStack()
1227
conf = branch.get_config()
1228
if conf.suppress_warning('format_deprecation'):
1196
conf = branch.get_config_stack()
1197
if 'format_deprecation' in conf.get('suppress_warnings'):
1230
1199
warning("Format %s for %s is deprecated -"
1231
1200
" please use 'bzr upgrade' to get better performance"
1291
1260
"""Returns the policy for making working trees on new branches."""
1292
1261
return not self._transport.has('no-working-trees')
1264
def update_feature_flags(self, updated_flags):
1265
"""Update the feature flags for this branch.
1267
:param updated_flags: Dictionary mapping feature names to necessities
1268
A necessity can be None to indicate the feature should be removed
1270
self._format._update_feature_flags(updated_flags)
1271
self.control_transport.put_bytes('format', self._format.as_string())
1295
1274
class RepositoryFormatRegistry(controldir.ControlComponentFormatRegistry):
1296
1275
"""Repository format registry."""
1408
1387
def __ne__(self, other):
1409
1388
return not self == other
1412
def find_format(klass, a_bzrdir):
1413
"""Return the format for the repository object in a_bzrdir.
1415
This is used by bzr native formats that have a "format" file in
1416
the repository. Other methods may be used by different types of
1420
transport = a_bzrdir.get_repository_transport(None)
1421
format_string = transport.get_bytes("format")
1422
return format_registry.get(format_string)
1423
except errors.NoSuchFile:
1424
raise errors.NoRepositoryPresent(a_bzrdir)
1426
raise errors.UnknownFormatError(format=format_string,
1430
@symbol_versioning.deprecated_method(symbol_versioning.deprecated_in((2, 4, 0)))
1431
def register_format(klass, format):
1432
format_registry.register(format)
1435
@symbol_versioning.deprecated_method(symbol_versioning.deprecated_in((2, 4, 0)))
1436
def unregister_format(klass, format):
1437
format_registry.remove(format)
1440
@symbol_versioning.deprecated_method(symbol_versioning.deprecated_in((2, 4, 0)))
1441
def get_default_format(klass):
1442
"""Return the current default format."""
1443
return format_registry.get_default()
1445
def get_format_string(self):
1446
"""Return the ASCII format string that identifies this format.
1448
Note that in pre format ?? repositories the format string is
1449
not permitted nor written to disk.
1451
raise NotImplementedError(self.get_format_string)
1453
1390
def get_format_description(self):
1454
1391
"""Return the short description for this format."""
1455
1392
raise NotImplementedError(self.get_format_description)
1537
1474
return matching
1539
1476
def __init__(self):
1540
super(MetaDirRepositoryFormat, self).__init__()
1477
RepositoryFormat.__init__(self)
1478
bzrdir.BzrFormat.__init__(self)
1542
1480
def _create_control_files(self, a_bzrdir):
1543
1481
"""Create the required files and the initial control_files object."""
1568
1506
control_files.unlock()
1570
def network_name(self):
1571
"""Metadir formats have matching disk and network format strings."""
1572
return self.get_format_string()
1509
def find_format(klass, a_bzrdir):
1510
"""Return the format for the repository object in a_bzrdir.
1512
This is used by bzr native formats that have a "format" file in
1513
the repository. Other methods may be used by different types of
1517
transport = a_bzrdir.get_repository_transport(None)
1518
format_string = transport.get_bytes("format")
1519
except errors.NoSuchFile:
1520
raise errors.NoRepositoryPresent(a_bzrdir)
1521
return klass._find_format(format_registry, 'repository', format_string)
1523
def check_support_status(self, allow_unsupported, recommend_upgrade=True,
1525
RepositoryFormat.check_support_status(self,
1526
allow_unsupported=allow_unsupported, recommend_upgrade=recommend_upgrade,
1528
bzrdir.BzrFormat.check_support_status(self, allow_unsupported=allow_unsupported,
1529
recommend_upgrade=recommend_upgrade, basedir=basedir)
1575
1532
# formats which have no format string are not discoverable or independently