/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
0.358.2 by Jelmer Vernooij
Refresh copyright headers, add my email.
1
# Copyright (C) 2009-2018 Jelmer Vernooij <jelmer@jelmer.uk>
0.200.1613 by Jelmer Vernooij
Handle encoding better in working tree iter changes.
2
# Copyright (C) 2012 Canonical Ltd
0.200.228 by Jelmer Vernooij
Split out map.
3
#
4
# This program is free software; you can redistribute it and/or modify
5
# it under the terms of the GNU General Public License as published by
6
# the Free Software Foundation; either version 2 of the License, or
7
# (at your option) any later version.
8
#
9
# This program is distributed in the hope that it will be useful,
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
# GNU General Public License for more details.
13
#
14
# You should have received a copy of the GNU General Public License
15
# along with this program; if not, write to the Free Software
0.358.1 by Jelmer Vernooij
Fix FSF address.
16
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
0.200.228 by Jelmer Vernooij
Split out map.
17
18
"""Map from Git sha's to Bazaar objects."""
19
0.200.260 by Jelmer Vernooij
Add DictGitShaMap, useful for testing.
20
from dulwich.objects import (
21
    Blob,
0.200.1029 by Jelmer Vernooij
Use dictionary with verifiers rather than requiring testament3-sha1 everywhere.
22
    Commit,
0.200.864 by Jelmer Vernooij
Cope with the first commit being pointless.
23
    Tree,
0.200.586 by Jelmer Vernooij
Fix issues pointed out by pyflakes.
24
    sha_to_hex,
0.200.1153 by Jelmer Vernooij
Import ZERO_SHA from dulwich.objects.
25
    ZERO_SHA,
0.200.260 by Jelmer Vernooij
Add DictGitShaMap, useful for testing.
26
    )
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
27
from dulwich.object_store import (
0.200.457 by Jelmer Vernooij
Use BaseObjectStore.
28
    BaseObjectStore,
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
29
    )
0.377.1 by Jelmer Vernooij
Fix some remote operations and add more tests.
30
from dulwich.pack import (
31
    pack_objects_to_data,
0.421.6 by Jelmer Vernooij
Some more simplifications.
32
    PackData,
33
    Pack,
0.377.1 by Jelmer Vernooij
Fix some remote operations and add more tests.
34
    )
0.200.249 by Jelmer Vernooij
Implement Tree.
35
6986.2.1 by Jelmer Vernooij
Move breezy.plugins.git to breezy.git.
36
from .. import (
0.231.1 by Jelmer Vernooij
Check that regenerated objects have the expected sha1.
37
    errors,
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
38
    lru_cache,
0.200.478 by Jelmer Vernooij
Cope with disappeared revisions.
39
    trace,
0.421.4 by Jelmer Vernooij
use paths in dirty_dirs.
40
    osutils,
0.200.260 by Jelmer Vernooij
Add DictGitShaMap, useful for testing.
41
    ui,
42
    )
6986.2.1 by Jelmer Vernooij
Move breezy.plugins.git to breezy.git.
43
from ..lock import LogicalLockResult
44
from ..revision import (
0.200.541 by Jelmer Vernooij
Cope with NULL_REVISION.
45
    NULL_REVISION,
46
    )
7357.1.8 by Jelmer Vernooij
Remove the InterTree object.
47
from ..tree import InterTree
7206.4.1 by Jelmer Vernooij
Move breezy.testament to breezy.bzr.testament.
48
from ..bzr.testament import (
0.200.1023 by Jelmer Vernooij
Set and verify testament.
49
    StrictTestament3,
50
    )
0.200.228 by Jelmer Vernooij
Split out map.
51
0.200.1641 by Jelmer Vernooij
Use relative imports where possible.
52
from .cache import (
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
53
    from_repository as cache_from_repository,
54
    )
0.200.1641 by Jelmer Vernooij
Use relative imports where possible.
55
from .mapping import (
0.200.463 by Jelmer Vernooij
Support remote dpush (except for references).
56
    default_mapping,
7490.70.1 by Jelmer Vernooij
Add functions for encoding/decoding git paths.
57
    encode_git_path,
0.421.3 by Jelmer Vernooij
Move directory_to_tree to object_store.
58
    entry_mode,
0.200.548 by Jelmer Vernooij
Extract unusual file modes from revision when reconstructing Trees.
59
    extract_unusual_modes,
0.231.1 by Jelmer Vernooij
Check that regenerated objects have the expected sha1.
60
    mapping_registry,
0.200.795 by Jelmer Vernooij
simplify sha extraction for blobs, process multiple blobs at once.
61
    symlink_to_blob,
0.200.229 by Jelmer Vernooij
More work on converter.
62
    )
0.200.1641 by Jelmer Vernooij
Use relative imports where possible.
63
from .unpeel_map import (
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
64
    UnpeelMap,
0.200.231 by Jelmer Vernooij
Partially fix pull.
65
    )
66
0.200.878 by Jelmer Vernooij
Fix determining of unusual file modes.
67
import posixpath
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
68
import stat
0.200.878 by Jelmer Vernooij
Fix determining of unusual file modes.
69
0.200.228 by Jelmer Vernooij
Split out map.
70
0.423.1 by Jelmer Vernooij
Some performance fixes.
71
BANNED_FILENAMES = ['.git']
72
73
0.200.452 by Jelmer Vernooij
Rename converter -> object_store, provide utility function for getting ObjectStore's.
74
def get_object_store(repo, mapping=None):
75
    git = getattr(repo, "_git", None)
76
    if git is not None:
0.200.1303 by Jelmer Vernooij
Fix locking.
77
        git.object_store.unlock = lambda: None
78
        git.object_store.lock_read = lambda: LogicalLockResult(lambda: None)
79
        git.object_store.lock_write = lambda: LogicalLockResult(lambda: None)
0.200.452 by Jelmer Vernooij
Rename converter -> object_store, provide utility function for getting ObjectStore's.
80
        return git.object_store
81
    return BazaarObjectStore(repo, mapping)
82
83
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
84
MAX_TREE_CACHE_SIZE = 50 * 1024 * 1024
85
86
87
class LRUTreeCache(object):
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
88
89
    def __init__(self, repository):
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
90
        def approx_tree_size(tree):
0.275.1 by Jelmer Vernooij
Use root_inventory.
91
            # Very rough estimate, 250 per inventory entry
0.275.5 by Jelmer Vernooij
Cope with root_inventory and inventory.
92
            try:
93
                inv = tree.root_inventory
94
            except AttributeError:
95
                inv = tree.inventory
96
            return len(inv) * 250
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
97
        self.repository = repository
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
98
        self._cache = lru_cache.LRUSizeCache(
99
            max_size=MAX_TREE_CACHE_SIZE, after_cleanup_size=None,
100
            compute_size=approx_tree_size)
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
101
0.200.963 by Jelmer Vernooij
Add some tests for LRUTreeCache.
102
    def revision_tree(self, revid):
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
103
        try:
0.200.989 by Jelmer Vernooij
Add asserts.
104
            tree = self._cache[revid]
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
105
        except KeyError:
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
106
            tree = self.repository.revision_tree(revid)
107
            self.add(tree)
0.200.989 by Jelmer Vernooij
Add asserts.
108
        return tree
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
109
110
    def iter_revision_trees(self, revids):
0.200.989 by Jelmer Vernooij
Add asserts.
111
        trees = {}
112
        todo = []
113
        for revid in revids:
114
            try:
115
                tree = self._cache[revid]
116
            except KeyError:
117
                todo.append(revid)
118
            else:
0.361.1 by Jelmer Vernooij
Don't use assert.
119
                if tree.get_revision_id() != revid:
