74
74
######################################################################
78
class _TagStore(object):
79
def __init__(self, repository):
80
self.repository = repository
82
class _DisabledTagStore(_TagStore):
83
"""Tag storage that refuses to store anything.
85
This is used by older formats that can't store tags.
88
def _not_supported(self, *a, **k):
89
raise errors.TagsNotSupported(self.repository)
91
def supports_tags(self):
94
set_tag = _not_supported
95
get_tag_dict = _not_supported
96
_set_tag_dict = _not_supported
97
lookup_tag = _not_supported
100
class _BasicTagStore(_TagStore):
101
"""Tag storage in an unversioned repository control file.
104
def supports_tags(self):
107
def set_tag(self, tag_name, tag_target):
108
"""Add a tag definition to the repository.
110
Behaviour if the tag is already present is not defined (yet).
112
# all done with a write lock held, so this looks atomic
113
self.repository.lock_write()
115
td = self.get_tag_dict()
116
td[tag_name] = tag_target
117
self._set_tag_dict(td)
119
self.repository.unlock()
121
def lookup_tag(self, tag_name):
122
"""Return the referent string of a tag"""
123
td = self.get_tag_dict()
127
raise errors.NoSuchTag(tag_name)
129
def get_tag_dict(self):
130
self.repository.lock_read()
132
tag_content = self.repository.control_files.get_utf8('tags').read()
133
return self._deserialize_tag_dict(tag_content)
135
self.repository.unlock()
137
def _set_tag_dict(self, new_dict):
138
"""Replace all tag definitions
140
:param new_dict: Dictionary from tag name to target.
142
self.repository.lock_read()
144
self.repository.control_files.put_utf8('tags',
145
self._serialize_tag_dict(new_dict))
147
self.repository.unlock()
149
def _serialize_tag_dict(self, tag_dict):
151
for tag, target in sorted(tag_dict.items()):
152
# TODO: check that tag names and targets are acceptable
153
s.append(tag + '\t' + target + '\n')
156
def _deserialize_tag_dict(self, tag_content):
157
"""Convert the tag file into a dictionary of tags"""
159
for l in tag_content.splitlines():
160
tag, target = l.split('\t', 1)
165
######################################################################
168
77
class Repository(object):
873
778
except UnicodeEncodeError:
874
779
raise errors.NonAsciiRevisionId(method, self)
876
def set_tag(self, tag_name, tag_target):
877
self._tag_store.set_tag(tag_name, tag_target)
879
def lookup_tag(self, tag_name):
880
return self._tag_store.lookup_tag(tag_name)
882
def get_tag_dict(self):
883
return self._tag_store.get_tag_dict()
885
def _set_tag_dict(self, new_dict):
886
return self._tag_store._set_tag_dict(new_dict)
888
def supports_tags(self):
889
return self._tag_store.supports_tags()
891
def copy_tags_to(self, to_repository):
892
"""Copy tags to another repository.
894
Subclasses should not override this, but rather customize copying
895
through the InterRepository mechanism.
897
return InterRepository.get(self, to_repository).copy_tags()
900
782
class AllInOneRepository(Repository):
901
783
"""Legacy support - the repository behaviour for all-in-one branches."""
1214
1096
# corresponds to RepositoryFormatKnit2
1216
# TODO: within a lock scope, we could keep the tags in memory...
1218
_tag_store_class = _BasicTagStore
1220
1098
def __init__(self, _format, a_bzrdir, control_files, _revision_store,
1221
1099
control_store, text_store):
1222
1100
KnitRepository.__init__(self, _format, a_bzrdir, control_files,
1418
1296
assert klass._formats[format.get_format_string()] is format
1419
1297
del klass._formats[format.get_format_string()]
1421
def supports_tags(self):
1422
"""True if this format supports tags stored in the repository"""
1423
return False # by default
1426
1300
class PreSplitOutRepositoryFormat(RepositoryFormat):
1427
1301
"""Base class for the pre split out repository formats."""