/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
1
# Copyright (C) 2007 Canonical Ltd
2
#
3
# This program is free software; you can redistribute it and/or modify
4
# it under the terms of the GNU General Public License as published by
5
# the Free Software Foundation; either version 2 of the License, or
6
# (at your option) any later version.
7
#
8
# This program is distributed in the hope that it will be useful,
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
# GNU General Public License for more details.
12
#
13
# You should have received a copy of the GNU General Public License
14
# along with this program; if not, write to the Free Software
15
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
16
17
"""An adapter between a Git Repository and a Bazaar Branch"""
18
0.200.56 by Jelmer Vernooij
Switch to using GitPython rather than our own in-house stuff.
19
import git
0.200.45 by David Allouche
More performance hacking, introduce sqlite cache, escape characters in commits that break serializers.
20
import os
0.200.57 by Jelmer Vernooij
Fix more tests.
21
import time
0.200.45 by David Allouche
More performance hacking, introduce sqlite cache, escape characters in commits that break serializers.
22
23
import bzrlib
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
24
from bzrlib import (
0.200.20 by John Arbash Meinel
All tests are passing again
25
    deprecated_graph,
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
26
    errors,
0.200.38 by David Allouche
Reimplement GitRepository.get_inventory, simpler and faster.
27
    inventory,
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
28
    osutils,
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
29
    repository,
0.200.29 by David Allouche
Smoke test for GitRepository.get_revision, and corresponding fixes.
30
    revision,
0.200.39 by David Allouche
Black-box text for "bzr log" in a git tree. Further simplification of GitRevisionTree.
31
    revisiontree,
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
32
    urlutils,
0.200.60 by Jelmer Vernooij
Support signature functions.
33
    versionedfile,
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
34
    )
0.200.45 by David Allouche
More performance hacking, introduce sqlite cache, escape characters in commits that break serializers.
35
from bzrlib.transport import get_transport
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
36
0.200.27 by David Allouche
Flat is better than nested, remove the gitlib hierarchy.
37
from bzrlib.plugins.git import (
0.200.92 by Jelmer Vernooij
Update versionedfiles.
38
    versionedfiles
0.200.20 by John Arbash Meinel
All tests are passing again
39
    )
0.200.97 by Jelmer Vernooij
use mapping object.
40
from bzrlib.plugins.git.mapping import default_mapping
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
41
42
43
class GitRepository(repository.Repository):
44
    """An adapter to git repositories for bzr."""
45
0.200.41 by David Allouche
Define _serializer = None in GitRepository.
46
    _serializer = None
47
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
48
    def __init__(self, gitdir, lockfiles):
0.200.61 by Jelmer Vernooij
Fix tests.
49
        self.base = gitdir.root_transport.base
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
50
        self.bzrdir = gitdir
51
        self.control_files = lockfiles
0.200.90 by Jelmer Vernooij
Basic support for opening working trees.
52
        self._git = gitdir._git
0.200.56 by Jelmer Vernooij
Switch to using GitPython rather than our own in-house stuff.
53
        self.texts = None
0.200.92 by Jelmer Vernooij
Update versionedfiles.
54
        self.signatures = versionedfiles.VirtualSignatureTexts(self)
55
        self.revisions = versionedfiles.VirtualRevisionTexts(self)
0.203.1 by Aaron Bentley
Make checkouts work
56
        self._format = GitFormat()
0.200.59 by Jelmer Vernooij
Add more tests, fix revision history.
57
        self._fallback_repositories = []
0.200.45 by David Allouche
More performance hacking, introduce sqlite cache, escape characters in commits that break serializers.
58
0.200.74 by Jelmer Vernooij
Implement Repository.all_revision_ids().
59
    def _all_revision_ids(self):
60
        if self._git.heads == []:
61
            return set()
62
        ret = set()
63
        skip = 0
64
        max_count = 1000
65
        cms = None
66
        while cms != []:
67
            cms = self._git.commits("--all", max_count=max_count, skip=skip)
68
            skip += max_count
0.200.97 by Jelmer Vernooij
use mapping object.
69
            ret.update([default_mapping.convert_revision_id_git_to_bzr(cm.id) for cm in cms])
0.200.74 by Jelmer Vernooij
Implement Repository.all_revision_ids().
70
        return ret
71
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
72
    def is_shared(self):
73
        return True
74
0.200.40 by David Allouche
GitRepository.supports_rich_root() => False
75
    def supports_rich_root(self):
76
        return False
77
0.200.82 by Jelmer Vernooij
Support listing tags.
78
    #def get_revision_delta(self, revision_id):
79
    #    parent_revid = self.get_revision(revision_id).parent_ids[0]
80
    #    diff = self._git.diff(ids.convert_revision_id_bzr_to_git(parent_revid),
81
    #                   ids.convert_revision_id_bzr_to_git(revision_id))
82
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
83
    def get_ancestry(self, revision_id):