120
                    raise AssertionError(
7143.15.2 by Jelmer Vernooij
Run autopep8.
121
                        "revision id did not match: %s != %s" % (
122
                            tree.get_revision_id(), revid))
0.200.989 by Jelmer Vernooij
Add asserts.
123
                trees[revid] = tree
124
        for tree in self.repository.revision_trees(todo):
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
125
            trees[tree.get_revision_id()] = tree
126
            self.add(tree)
127
        return (trees[r] for r in revids)
128
129
    def revision_trees(self, revids):
130
        return list(self.iter_revision_trees(revids))
131
132
    def add(self, tree):
0.270.1 by Martin
Avoid the deprecated LRUSizeCache.add method
133
        self._cache[tree.get_revision_id()] = tree
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
134
135
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
136
def _find_missing_bzr_revids(graph, want, have, shallow=None):
0.252.5 by Jelmer Vernooij
enable 'bzr push'.
137
    """Find the revisions that have to be pushed.
138
139
    :param get_parent_map: Function that returns the parents for a sequence
140
        of revisions.
141
    :param want: Revisions the target wants
142
    :param have: Revisions the target already has
143
    :return: Set of revisions to fetch
144
    """
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
145
    handled = set(have)
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
146
    if shallow:
147
        # Shallows themselves still need to be fetched, but let's exclude their
148
        # parents.
149
        for ps in graph.get_parent_map(shallow).values():
150
            handled.update(ps)
151
    handled.add(NULL_REVISION)
0.200.899 by Jelmer Vernooij
Add tests for find_missing_bzr_revids.
152
    todo = set()
0.200.1053 by Jelmer Vernooij
Fix find_missing_bzr_revids.
153
    for rev in want:
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
154
        extra_todo = graph.find_unique_ancestors(rev, handled)
155
        todo.update(extra_todo)
156
        handled.update(extra_todo)
0.200.899 by Jelmer Vernooij
Add tests for find_missing_bzr_revids.
157
    return todo
158
159
0.200.793 by Jelmer Vernooij
Make _check_expected_sha a global fn.
160
def _check_expected_sha(expected_sha, object):
0.200.797 by Jelmer Vernooij
Add docstring, fix formatting.
161
    """Check whether an object matches an expected SHA.
162
163
    :param expected_sha: None or expected SHA as either binary or as hex digest
164
    :param object: Object to verify
165
    """
0.200.793 by Jelmer Vernooij
Make _check_expected_sha a global fn.
166
    if expected_sha is None:
167
        return
168
    if len(expected_sha) == 40:
7018.3.2 by Jelmer Vernooij
Fix some git tests.
169
        if expected_sha != object.sha().hexdigest().encode('ascii'):
0.200.797 by Jelmer Vernooij
Add docstring, fix formatting.
170
            raise AssertionError("Invalid sha for %r: %s" % (object,
7143.15.2 by Jelmer Vernooij
Run autopep8.
171
                                                             expected_sha))
0.200.793 by Jelmer Vernooij
Make _check_expected_sha a global fn.
172
    elif len(expected_sha) == 20:
173
        if expected_sha != object.sha().digest():
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
174
            raise AssertionError("Invalid sha for %r: %s" % (
175
                object, sha_to_hex(expected_sha)))
0.200.793 by Jelmer Vernooij
Make _check_expected_sha a global fn.
176
    else:
0.200.797 by Jelmer Vernooij
Add docstring, fix formatting.
177
        raise AssertionError("Unknown length %d for %r" % (len(expected_sha),
7143.15.2 by Jelmer Vernooij
Run autopep8.
178
                                                           expected_sha))
0.200.793 by Jelmer Vernooij
Make _check_expected_sha a global fn.
179
180
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
181
def directory_to_tree(path, children, lookup_ie_sha1, unusual_modes,
182
                      empty_file_name, allow_empty=False):
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
183
    """Create a Git Tree object from a Bazaar directory.
184
0.421.6 by Jelmer Vernooij
Some more simplifications.
185
    :param path: directory path
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
186
    :param children: Children inventory entries
187
    :param lookup_ie_sha1: Lookup the Git SHA1 for a inventory entry
188
    :param unusual_modes: Dictionary with unusual file modes by file ids
189
    :param empty_file_name: Name to use for dummy files in empty directories,
190
        None to ignore empty directories.
191
    """
192
    tree = Tree()
0.421.6 by Jelmer Vernooij
Some more simplifications.
193
    for value in children:
0.423.1 by Jelmer Vernooij
Some performance fixes.
194
        if value.name in BANNED_FILENAMES:
195
            continue
0.421.6 by Jelmer Vernooij
Some more simplifications.
196
        child_path = osutils.pathjoin(path, value.name)
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
197
        try:
0.421.6 by Jelmer Vernooij
Some more simplifications.
198
            mode = unusual_modes[child_path]
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
199
        except KeyError:
0.421.6 by Jelmer Vernooij
Some more simplifications.
200
            mode = entry_mode(value)
201
        hexsha = lookup_ie_sha1(child_path, value)
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
202
        if hexsha is not None:
7490.70.1 by Jelmer Vernooij
Add functions for encoding/decoding git paths.
203
            tree.add(encode_git_path(value.name), mode, hexsha)
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
204
    if not allow_empty and len(tree) == 0:
205
        # Only the root can be an empty tree
206
        if empty_file_name is not None:
6964.2.1 by Jelmer Vernooij
Initial work to support brz-git on python3.
207
            tree.add(empty_file_name, stat.S_IFREG | 0o644, Blob().id)
0.421.2 by Jelmer Vernooij
Move directory_to_tree.
208
        else:
209
            return None
210
    return tree
211
212
0.200.931 by Jelmer Vernooij
Update docstring, deal with kind changes appropriately in _tree_to_objects
213
def _tree_to_objects(tree, parent_trees, idmap, unusual_modes,
0.423.1 by Jelmer Vernooij
Some performance fixes.
214
                     dummy_file_name=None, add_cache_entry=None):
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
215
    """Iterate over the objects that were introduced in a revision.
216
0.200.841 by Jelmer Vernooij
Eliminate InventorySHAMap.
217
    :param idmap: id map
0.200.931 by Jelmer Vernooij
Update docstring, deal with kind changes appropriately in _tree_to_objects
218
    :param parent_trees: Parent revision trees
219
    :param unusual_modes: Unusual file modes dictionary
0.252.30 by Jelmer Vernooij
Support creating dummy files for empty directories.
220
    :param dummy_file_name: File name to use for dummy files
221
        in empty directories. None to skip empty directories
0.200.837 by Jelmer Vernooij
Return inventory entries when creating git objects for a revision.
222
    :return: Yields (path, object, ie) entries
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
223
    """
0.282.1 by William Grant
Rework _tree_to_objects to work out parents by ID, not path. Fixes weirdness with various directory renames.
224
    dirty_dirs = set()
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
225
    new_blobs = []
226
    shamap = {}
0.250.1 by Jelmer Vernooij
Use iter_changes() rather than iterating over all contents of an inventory.
227
    try:
228
        base_tree = parent_trees[0]
229
        other_parent_trees = parent_trees[1:]
230
    except IndexError:
231
        base_tree = tree._repository.revision_tree(NULL_REVISION)
232
        other_parent_trees = []
7143.15.2 by Jelmer Vernooij
Run autopep8.
233
7358.10.1 by Jelmer Vernooij
Avoid id2path.
234
    def find_unchanged_parent_ie(path, kind, other, parent_trees):
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
235
        for ptree in parent_trees:
7357.1.8 by Jelmer Vernooij
Remove the InterTree object.
236
            intertree = InterTree.get(ptree, tree)
237
            ppath = intertree.find_source_path(path)
7358.10.1 by Jelmer Vernooij
Avoid id2path.
238
            if ppath is not None:
7192.5.1 by Jelmer Vernooij
Remove more file ids.
239
                pkind = ptree.kind(ppath)
0.275.1 by Jelmer Vernooij
Use root_inventory.
240
                if kind == "file":
0.200.1636 by Jelmer Vernooij
Some formatting fixes.
241
                    if (pkind == "file" and
7192.5.1 by Jelmer Vernooij
Remove more file ids.
242
                            ptree.get_file_sha1(ppath) == other):
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
243
                        return (
7358.10.1 by Jelmer Vernooij
Avoid id2path.
244
                            ptree.path2id(ppath), ptree.get_file_revision(ppath))
0.275.1 by Jelmer Vernooij
Use root_inventory.
245
                if kind == "symlink":
246
                    if (pkind == "symlink" and
7192.5.1 by Jelmer Vernooij
Remove more file ids.
247
                            ptree.get_symlink_target(ppath) == other):
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
248
                        return (
7358.10.1 by Jelmer Vernooij
Avoid id2path.
249
                            ptree.path2id(ppath), ptree.get_file_revision(ppath))
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
250
        raise KeyError
0.200.965 by Jelmer Vernooij
Formatting fixes.
251
0.200.931 by Jelmer Vernooij
Update docstring, deal with kind changes appropriately in _tree_to_objects
252
    # Find all the changed blobs
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
253
    for change in tree.iter_changes(base_tree):
254
        if change.name[1] in BANNED_FILENAMES:
0.424.1 by Jelmer Vernooij
Fix error message about .git directory.
255
            continue
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
256
        if change.kind[1] == "file":
257
            sha1 = tree.get_file_sha1(change.path[1])
0.423.1 by Jelmer Vernooij
Some performance fixes.
258
            blob_id = None
259
            try:
7143.15.2 by Jelmer Vernooij
Run autopep8.
260
                (pfile_id, prevision) = find_unchanged_parent_ie(
7358.10.1 by Jelmer Vernooij
Avoid id2path.
261
                    change.path[1], change.kind[1], sha1, other_parent_trees)
0.423.1 by Jelmer Vernooij
Some performance fixes.
262
            except KeyError:
263
                pass
264
            else:
265
                # It existed in one of the parents, with the same contents.
266
                # So no need to yield any new git objects.
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
267
                try:
0.423.1 by Jelmer Vernooij
Some performance fixes.
268
                    blob_id = idmap.lookup_blob_id(
269
                        pfile_id, prevision)
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
270
                except KeyError:
7414.1.1 by Jelmer Vernooij
Fix handling of no-change merges during push.
271
                    if not change.changed_content:
0.252.40 by Jelmer Vernooij
Checks for roundtripping.
272
                        # no-change merge ?
273
                        blob = Blob()
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
274
                        blob.data = tree.get_file_text(change.path[1])
0.423.1 by Jelmer Vernooij
Some performance fixes.
275
                        blob_id = blob.id
276
            if blob_id is None:
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
277
                new_blobs.append((change.path[1], change.file_id))
0.423.1 by Jelmer Vernooij
Some performance fixes.
278
            else:
7343.1.1 by Jelmer Vernooij
Fix corner case pushing to git.
279
                # TODO(jelmer): This code path does not have any test coverage.
280
                shamap[change.path[1]] = blob_id
0.423.1 by Jelmer Vernooij
Some performance fixes.
281
                if add_cache_entry is not None:
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
282
                    add_cache_entry(
283
                        ("blob", blob_id),
7343.1.1 by Jelmer Vernooij
Fix corner case pushing to git.
284
                        (change.file_id, tree.get_file_revision(change.path[1])), change.path[1])
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
285
        elif change.kind[1] == "symlink":
286
            target = tree.get_symlink_target(change.path[1])
0.423.1 by Jelmer Vernooij
Some performance fixes.
287
            blob = symlink_to_blob(target)
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
288
            shamap[change.path[1]] = blob.id
0.423.1 by Jelmer Vernooij
Some performance fixes.
289
            if add_cache_entry is not None:
7143.15.2 by Jelmer Vernooij
Run autopep8.
290
                add_cache_entry(
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
291
                    blob, (change.file_id, tree.get_file_revision(change.path[1])), change.path[1])
0.423.1 by Jelmer Vernooij
Some performance fixes.
292
            try:
7143.15.2 by Jelmer Vernooij
Run autopep8.
293
                find_unchanged_parent_ie(
7358.10.1 by Jelmer Vernooij
Avoid id2path.
294
                    change.path[1], change.kind[1], target, other_parent_trees)
0.423.1 by Jelmer Vernooij
Some performance fixes.
295
            except KeyError:
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
296
                if change.changed_content:
297
                    yield (change.path[1], blob,
7322.1.7 by Jelmer Vernooij
Fix remaining tests.
298
                           (change.file_id, tree.get_file_revision(change.path[1])))
7322.1.6 by Jelmer Vernooij
Use the new attributes on TreeChange.
299
        elif change.kind[1] is None:
300
            shamap[change.path[1]] = None
301
        elif change.kind[1] != 'directory':
302
            raise AssertionError(change.kind[1])
303
        for p in change.path:
0.421.6 by Jelmer Vernooij
Some more simplifications.
304
            if p is None:
305
                continue
0.421.8 by Jelmer Vernooij
Avoid id2path call.
306
            dirty_dirs.add(osutils.dirname(p))
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
307
0.200.931 by Jelmer Vernooij
Update docstring, deal with kind changes appropriately in _tree_to_objects
308
    # Fetch contents of the blobs that were changed
0.275.1 by Jelmer Vernooij
Use root_inventory.
309
    for (path, file_id), chunks in tree.iter_files_bytes(
7143.15.2 by Jelmer Vernooij
Run autopep8.
310
            [(path, (path, file_id)) for (path, file_id) in new_blobs]):
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
311
        obj = Blob()
7488.1.1 by Jelmer Vernooij
iter_files_bytes can return iterators.
312
        obj.chunked = list(chunks)
0.423.1 by Jelmer Vernooij
Some performance fixes.
313
        if add_cache_entry is not None:
314
            add_cache_entry(obj, (file_id, tree.get_file_revision(path)), path)
7141.7.1 by Jelmer Vernooij
Get rid of file_ids in most of Tree.
315
        yield path, obj, (file_id, tree.get_file_revision(path))
0.421.1 by Jelmer Vernooij
Use paths in shacache.
316
        shamap[path] = obj.id
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
317
0.200.879 by Jelmer Vernooij
Fix unusual modes.
318
    for path in unusual_modes:
0.421.6 by Jelmer Vernooij
Some more simplifications.
319
        dirty_dirs.add(posixpath.dirname(path))
0.282.1 by William Grant
Rework _tree_to_objects to work out parents by ID, not path. Fixes weirdness with various directory renames.
320
0.421.4 by Jelmer Vernooij
use paths in dirty_dirs.
321
    for dir in list(dirty_dirs):
322
        for parent in osutils.parent_directories(dir):
323
            if parent in dirty_dirs:
324
                break
325
            dirty_dirs.add(parent)
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
326
0.200.1926 by Jelmer Vernooij
Fix push.
327
    if dirty_dirs:
328
        dirty_dirs.add('')
329
0.421.6 by Jelmer Vernooij
Some more simplifications.
330
    def ie_to_hexsha(path, ie):
0.423.1 by Jelmer Vernooij
Some performance fixes.
331
        try:
332
            return shamap[path]
333
        except KeyError:
334
            pass
0.421.6 by Jelmer Vernooij
Some more simplifications.
335
        # FIXME: Should be the same as in parent
7290.1.18 by Jelmer Vernooij
Fix a nasty corner case when the base tree contains symlinks.
336
        if ie.kind == "file":
0.421.6 by Jelmer Vernooij
Some more simplifications.
337
            try:
338
                return idmap.lookup_blob_id(ie.file_id, ie.revision)
339
            except KeyError:
340
                # no-change merge ?
341
                blob = Blob()
7192.5.1 by Jelmer Vernooij
Remove more file ids.
342
                blob.data = tree.get_file_text(path)
0.423.1 by Jelmer Vernooij
Some performance fixes.
343
                if add_cache_entry is not None:
344
                    add_cache_entry(blob, (ie.file_id, ie.revision), path)
0.421.6 by Jelmer Vernooij
Some more simplifications.
345
                return blob.id
7290.1.18 by Jelmer Vernooij
Fix a nasty corner case when the base tree contains symlinks.
346
        elif ie.kind == "symlink":
347
            try:
348
                return idmap.lookup_blob_id(ie.file_id, ie.revision)
349
            except KeyError:
350
                # no-change merge ?
351
                target = tree.get_symlink_target(path)
352
                blob = symlink_to_blob(target)
353
                if add_cache_entry is not None:
354
                    add_cache_entry(blob, (ie.file_id, ie.revision), path)
355
                return blob.id
0.421.6 by Jelmer Vernooij
Some more simplifications.
356
        elif ie.kind == "directory":
357
            # Not all cache backends store the tree information,
358
            # calculate again from scratch
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
359
            ret = directory_to_tree(
360
                path, ie.children.values(), ie_to_hexsha, unusual_modes,
361
                dummy_file_name, ie.parent_id is None)
0.421.6 by Jelmer Vernooij
Some more simplifications.
362
            if ret is None:
363
                return ret
364
            return ret.id
365
        else:
366
            raise AssertionError
0.200.808 by Jelmer Vernooij
Avoid recalculating tree shas we already have.
367
0.421.4 by Jelmer Vernooij
use paths in dirty_dirs.
368
    for path in sorted(dirty_dirs, reverse=True):
0.423.1 by Jelmer Vernooij
Some performance fixes.
369
        if not tree.has_filename(path):
370
            continue
371
0.421.4 by Jelmer Vernooij
use paths in dirty_dirs.
372
        if tree.kind(path) != 'directory':
7290.4.1 by Jelmer Vernooij
Fix pushing of revisions from bzr to git that convert directories to symlinks.
373
            continue
0.421.6 by Jelmer Vernooij
Some more simplifications.
374
7290.1.17 by Jelmer Vernooij
Reuse directory_to_tree.
375
        obj = directory_to_tree(
376
            path, tree.iter_child_entries(path), ie_to_hexsha, unusual_modes,
377
            dummy_file_name, path == '')
0.421.6 by Jelmer Vernooij
Some more simplifications.
378
7290.1.17 by Jelmer Vernooij
Reuse directory_to_tree.
379
        if obj is not None:
0.423.1 by Jelmer Vernooij
Some performance fixes.
380
            file_id = tree.path2id(path)
381
            if add_cache_entry is not None:
382
                add_cache_entry(obj, (file_id, tree.get_revision_id()), path)
383
            yield path, obj, (file_id, tree.get_revision_id())
0.421.1 by Jelmer Vernooij
Use paths in shacache.
384
            shamap[path] = obj.id
0.200.798 by Jelmer Vernooij
Split out _inventory_to_objects into a function.
385
386
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
387
class PackTupleIterable(object):
388
389
    def __init__(self, store):
390
        self.store = store
0.200.1432 by Jelmer Vernooij
Make sure object store is locked/unlocked.
391
        self.store.lock_read()
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
392
        self.objects = {}
393
0.200.1432 by Jelmer Vernooij
Make sure object store is locked/unlocked.
394
    def __del__(self):
395
        self.store.unlock()
396
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
397
    def add(self, sha, path):
398
        self.objects[sha] = path
399
400
    def __len__(self):
401
        return len(self.objects)
402
403
    def __iter__(self):
404
        return ((self.store[object_id], path) for (object_id, path) in
7479.2.1 by Jelmer Vernooij
Drop python2 support.
405
                self.objects.items())
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
406
407
0.200.457 by Jelmer Vernooij
Use BaseObjectStore.
408
class BazaarObjectStore(BaseObjectStore):
0.200.320 by Jelmer Vernooij
Handle lightweight checkouts.
409
    """A Git-style object store backed onto a Bazaar repository."""
0.200.228 by Jelmer Vernooij
Split out map.
410
411
    def __init__(self, repository, mapping=None):
412
        self.repository = repository
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
413
        self._map_updated = False
414
        self._locked = None
0.200.228 by Jelmer Vernooij
Split out map.
415
        if mapping is None:
0.200.463 by Jelmer Vernooij
Support remote dpush (except for references).
416
            self.mapping = default_mapping
0.200.228 by Jelmer Vernooij
Split out map.
417
        else:
418
            self.mapping = mapping
0.200.847 by Jelmer Vernooij
Add BzrGitCache object.
419
        self._cache = cache_from_repository(repository)
0.200.1291 by Jelmer Vernooij
add hook for updating to local git cache.
420
        self._content_cache_types = ("tree",)
0.200.847 by Jelmer Vernooij
Add BzrGitCache object.
421
        self.start_write_group = self._cache.idmap.start_write_group
422
        self.abort_write_group = self._cache.idmap.abort_write_group
423
        self.commit_write_group = self._cache.idmap.commit_write_group
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
424
        self.tree_cache = LRUTreeCache(self.repository)
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
425
        self.unpeel_map = UnpeelMap.from_repository(self.repository)
0.200.228 by Jelmer Vernooij
Split out map.
426
0.200.1319 by Jelmer Vernooij
Only update git cache during post-commit if parents are already in the cache.
427
    def _missing_revisions(self, revisions):
428
        return self._cache.idmap.missing_revisions(revisions)
429
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
430
    def _update_sha_map(self, stop_revision=None):
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
431
        if not self.is_locked():
0.403.2 by Jelmer Vernooij
Raise LockNotHeld exception rather than AssertionError.
432
            raise errors.LockNotHeld(self)
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
433
        if self._map_updated:
434
            return
0.200.1264 by Jelmer Vernooij
Fix updating cache for single revision - don't consider it an update of the full cache.
435
        if (stop_revision is not None and
7143.15.2 by Jelmer Vernooij
Run autopep8.
436
                not self._missing_revisions([stop_revision])):
0.200.1264 by Jelmer Vernooij
Fix updating cache for single revision - don't consider it an update of the full cache.
437
            return
0.200.683 by Jelmer Vernooij
Lazier checking of which revisions need to be fetched.
438
        graph = self.repository.get_graph()
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
439
        if stop_revision is None:
0.200.1301 by Jelmer Vernooij
Avoid expensive get_parent_map call.
440
            all_revids = self.repository.all_revision_ids()
0.200.1319 by Jelmer Vernooij
Only update git cache during post-commit if parents are already in the cache.
441
            missing_revids = self._missing_revisions(all_revids)
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
442
        else:
0.200.683 by Jelmer Vernooij
Lazier checking of which revisions need to be fetched.
443
            heads = set([stop_revision])
0.200.1319 by Jelmer Vernooij
Only update git cache during post-commit if parents are already in the cache.
444
            missing_revids = self._missing_revisions(heads)
