~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/smart/repository.py

Merge from bzr.dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
31
31
    SmartServerRequest,
32
32
    SuccessfulSmartServerResponse,
33
33
    )
 
34
from bzrlib.repository import _strip_NULL_ghosts
34
35
from bzrlib import revision as _mod_revision
35
36
 
36
37
 
40
41
    def do(self, path, *args):
41
42
        """Execute a repository request.
42
43
        
43
 
        The repository must be at the exact path - no searching is done.
 
44
        All Repository requests take a path to the repository as their first
 
45
        argument.  The repository must be at the exact path given by the
 
46
        client - no searching is done.
44
47
 
45
48
        The actual logic is delegated to self.do_repository_request.
46
49
 
47
 
        :param path: The path for the repository.
48
 
        :return: A smart server from self.do_repository_request().
 
50
        :param client_path: The path for the repository as received from the
 
51
            client.
 
52
        :return: A SmartServerResponse from self.do_repository_request().
49
53
        """
50
 
        transport = self._backing_transport.clone(path)
 
54
        transport = self.transport_from_client_path(path)
51
55
        bzrdir = BzrDir.open_from_transport(transport)
52
56
        # Save the repository for use with do_body.
53
57
        self._repository = bzrdir.open_repository()
87
91
            repository.unlock()
88
92
 
89
93
 
 
94
class SmartServerRepositoryReadLocked(SmartServerRepositoryRequest):
 
95
    """Calls self.do_readlocked_repository_request."""
 
96
 
 
97
    def do_repository_request(self, repository, *args):
 
98
        """Read lock a repository for do_readlocked_repository_request."""
 
99
        repository.lock_read()
 
100
        try:
 
101
            return self.do_readlocked_repository_request(repository, *args)
 
102
        finally:
 
103
            repository.unlock()
 
104
 
 
105
 
90
106
class SmartServerRepositoryGetParentMap(SmartServerRepositoryRequest):
91
107
    """Bzr 1.2+ - get parent data for revisions during a graph search."""
92
108
    
173
189
            ('ok', ), bz2.compress('\n'.join(lines)))
174
190
 
175
191
 
176
 
class SmartServerRepositoryGetRevisionGraph(SmartServerRepositoryRequest):
 
192
class SmartServerRepositoryGetRevisionGraph(SmartServerRepositoryReadLocked):
177
193
    
178
 
    def do_repository_request(self, repository, revision_id):
 
194
    def do_readlocked_repository_request(self, repository, revision_id):
179
195
        """Return the result of repository.get_revision_graph(revision_id).
 
196
 
 
197
        Deprecated as of bzr 1.4, but supported for older clients.
180
198
        
181
199
        :param repository: The repository to query in.
182
200
        :param revision_id: The utf8 encoded revision_id to get a graph from.
187
205
            revision_id = None
188
206
 
189
207
        lines = []
190
 
        try:
191
 
            revision_graph = repository.get_revision_graph(revision_id)
192
 
        except errors.NoSuchRevision:
 
208
        graph = repository.get_graph()
 
209
        if revision_id:
 
210
            search_ids = [revision_id]
 
211
        else:
 
212
            search_ids = repository.all_revision_ids()
 
213
        search = graph._make_breadth_first_searcher(search_ids)
 
214
        transitive_ids = set()
 
215
        map(transitive_ids.update, list(search))
 
216
        parent_map = graph.get_parent_map(transitive_ids)
 
217
        revision_graph = _strip_NULL_ghosts(parent_map)
 
218
        if revision_id and revision_id not in revision_graph:
193
219
            # Note that we return an empty body, rather than omitting the body.
194
220
            # This way the client knows that it can always expect to find a body
195
221
            # in the response for this method, even in the error case.
423
449
        pack = ContainerSerialiser()
424
450
        yield pack.begin()
425
451
        try:
426
 
            for name_tuple, bytes in stream:
427
 
                yield pack.bytes_record(bytes, [name_tuple])
 
452
            try:
 
453
                for name_tuple, bytes in stream:
 
454
                    yield pack.bytes_record(bytes, [name_tuple])
 
455
            except:
 
456
                # Undo the lock_read that that happens once the iterator from
 
457
                # get_data_stream is started.
 
458
                repository.unlock()
 
459
                raise
428
460
        except errors.RevisionNotPresent, e:
429
461
            # This shouldn't be able to happen, but as we don't buffer
430
462
            # everything it can in theory happen.
 
463
            repository.unlock()
431
464
            yield FailedSmartServerResponse(('NoSuchRevision', e.revision_id))
432
 
        repository.unlock()
433
 
        pack.end()
 
465
        else:
 
466
            repository.unlock()
 
467
            pack.end()
434
468