0.200.65 by Jelmer Vernooij
Implement get_ancestry properly.
84
        revision_id = revision.ensure_null(revision_id)
85
        ret = []
86
        if revision_id != revision.NULL_REVISION:
87
            skip = 0
88
            max_count = 1000
89
            cms = None
90
            while cms != []:
0.200.97 by Jelmer Vernooij
use mapping object.
91
                cms = self._git.commits(default_mapping.convert_revision_id_bzr_to_git(revision_id), max_count=max_count, skip=skip)
0.200.65 by Jelmer Vernooij
Implement get_ancestry properly.
92
                skip += max_count
0.200.97 by Jelmer Vernooij
use mapping object.
93
                ret += [default_mapping.convert_revision_id_git_to_bzr(cm.id) for cm in cms]
0.200.65 by Jelmer Vernooij
Implement get_ancestry properly.
94
        return [None] + ret
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
95
96
    def get_signature_text(self, revision_id):
97
        raise errors.NoSuchRevision(self, revision_id)
98
0.200.60 by Jelmer Vernooij
Support signature functions.
99
    def has_signature_for_revision_id(self, revision_id):
100
        return False
101
0.200.57 by Jelmer Vernooij
Fix more tests.
102
    def get_parent_map(self, revision_ids):
103
        ret = {}
104
        for revid in revision_ids:
0.200.77 by Jelmer Vernooij
Handle NULL_REVISION in get_parent_map.
105
            if revid == revision.NULL_REVISION:
106
                ret[revid] = ()
107
            else:
0.200.97 by Jelmer Vernooij
use mapping object.
108
                commit = self._git.commit(default_mapping.convert_revision_id_bzr_to_git(revid))
109
                ret[revid] = tuple([default_mapping.convert_revision_id_git_to_bzr(p.id) for p in commit.parents])
0.200.57 by Jelmer Vernooij
Fix more tests.
110
        return ret
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
111
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
112
    def get_revision(self, revision_id):
0.200.97 by Jelmer Vernooij
use mapping object.
113
        git_commit_id = default_mapping.convert_revision_id_bzr_to_git(revision_id)
0.200.57 by Jelmer Vernooij
Fix more tests.
114
        commit = self._git.commit(git_commit_id)
0.204.5 by James Westby
Lose the debuggin prints.
115
        # print "fetched revision:", git_commit_id
0.200.57 by Jelmer Vernooij
Fix more tests.
116
        revision = self._parse_rev(commit)
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
117
        return revision
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
118
119
    def has_revision(self, revision_id):
120
        try:
121
            self.get_revision(revision_id)
122
        except NoSuchRevision:
123
            return False
124
        else:
125
            return True
126
127
    def get_revisions(self, revisions):
128
        return [self.get_revision(r) for r in revisions]
129
0.200.32 by David Allouche
Rewrite GitRepository._parse_rev, with unit tests.
130
    @classmethod
0.200.57 by Jelmer Vernooij
Fix more tests.
131
    def _parse_rev(klass, commit):
132
        """Convert a git commit to a bzr revision.
133
0.200.32 by David Allouche
Rewrite GitRepository._parse_rev, with unit tests.
134
        :return: a `bzrlib.revision.Revision` object.
135
        """
0.200.97 by Jelmer Vernooij
use mapping object.
136
        rev = revision.Revision(default_mapping.convert_revision_id_git_to_bzr(commit.id))
137
        rev.parent_ids = tuple([default_mapping.convert_revision_id_git_to_bzr(p.id) for p in commit.parents])
0.200.32 by David Allouche
Rewrite GitRepository._parse_rev, with unit tests.
138
        rev.inventory_sha1 = ""
0.200.63 by Jelmer Vernooij
Ignore decoding errors since git doesn't support storing encoding.
139
        rev.message = commit.message.decode("utf-8", "replace")
0.200.59 by Jelmer Vernooij
Add more tests, fix revision history.
140
        rev.committer = str(commit.committer)
141
        rev.properties['author'] = str(commit.author)
0.200.57 by Jelmer Vernooij
Fix more tests.
142
        rev.timestamp = time.mktime(commit.committed_date)
143
        rev.timezone = 0
0.200.32 by David Allouche
Rewrite GitRepository._parse_rev, with unit tests.
144
        return rev
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
145
146
    def revision_trees(self, revids):
147
        for revid in revids:
148
            yield self.revision_tree(revid)
149
150
    def revision_tree(self, revision_id):
0.200.57 by Jelmer Vernooij
Fix more tests.
151
        revision_id = revision.ensure_null(revision_id)
152
153
        if revision_id == revision.NULL_REVISION:
154
            inv = inventory.Inventory(root_id=None)
155
            inv.revision_id = revision_id
156
            return revisiontree.RevisionTree(self, inv, revision_id)
157
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
158
        return GitRevisionTree(self, revision_id)
159
160
    def get_inventory(self, revision_id):