0.200.1301 by Jelmer Vernooij
Avoid expensive get_parent_map call.
445
            while heads:
446
                parents = graph.get_parent_map(heads)
447
                todo = set()
448
                for p in parents.values():
449
                    todo.update([x for x in p if x not in missing_revids])
0.200.1319 by Jelmer Vernooij
Only update git cache during post-commit if parents are already in the cache.
450
                heads = self._missing_revisions(todo)
0.200.1301 by Jelmer Vernooij
Avoid expensive get_parent_map call.
451
                missing_revids.update(heads)
0.200.694 by Jelmer Vernooij
Avoid processing NULL_REVISION.
452
        if NULL_REVISION in missing_revids:
453
            missing_revids.remove(NULL_REVISION)
0.254.16 by Jelmer Vernooij
Add optimization preventing recursive index updating.
454
        missing_revids = self.repository.has_revisions(missing_revids)
455
        if not missing_revids:
0.200.1264 by Jelmer Vernooij
Fix updating cache for single revision - don't consider it an update of the full cache.
456
            if stop_revision is None:
457
                self._map_updated = True
0.254.16 by Jelmer Vernooij
Add optimization preventing recursive index updating.
458
            return
0.200.735 by Jelmer Vernooij
Use convenience functions for start/stop write groups.
459
        self.start_write_group()
0.200.231 by Jelmer Vernooij
Partially fix pull.
460
        try:
7143.22.2 by Jelmer Vernooij
use more context libs for progress bars.
461
            with ui.ui_factory.nested_progress_bar() as pb:
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
462
                for i, revid in enumerate(graph.iter_topo_order(
463
                        missing_revids)):
0.254.16 by Jelmer Vernooij
Add optimization preventing recursive index updating.
464
                    trace.mutter('processing %r', revid)
0.254.4 by Jelmer Vernooij
Merge trunk.
465
                    pb.update("updating git map", i, len(missing_revids))
466
                    self._update_sha_map_revision(revid)
0.200.1264 by Jelmer Vernooij
Fix updating cache for single revision - don't consider it an update of the full cache.
467
            if stop_revision is None:
468
                self._map_updated = True
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
469
        except BaseException:
0.200.735 by Jelmer Vernooij
Use convenience functions for start/stop write groups.
470
            self.abort_write_group()
471
            raise
472
        else:
473
            self.commit_write_group()
0.200.229 by Jelmer Vernooij
More work on converter.
474
0.200.422 by Jelmer Vernooij
'bzr git-object' without arguments now prints the available git objects.
475
    def __iter__(self):
476
        self._update_sha_map()
0.200.847 by Jelmer Vernooij
Add BzrGitCache object.
477
        return iter(self._cache.idmap.sha1s())
0.200.422 by Jelmer Vernooij
'bzr git-object' without arguments now prints the available git objects.
478
0.200.1509 by Jelmer Vernooij
Properly raise exception when pulling from git into bzr without experimental mappings.
479
    def _reconstruct_commit(self, rev, tree_sha, lossy, verifiers):
0.200.1029 by Jelmer Vernooij
Use dictionary with verifiers rather than requiring testament3-sha1 everywhere.
480
        """Reconstruct a Commit object.
481
482
        :param rev: Revision object
483
        :param tree_sha: SHA1 of the root tree object
0.200.1509 by Jelmer Vernooij
Properly raise exception when pulling from git into bzr without experimental mappings.
484
        :param lossy: Whether or not to roundtrip bzr metadata
0.200.1029 by Jelmer Vernooij
Use dictionary with verifiers rather than requiring testament3-sha1 everywhere.
485
        :param verifiers: Verifiers for the commits
486
        :return: Commit object
487
        """
0.238.7 by Jelmer Vernooij
Cope with ghosts a bit better.
488
        def parent_lookup(revid):
489
            try:
490
                return self._lookup_revision_sha1(revid)
491
            except errors.NoSuchRevision:
492
                return None
0.252.4 by Jelmer Vernooij
More work on roundtripping.
493
        return self.mapping.export_commit(rev, tree_sha, parent_lookup,
7143.15.2 by Jelmer Vernooij
Run autopep8.
494
                                          lossy, verifiers)
0.238.7 by Jelmer Vernooij
Cope with ghosts a bit better.
495
0.423.1 by Jelmer Vernooij
Some performance fixes.
496
    def _revision_to_objects(self, rev, tree, lossy, add_cache_entry=None):
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
497
        """Convert a revision to a set of git objects.
498
499
        :param rev: Bazaar revision object
500
        :param tree: Bazaar revision tree
0.200.1509 by Jelmer Vernooij
Properly raise exception when pulling from git into bzr without experimental mappings.
501
        :param lossy: Whether to not roundtrip all Bazaar revision data
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
502
        """
0.200.548 by Jelmer Vernooij
Extract unusual file modes from revision when reconstructing Trees.
503
        unusual_modes = extract_unusual_modes(rev)
0.200.789 by Jelmer Vernooij
Cope with ghosts, cache inventories.
504
        present_parents = self.repository.has_revisions(rev.parent_ids)
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
505
        parent_trees = self.tree_cache.revision_trees(
0.200.797 by Jelmer Vernooij
Add docstring, fix formatting.
506
            [p for p in rev.parent_ids if p in present_parents])
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
507
        root_tree = None
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
508
        for path, obj, bzr_key_data in _tree_to_objects(
509
                tree, parent_trees, self._cache.idmap, unusual_modes,
510
                self.mapping.BZR_DUMMY_FILE, add_cache_entry):
0.200.773 by Jelmer Vernooij
Implement inventory_to_objects
511
            if path == "":
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
512
                root_tree = obj
0.275.2 by Jelmer Vernooij
Pass tuples around for cache entries, rather than inventory entries.
513
                root_key_data = bzr_key_data
0.252.34 by Jelmer Vernooij
Yield the proper object for the tree root.
514
                # Don't yield just yet
515
            else:
0.423.1 by Jelmer Vernooij
Some performance fixes.
516
                yield path, obj
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
517
        if root_tree is None:
0.250.2 by Jelmer Vernooij
Make it work for evolution.
518
            # Pointless commit - get the tree sha elsewhere
0.200.864 by Jelmer Vernooij
Cope with the first commit being pointless.
519
            if not rev.parent_ids:
0.252.23 by Jelmer Vernooij
More work on roundtripping support.
520
                root_tree = Tree()
0.200.864 by Jelmer Vernooij
Cope with the first commit being pointless.
521
            else:
522
                base_sha1 = self._lookup_revision_sha1(rev.parent_ids[0])
0.252.37 by Jelmer Vernooij
Factor out some common code for finding refs to send.
523
                root_tree = self[self[base_sha1].tree]
7358.14.1 by Jelmer Vernooij
Remove Tree.get_root_id() in favour of Tree.path2id('').
524
            root_key_data = (tree.path2id(''), tree.get_revision_id())
0.423.1 by Jelmer Vernooij
Some performance fixes.
525
        if add_cache_entry is not None:
526
            add_cache_entry(root_tree, root_key_data, "")
527
        yield "", root_tree
0.200.1509 by Jelmer Vernooij
Properly raise exception when pulling from git into bzr without experimental mappings.
528
        if not lossy:
0.200.1559 by Jelmer Vernooij
Fix compatibility with bzr 2.5.
529
            testament3 = StrictTestament3(rev, tree)
7143.15.2 by Jelmer Vernooij
Run autopep8.
530
            verifiers = {"testament3-sha1": testament3.as_sha1()}
0.200.1023 by Jelmer Vernooij
Set and verify testament.
531
        else:
0.200.1029 by Jelmer Vernooij
Use dictionary with verifiers rather than requiring testament3-sha1 everywhere.
532
            verifiers = {}
0.252.43 by Jelmer Vernooij
Some refactoring, support proper file ids in revision deltas.
533
        commit_obj = self._reconstruct_commit(rev, root_tree.id,
7143.15.2 by Jelmer Vernooij
Run autopep8.
534
                                              lossy=lossy, verifiers=verifiers)
0.231.1 by Jelmer Vernooij
Check that regenerated objects have the expected sha1.
535
        try:
0.200.841 by Jelmer Vernooij
Eliminate InventorySHAMap.
536
            foreign_revid, mapping = mapping_registry.parse_revision_id(
537
                rev.revision_id)
0.231.1 by Jelmer Vernooij
Check that regenerated objects have the expected sha1.
538
        except errors.InvalidRevisionId:
539
            pass
540
        else:
0.200.794 by Jelmer Vernooij
Use _check_expected_sha rather than custom checks.
541
            _check_expected_sha(foreign_revid, commit_obj)
0.423.1 by Jelmer Vernooij
Some performance fixes.
542
        if add_cache_entry is not None:
543
            add_cache_entry(commit_obj, verifiers, None)
544
545
        yield None, commit_obj
0.200.783 by Jelmer Vernooij
Move object generation into a separate function.
546
0.200.838 by Jelmer Vernooij
Add convenience object for updating the object store.
547
    def _get_updater(self, rev):
0.200.849 by Jelmer Vernooij
Allow cache backends to decide when to add entries rather than adding once per commit.
548
        return self._cache.get_updater(rev)
0.200.838 by Jelmer Vernooij
Add convenience object for updating the object store.
549
0.200.783 by Jelmer Vernooij
Move object generation into a separate function.
550
    def _update_sha_map_revision(self, revid):
551
        rev = self.repository.get_revision(revid)
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
552
        tree = self.tree_cache.revision_tree(rev.revision_id)
0.200.838 by Jelmer Vernooij
Add convenience object for updating the object store.
553
        updater = self._get_updater(rev)
0.200.1510 by Jelmer Vernooij
Fix tests.
554
        # FIXME JRV 2011-12-15: Shouldn't we try both values for lossy ?
0.423.1 by Jelmer Vernooij
Some performance fixes.
555
        for path, obj in self._revision_to_objects(
556
                rev, tree, lossy=(not self.mapping.roundtripping),
557
                add_cache_entry=updater.add_object):
0.200.1029 by Jelmer Vernooij
Use dictionary with verifiers rather than requiring testament3-sha1 everywhere.
558
            if isinstance(obj, Commit):
0.423.1 by Jelmer Vernooij
Some performance fixes.
559
                commit_obj = obj
0.200.838 by Jelmer Vernooij
Add convenience object for updating the object store.
560
        commit_obj = updater.finish()
0.200.781 by Jelmer Vernooij
Return commit id after converting a revision.
561
        return commit_obj.id
0.200.229 by Jelmer Vernooij
More work on converter.
562
0.200.855 by Jelmer Vernooij
_get_ -> _reconstruct_.
563
    def _reconstruct_blobs(self, keys):
0.200.698 by Jelmer Vernooij
Merge fixes for SHA1s of symlinks.
564
        """Return a Git Blob object from a fileid and revision stored in bzr.
565
566
        :param fileid: File id of the text
567
        :param revision: Revision of the text
568
        """
0.250.2 by Jelmer Vernooij
Make it work for evolution.
569
        stream = self.repository.iter_files_bytes(
570
            ((key[0], key[1], key) for key in keys))
0.326.1 by Jelmer Vernooij
Update objectstore to new API.
571
        for (file_id, revision, expected_sha), chunks in stream:
0.200.854 by Jelmer Vernooij
_get_blob -> _get_blobs.
572
            blob = Blob()
7488.1.1 by Jelmer Vernooij
iter_files_bytes can return iterators.
573
            blob.chunked = list(chunks)
7290.4.1 by Jelmer Vernooij
Fix pushing of revisions from bzr to git that convert directories to symlinks.
574
            if blob.id != expected_sha and blob.data == b"":
0.200.854 by Jelmer Vernooij
_get_blob -> _get_blobs.
575
                # Perhaps it's a symlink ?
576
                tree = self.tree_cache.revision_tree(revision)
0.326.1 by Jelmer Vernooij
Update objectstore to new API.
577
                path = tree.id2path(file_id)
7192.5.1 by Jelmer Vernooij
Remove more file ids.
578
                if tree.kind(path) == 'symlink':
579
                    blob = symlink_to_blob(tree.get_symlink_target(path))
0.200.854 by Jelmer Vernooij
_get_blob -> _get_blobs.
580
            _check_expected_sha(expected_sha, blob)
581
            yield blob
0.200.229 by Jelmer Vernooij
More work on converter.
582
0.273.2 by Jelmer Vernooij
use tree objects rather than inventories
583
    def _reconstruct_tree(self, fileid, revid, bzr_tree, unusual_modes,
7143.15.2 by Jelmer Vernooij
Run autopep8.
584
                          expected_sha=None):
0.200.343 by Jelmer Vernooij
Use file ids consistently in map.
585
        """Return a Git Tree object from a file id and a revision stored in bzr.
0.200.249 by Jelmer Vernooij
Implement Tree.
586
0.200.343 by Jelmer Vernooij
Use file ids consistently in map.
587
        :param fileid: fileid in the tree.
0.200.249 by Jelmer Vernooij
Implement Tree.
588
        :param revision: Revision of the tree.
589
        """
0.421.6 by Jelmer Vernooij
Some more simplifications.
590
        def get_ie_sha1(path, entry):
0.200.776 by Jelmer Vernooij
Remove unnecessary lookups.
591
            if entry.kind == "directory":
0.200.808 by Jelmer Vernooij
Avoid recalculating tree shas we already have.
592
                try:
0.200.859 by Jelmer Vernooij
Trivial cleanups.
593
                    return self._cache.idmap.lookup_tree_id(entry.file_id,
7143.15.2 by Jelmer Vernooij
Run autopep8.
594
                                                            revid)
0.200.812 by Jelmer Vernooij
Catch KeyError from lookup_tree as well - some caches (such as sqlite) don't store all trees, only some.
595
                except (NotImplementedError, KeyError):
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
596
                    obj = self._reconstruct_tree(
597
                        entry.file_id, revid, bzr_tree, unusual_modes)
0.200.808 by Jelmer Vernooij
Avoid recalculating tree shas we already have.
598
                    if obj is None:
599
                        return None
600
                    else:
601
                        return obj.id
0.200.776 by Jelmer Vernooij
Remove unnecessary lookups.
602
            elif entry.kind in ("file", "symlink"):
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
603
                try:
604
                    return self._cache.idmap.lookup_blob_id(entry.file_id,
7143.15.2 by Jelmer Vernooij
Run autopep8.
605
                                                            entry.revision)
0.200.868 by Jelmer Vernooij
Cope with no-change merges.
606
                except KeyError:
607
                    # no-change merge?
7018.3.2 by Jelmer Vernooij
Fix some git tests.
608
                    return next(self._reconstruct_blobs(
609
                        [(entry.file_id, entry.revision, None)])).id
0.200.1551 by Jelmer Vernooij
Support nested trees in reconstruction code.
610
            elif entry.kind == 'tree-reference':
611
                # FIXME: Make sure the file id is the root id
612
                return self._lookup_revision_sha1(entry.reference_revision)
0.200.776 by Jelmer Vernooij
Remove unnecessary lookups.
613
            else:
614
                raise AssertionError("unknown entry kind '%s'" % entry.kind)