0.200.57 by Jelmer Vernooij
Fix more tests.
161
        assert revision_id != None
162
        return self.revision_tree(revision_id).inventory
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
163
164
165
def escape_file_id(file_id):
166
    return file_id.replace('_', '__').replace(' ', '_s')
0.200.39 by David Allouche
Black-box text for "bzr log" in a git tree. Further simplification of GitRevisionTree.
167
0.200.45 by David Allouche
More performance hacking, introduce sqlite cache, escape characters in commits that break serializers.
168
0.200.88 by Jelmer Vernooij
Fix RevisionTree.get_file_text().
169
def unescape_file_id(file_id):
170
    return file_id.replace("_s", " ").replace("__", "_")
171
172
0.200.39 by David Allouche
Black-box text for "bzr log" in a git tree. Further simplification of GitRevisionTree.
173
class GitRevisionTree(revisiontree.RevisionTree):
0.200.18 by John Arbash Meinel
Start splitting up the Git{Branch,Dir,Repository} into separate modules, etc.
174
175
    def __init__(self, repository, revision_id):
0.200.39 by David Allouche
Black-box text for "bzr log" in a git tree. Further simplification of GitRevisionTree.
176
        self._repository = repository
0.200.58 by Jelmer Vernooij
Fix remaining tests.
177
        self.revision_id = revision_id
0.200.97 by Jelmer Vernooij
use mapping object.
178
        git_id = default_mapping.convert_revision_id_bzr_to_git(revision_id)
0.200.57 by Jelmer Vernooij
Fix more tests.
179
        self.tree = repository._git.commit(git_id).tree
0.200.58 by Jelmer Vernooij
Fix remaining tests.
180
        self._inventory = inventory.Inventory(revision_id=revision_id)
181
        self._inventory.root.revision = revision_id
182
        self._build_inventory(self.tree, self._inventory.root, "")
0.200.19 by John Arbash Meinel
More refactoring. Add some direct tests for GitModel.
183
0.200.79 by Jelmer Vernooij
Implement RevisionTree.get_revision_id().
184
    def get_revision_id(self):
185
        return self.revision_id
186
0.200.87 by Jelmer Vernooij
Remove cache usage.
187
    def get_file_text(self, file_id):
0.200.43 by David Allouche
Ultra-experimental support for "bzr pull". No test. No sanity.
188
        entry = self._inventory[file_id]
0.200.87 by Jelmer Vernooij
Remove cache usage.
189
        if entry.kind == 'directory': return ""
0.200.88 by Jelmer Vernooij
Fix RevisionTree.get_file_text().
190
        return self._repository._git.blob(entry.text_id).data
0.203.1 by Aaron Bentley
Make checkouts work
191
0.200.58 by Jelmer Vernooij
Fix remaining tests.
192
    def _build_inventory(self, tree, ie, path):
193
        assert isinstance(path, str)
194
        for b in tree.contents:
195
            basename = b.name.decode("utf-8")
196
            if path == "":
197
                child_path = b.name
198
            else:
199
                child_path = urlutils.join(path, b.name)
200
            file_id = escape_file_id(child_path.encode('utf-8'))
201
            if b.mode[0] == '0':
202
                child_ie = inventory.InventoryDirectory(file_id, basename, ie.file_id)
203
            elif b.mode[0] == '1':
204
                if b.mode[1] == '0':
205
                    child_ie = inventory.InventoryFile(file_id, basename, ie.file_id)
206
                    child_ie.text_sha1 = osutils.sha_string(b.data)
207
                elif b.mode[1] == '2':
208
                    child_ie = inventory.InventoryLink(file_id, basename, ie.file_id)
209
                    child_ie.text_sha1 = osutils.sha_string("")
210
                else:
211
                    raise AssertionError(
212
                        "Unknown file kind, perms=%r." % (b.mode,))
0.200.88 by Jelmer Vernooij
Fix RevisionTree.get_file_text().
213
                child_ie.text_id = b.id
0.200.58 by Jelmer Vernooij
Fix remaining tests.
214
                child_ie.text_size = b.size
215
            else:
216
                raise AssertionError(
217
                    "Unknown blob kind, perms=%r." % (b.mode,))
218
            child_ie.executable = bool(int(b.mode[3:], 8) & 0111)
219
            child_ie.revision = self.revision_id
0.200.88 by Jelmer Vernooij
Fix RevisionTree.get_file_text().
220
            self._inventory.add(child_ie)
0.200.58 by Jelmer Vernooij
Fix remaining tests.
221
            if b.mode[0] == '0':
222
                self._build_inventory(b, child_ie, child_path)
223
0.203.1 by Aaron Bentley
Make checkouts work
224
225
class GitFormat(object):
226
227
    supports_tree_reference = False
0.200.71 by Jelmer Vernooij
Implement GitRepositoryFormat.get_format_description.
228
229
    def get_format_description(self):
230
        return "Git Repository"