0.421.6 by Jelmer Vernooij
Some more simplifications.
615
        path = bzr_tree.id2path(fileid)
616
        tree = directory_to_tree(
7143.15.2 by Jelmer Vernooij
Run autopep8.
617
            path,
618
            bzr_tree.iter_child_entries(path),
619
            get_ie_sha1, unusual_modes, self.mapping.BZR_DUMMY_FILE,
7358.14.1 by Jelmer Vernooij
Remove Tree.get_root_id() in favour of Tree.path2id('').
620
            bzr_tree.path2id('') == fileid)
0.200.1223 by Jelmer Vernooij
Cope with empty directories.
621
        if tree is not None:
622
            _check_expected_sha(expected_sha, tree)
0.200.249 by Jelmer Vernooij
Implement Tree.
623
        return tree
0.200.229 by Jelmer Vernooij
More work on converter.
624
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
625
    def get_parents(self, sha):
0.200.454 by Jelmer Vernooij
Use ObjectStore.find_missing_objects in server.
626
        """Retrieve the parents of a Git commit by SHA1.
627
628
        :param sha: SHA1 of the commit
629
        :raises: KeyError, NotCommitError
630
        """
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
631
        return self[sha].parents
632
0.200.364 by Jelmer Vernooij
Reimplement dpush, but more efficient and only writing a single pack file rather than one per revision.
633
    def _lookup_revision_sha1(self, revid):
0.200.449 by Jelmer Vernooij
Use BazaarObjectStore to find matching SHA1s for bzr revisions.
634
        """Return the SHA1 matching a Bazaar revision."""
0.200.541 by Jelmer Vernooij
Cope with NULL_REVISION.
635
        if revid == NULL_REVISION:
0.200.891 by Jelmer Vernooij
Use ZERO_SHA constant where possible.
636
            return ZERO_SHA
0.200.364 by Jelmer Vernooij
Reimplement dpush, but more efficient and only writing a single pack file rather than one per revision.
637
        try:
0.200.847 by Jelmer Vernooij
Add BzrGitCache object.
638
            return self._cache.idmap.lookup_commit(revid)
0.200.364 by Jelmer Vernooij
Reimplement dpush, but more efficient and only writing a single pack file rather than one per revision.
639
        except KeyError:
0.200.682 by Jelmer Vernooij
Avoid doing a full sha map update if we already know the SHA1.
640
            try:
641
                return mapping_registry.parse_revision_id(revid)[0]
642
            except errors.InvalidRevisionId:
0.200.1264 by Jelmer Vernooij
Fix updating cache for single revision - don't consider it an update of the full cache.
643
                self._update_sha_map(revid)
0.200.847 by Jelmer Vernooij
Add BzrGitCache object.
644
                return self._cache.idmap.lookup_commit(revid)
0.200.364 by Jelmer Vernooij
Reimplement dpush, but more efficient and only writing a single pack file rather than one per revision.
645
0.200.310 by Jelmer Vernooij
Fix pull from remote branches.
646
    def get_raw(self, sha):
0.200.454 by Jelmer Vernooij
Use ObjectStore.find_missing_objects in server.
647
        """Get the raw representation of a Git object by SHA1.
648
649
        :param sha: SHA1 of the git object
650
        """
0.200.1622 by William Grant
BazaarObjectStore.get_raw now copes with non-hex-encoded SHA-1s, as some ref delta resolution in dulwich apparently requires.
651
        if len(sha) == 20:
652
            sha = sha_to_hex(sha)
0.200.566 by Jelmer Vernooij
Fix ObjectStore.get_raw() .
653
        obj = self[sha]
654
        return (obj.type, obj.as_raw_string())
0.200.310 by Jelmer Vernooij
Fix pull from remote branches.
655
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
656
    def __contains__(self, sha):
657
        # See if sha is in map
658
        try:
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
659
            for (type, type_data) in self.lookup_git_sha(sha):
660
                if type == "commit":
661
                    if self.repository.has_revision(type_data[0]):
662
                        return True
663
                elif type == "blob":
0.200.1648 by Jelmer Vernooij
Fix compatibility with newer versions of breezy.
664
                    if type_data in self.repository.texts:
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
665
                        return True
666
                elif type == "tree":
667
                    if self.repository.has_revision(type_data[1]):
668
                        return True
669
                else:
670
                    raise AssertionError("Unknown object type '%s'" % type)
0.200.568 by Jelmer Vernooij
Properly check that matching bzr objects exist.
671
            else:
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
672
                return False
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
673
        except KeyError:
674
            return False
675
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
676
    def lock_read(self):
677
        self._locked = 'r'
678
        self._map_updated = False
679
        self.repository.lock_read()
680
        return LogicalLockResult(self.unlock)
681
682
    def lock_write(self):
683
        self._locked = 'r'
684
        self._map_updated = False
685
        self.repository.lock_write()
686
        return LogicalLockResult(self.unlock)
687
688
    def is_locked(self):
689
        return (self._locked is not None)
690
691
    def unlock(self):
692
        self._locked = None
693
        self._map_updated = False
694
        self.repository.unlock()
695
696
    def lookup_git_shas(self, shas):
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
697
        ret = {}
698
        for sha in shas:
0.200.969 by Jelmer Vernooij
Use tuples with bzr revid and git sha to avoid lookups.
699
            if sha == ZERO_SHA:
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
700
                ret[sha] = [("commit", (NULL_REVISION, None, {}))]
0.200.969 by Jelmer Vernooij
Use tuples with bzr revid and git sha to avoid lookups.
701
                continue
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
702
            try:
0.261.3 by Jelmer Vernooij
Fix more tests.
703
                ret[sha] = list(self._cache.idmap.lookup_git_sha(sha))
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
704
            except KeyError:
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
705
                # if not, see if there are any unconverted revisions and
706
                # add them to the map, search for sha in map again
707
                self._update_sha_map()
708
                try:
709
                    ret[sha] = list(self._cache.idmap.lookup_git_sha(sha))
710
                except KeyError:
711
                    pass
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
712
        return ret
713
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
714
    def lookup_git_sha(self, sha):
715
        return self.lookup_git_shas([sha])[sha]
0.200.437 by Jelmer Vernooij
Implement BazaarObjectStore.__contains__, BazaarObjectStore.iter_shas, BazaarObjectStore.get_parents.
716
717
    def __getitem__(self, sha):
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
718
        for (kind, type_data) in self.lookup_git_sha(sha):
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
719
            # convert object to git object
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
720
            if kind == "commit":
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
721
                (revid, tree_sha, verifiers) = type_data
722
                try:
723
                    rev = self.repository.get_revision(revid)
724
                except errors.NoSuchRevision:
0.200.1341 by Jelmer Vernooij
Add check that callers don't try to look up NULL_REVISION.
725
                    if revid == NULL_REVISION:
726
                        raise AssertionError(
727
                            "should not try to look up NULL_REVISION")
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
728
                    trace.mutter('entry for %s %s in shamap: %r, but not '
729
                                 'found in repository', kind, sha, type_data)
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
730
                    raise KeyError(sha)
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
731
                # FIXME: the type data should say whether conversion was
732
                # lossless
733
                commit = self._reconstruct_commit(
734
                    rev, tree_sha, lossy=(not self.mapping.roundtripping),
735
                    verifiers=verifiers)
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
736
                _check_expected_sha(sha, commit)
737
                return commit
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
738
            elif kind == "blob":
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
739
                (fileid, revision) = type_data
0.200.1212 by Jelmer Vernooij
Support read locking object stores.
740
                blobs = self._reconstruct_blobs([(fileid, revision, sha)])
7018.3.2 by Jelmer Vernooij
Fix some git tests.
741
                return next(blobs)
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
742
            elif kind == "tree":
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
743
                (fileid, revid) = type_data
744
                try:
745
                    tree = self.tree_cache.revision_tree(revid)
746
                    rev = self.repository.get_revision(revid)
747
                except errors.NoSuchRevision:
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
748
                    trace.mutter(
749
                        'entry for %s %s in shamap: %r, but not found in '
750
                        'repository', kind, sha, type_data)
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
751
                    raise KeyError(sha)
752
                unusual_modes = extract_unusual_modes(rev)
753
                try:
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
754
                    return self._reconstruct_tree(
755
                        fileid, revid, tree, unusual_modes, expected_sha=sha)
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
756
                except errors.NoSuchRevision:
757
                    raise KeyError(sha)
758
            else:
0.200.1169 by Jelmer Vernooij
Fix some sha lookups.
759
                raise AssertionError("Unknown object type '%s'" % kind)
0.200.228 by Jelmer Vernooij
Split out map.
760
        else:
0.261.1 by Jelmer Vernooij
Initial work on supporting multiple results for git shas.
761
            raise KeyError(sha)
0.200.782 by Jelmer Vernooij
Add custom generate_pack_contents implementation.
762
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
763
    def generate_lossy_pack_data(self, have, want, shallow=None,
764
                                 progress=None,
7143.15.2 by Jelmer Vernooij
Run autopep8.
765
                                 get_tagged=None, ofs_delta=False):
0.377.1 by Jelmer Vernooij
Fix some remote operations and add more tests.
766
        return pack_objects_to_data(
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
767
            self.generate_pack_contents(have, want, progress=progress,
768
                                        shallow=shallow, get_tagged=get_tagged,
7143.15.2 by Jelmer Vernooij
Run autopep8.
769
                                        lossy=True))
0.252.37 by Jelmer Vernooij
Factor out some common code for finding refs to send.
770
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
771
    def generate_pack_contents(self, have, want, shallow=None, progress=None,
7143.15.2 by Jelmer Vernooij
Run autopep8.
772
                               ofs_delta=False, get_tagged=None, lossy=False):
0.200.782 by Jelmer Vernooij
Add custom generate_pack_contents implementation.
773
        """Iterate over the contents of a pack file.
774
775
        :param have: List of SHA1s of objects that should not be sent
776
        :param want: List of SHA1s of objects that should be sent
777
        """
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
778
        processed = set()
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
779
        ret = self.lookup_git_shas(have + want)
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
780
        for commit_sha in have:
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
781
            commit_sha = self.unpeel_map.peel_tag(commit_sha, commit_sha)
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
782
            try:
0.200.1180 by Jelmer Vernooij
Some dpush fixes.
783
                for (type, type_data) in ret[commit_sha]:
0.361.1 by Jelmer Vernooij
Don't use assert.
784
                    if type != "commit":
785
                        raise AssertionError("Type was %s, not commit" % type)
0.200.1180 by Jelmer Vernooij
Some dpush fixes.
786
                    processed.add(type_data[0])
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
787
            except KeyError:
0.200.1292 by Jelmer Vernooij
Fix repeeling objects when determining what to send.
788
                trace.mutter("unable to find remote ref %s", commit_sha)
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
789
        pending = set()
790
        for commit_sha in want:
791
            if commit_sha in have:
792
                continue
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
793
            try:
0.200.1180 by Jelmer Vernooij
Some dpush fixes.
794
                for (type, type_data) in ret[commit_sha]:
0.361.1 by Jelmer Vernooij
Don't use assert.
795
                    if type != "commit":
796
                        raise AssertionError("Type was %s, not commit" % type)
0.200.1180 by Jelmer Vernooij
Some dpush fixes.
797
                    pending.add(type_data[0])
0.200.898 by Jelmer Vernooij
Optimize finding of git shas.
798
            except KeyError:
799
                pass
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
800
        shallows = set()
801
        for commit_sha in shallow or set():
802
            try:
803
                for (type, type_data) in ret[commit_sha]:
804
                    if type != "commit":
805
                        raise AssertionError("Type was %s, not commit" % type)
806
                    shallows.add(type_data[0])
807
            except KeyError:
808
                pass
0.200.899 by Jelmer Vernooij
Add tests for find_missing_bzr_revids.
809
0.200.1053 by Jelmer Vernooij
Fix find_missing_bzr_revids.
810
        graph = self.repository.get_graph()
7490.26.1 by Jelmer Vernooij
Fix shallow handling in Git.
811
        todo = _find_missing_bzr_revids(graph, pending, processed, shallow)
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
812
        ret = PackTupleIterable(self)
7143.22.2 by Jelmer Vernooij
use more context libs for progress bars.
813
        with ui.ui_factory.nested_progress_bar() as pb:
0.423.1 by Jelmer Vernooij
Some performance fixes.
814
            for i, revid in enumerate(graph.iter_topo_order(todo)):
0.200.787 by Jelmer Vernooij
Implement custom ObjectWalker.generate_pack_contents.
815
                pb.update("generating git objects", i, len(todo))
0.200.1059 by Jelmer Vernooij
Fix graph tests.
816
                try:
817
                    rev = self.repository.get_revision(revid)
818
                except errors.NoSuchRevision:
819
                    continue
0.200.852 by Jelmer Vernooij
Cache trees rather than inventories.
820
                tree = self.tree_cache.revision_tree(revid)
0.423.1 by Jelmer Vernooij
Some performance fixes.
821
                for path, obj in self._revision_to_objects(
822
                        rev, tree, lossy=lossy):
0.200.1290 by Jelmer Vernooij
Avoid storing all objects to push in memory.
823
                    ret.add(obj.id, path)
0.200.1298 by Jelmer Vernooij
Fix compatibility with newer versions of dulwich.
824
            return ret
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
825
826
    def add_thin_pack(self):
827
        import tempfile
828
        import os
829
        fd, path = tempfile.mkstemp(suffix=".pack")
830
        f = os.fdopen(fd, 'wb')
7143.15.2 by Jelmer Vernooij
Run autopep8.
831
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
832
        def commit():
0.200.1641 by Jelmer Vernooij
Use relative imports where possible.
833
            from .fetch import import_git_objects
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
834
            os.fsync(fd)
835
            f.close()
836
            if os.path.getsize(path) == 0:
837
                return
838
            pd = PackData(path)
7143.15.2 by Jelmer Vernooij
Run autopep8.
839
            pd.create_index_v2(path[:-5] + ".idx", self.object_store.get_raw)
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
840
841
            p = Pack(path[:-5])
0.200.1788 by Jelmer Vernooij
Use context managers.
842
            with self.repository.lock_write():
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
843
                self.repository.start_write_group()
844
                try:
0.200.1289 by Jelmer Vernooij
Switch to dulwich 0.8.0.
845
                    import_git_objects(self.repository, self.mapping,
7143.15.2 by Jelmer Vernooij
Run autopep8.
846
                                       p.iterobjects(get_raw=self.get_raw),
847
                                       self.object_store)
7143.15.3 by Jelmer Vernooij
Fix pep8 issues in breezy.git.
848
                except BaseException:
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
849
                    self.repository.abort_write_group()
850
                    raise
851
                else:
852
                    self.repository.commit_write_group()
853
        return f, commit
854
0.200.1636 by Jelmer Vernooij
Some formatting fixes.
855
    # The pack isn't kept around anyway, so no point
0.251.1 by Jelmer Vernooij
Implement ObjectStore.add_{thin_,}pack.
856
    # in treating full packs different from thin packs
857
    add_pack = add_thin_pack