/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to bzrlib/tests/test_remote.py

Merge bzr.dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
27
27
from cStringIO import StringIO
28
28
 
29
29
from bzrlib import (
 
30
    bzrdir,
30
31
    config,
31
32
    errors,
32
33
    graph,
171
172
    """Lookalike for _SmartClient allowing testing."""
172
173
    
173
174
    def __init__(self, fake_medium_base='fake base'):
174
 
        """Create a FakeClient.
175
 
 
176
 
        :param responses: A list of response-tuple, body-data pairs to be sent
177
 
            back to callers.  A special case is if the response-tuple is
178
 
            'unknown verb', then a UnknownSmartMethod will be raised for that
179
 
            call, using the second element of the tuple as the verb in the
180
 
            exception.
181
 
        """
 
175
        """Create a FakeClient."""
182
176
        self.responses = []
183
177
        self._calls = []
184
178
        self.expecting_body = False
1019
1013
            client._calls)
1020
1014
 
1021
1015
 
 
1016
class TestTransportMkdir(tests.TestCase):
 
1017
 
 
1018
    def test_permissiondenied(self):
 
1019
        client = FakeClient()
 
1020
        client.add_error_response('PermissionDenied', 'remote path', 'extra')
 
1021
        transport = RemoteTransport('bzr://example.com/', medium=False,
 
1022
                                    _client=client)
 
1023
        exc = self.assertRaises(
 
1024
            errors.PermissionDenied, transport.mkdir, 'client path')
 
1025
        expected_error = errors.PermissionDenied('/client path', 'extra')
 
1026
        self.assertEqual(expected_error, exc)
 
1027
 
 
1028
 
1022
1029
class TestRemoteSSHTransportAuthentication(tests.TestCaseInTempDir):
1023
1030
 
1024
1031
    def test_defaults_to_none(self):
1123
1130
class TestRepositoryGetGraph(TestRemoteRepository):
1124
1131
 
1125
1132
    def test_get_graph(self):
1126
 
        # get_graph returns a graph with the repository as the
1127
 
        # parents_provider.
 
1133
        # get_graph returns a graph with a custom parents provider.
1128
1134
        transport_path = 'quack'
1129
1135
        repo, client = self.setup_fake_client_and_repository(transport_path)
1130
1136
        graph = repo.get_graph()
1131
 
        self.assertEqual(graph._parents_provider, repo)
 
1137
        self.assertNotEqual(graph._parents_provider, repo)
1132
1138
 
1133
1139
 
1134
1140
class TestRepositoryGetParentMap(TestRemoteRepository):
1450
1456
        src_repo.copy_content_into(dest_repo)
1451
1457
 
1452
1458
 
 
1459
class _StubRealPackRepository(object):
 
1460
 
 
1461
    def __init__(self, calls):
 
1462
        self._pack_collection = _StubPackCollection(calls)
 
1463
 
 
1464
 
 
1465
class _StubPackCollection(object):
 
1466
 
 
1467
    def __init__(self, calls):
 
1468
        self.calls = calls
 
1469
 
 
1470
    def autopack(self):
 
1471
        self.calls.append(('pack collection autopack',))
 
1472
 
 
1473
    def reload_pack_names(self):
 
1474
        self.calls.append(('pack collection reload_pack_names',))
 
1475
 
 
1476
    
 
1477
class TestRemotePackRepositoryAutoPack(TestRemoteRepository):
 
1478
    """Tests for RemoteRepository.autopack implementation."""
 
1479
 
 
1480
    def test_ok(self):
 
1481
        """When the server returns 'ok' and there's no _real_repository, then
 
1482
        nothing else happens: the autopack method is done.
 
1483
        """
 
1484
        transport_path = 'quack'
 
1485
        repo, client = self.setup_fake_client_and_repository(transport_path)
 
1486
        client.add_expected_call(
 
1487
            'PackRepository.autopack', ('quack/',), 'success', ('ok',))
 
1488
        repo.autopack()
 
1489
        client.finished_test()
 
1490
 
 
1491
    def test_ok_with_real_repo(self):
 
1492
        """When the server returns 'ok' and there is a _real_repository, then
 
1493
        the _real_repository's reload_pack_name's method will be called.
 
1494
        """
 
1495
        transport_path = 'quack'
 
1496
        repo, client = self.setup_fake_client_and_repository(transport_path)
 
1497
        client.add_expected_call(
 
1498
            'PackRepository.autopack', ('quack/',),
 
1499
            'success', ('ok',))
 
1500
        repo._real_repository = _StubRealPackRepository(client._calls)
 
1501
        repo.autopack()
 
1502
        self.assertEqual(
 
1503
            [('call', 'PackRepository.autopack', ('quack/',)),
 
1504
             ('pack collection reload_pack_names',)],
 
1505
            client._calls)
 
1506
        
 
1507
    def test_backwards_compatibility(self):
 
1508
        """If the server does not recognise the PackRepository.autopack verb,
 
1509
        fallback to the real_repository's implementation.
 
1510
        """
 
1511
        transport_path = 'quack'
 
1512
        repo, client = self.setup_fake_client_and_repository(transport_path)
 
1513
        client.add_unknown_method_response('PackRepository.autopack')
 
1514
        def stub_ensure_real():
 
1515
            client._calls.append(('_ensure_real',))
 
1516
            repo._real_repository = _StubRealPackRepository(client._calls)
 
1517
        repo._ensure_real = stub_ensure_real
 
1518
        repo.autopack()
 
1519
        self.assertEqual(
 
1520
            [('call', 'PackRepository.autopack', ('quack/',)),
 
1521
             ('_ensure_real',),
 
1522
             ('pack collection autopack',)],
 
1523
            client._calls)
 
1524
 
 
1525
 
1453
1526
class TestErrorTranslationBase(tests.TestCaseWithMemoryTransport):
1454
1527
    """Base class for unit tests for bzrlib.remote._translate_error."""
1455
1528
 
1483
1556
                **context)
1484
1557
        return translated_error
1485
1558
 
1486
 
    
 
1559
 
1487
1560
class TestErrorTranslationSuccess(TestErrorTranslationBase):
1488
1561
    """Unit tests for bzrlib.remote._translate_error.
1489
1562
    
1551
1624
        expected_error = errors.DivergedBranches(branch, other_branch)
1552
1625
        self.assertEqual(expected_error, translated_error)
1553
1626
 
 
1627
    def test_ReadError_no_args(self):
 
1628
        path = 'a path'
 
1629
        translated_error = self.translateTuple(('ReadError',), path=path)
 
1630
        expected_error = errors.ReadError(path)
 
1631
        self.assertEqual(expected_error, translated_error)
 
1632
 
 
1633
    def test_ReadError(self):
 
1634
        path = 'a path'
 
1635
        translated_error = self.translateTuple(('ReadError', path))
 
1636
        expected_error = errors.ReadError(path)
 
1637
        self.assertEqual(expected_error, translated_error)
 
1638
 
 
1639
    def test_PermissionDenied_no_args(self):
 
1640
        path = 'a path'
 
1641
        translated_error = self.translateTuple(('PermissionDenied',), path=path)
 
1642
        expected_error = errors.PermissionDenied(path)
 
1643
        self.assertEqual(expected_error, translated_error)
 
1644
 
 
1645
    def test_PermissionDenied_one_arg(self):
 
1646
        path = 'a path'
 
1647
        translated_error = self.translateTuple(('PermissionDenied', path))
 
1648
        expected_error = errors.PermissionDenied(path)
 
1649
        self.assertEqual(expected_error, translated_error)
 
1650
 
 
1651
    def test_PermissionDenied_one_arg_and_context(self):
 
1652
        """Given a choice between a path from the local context and a path on
 
1653
        the wire, _translate_error prefers the path from the local context.
 
1654
        """
 
1655
        local_path = 'local path'
 
1656
        remote_path = 'remote path'
 
1657
        translated_error = self.translateTuple(
 
1658
            ('PermissionDenied', remote_path), path=local_path)
 
1659
        expected_error = errors.PermissionDenied(local_path)
 
1660
        self.assertEqual(expected_error, translated_error)
 
1661
 
 
1662
    def test_PermissionDenied_two_args(self):
 
1663
        path = 'a path'
 
1664
        extra = 'a string with extra info'
 
1665
        translated_error = self.translateTuple(
 
1666
            ('PermissionDenied', path, extra))
 
1667
        expected_error = errors.PermissionDenied(path, extra)
 
1668
        self.assertEqual(expected_error, translated_error)
 
1669
 
1554
1670
 
1555
1671
class TestErrorTranslationRobustness(TestErrorTranslationBase):
1556
1672
    """Unit tests for bzrlib.remote._translate_error's robustness.
1589
1705
            self._get_log(keep_log_file=True),
1590
1706
            "Missing key 'branch' in context")
1591
1707
        
 
1708
    def test_path_missing(self):
 
1709
        """Some translations (PermissionDenied, ReadError) can determine the
 
1710
        'path' variable from either the wire or the local context.  If neither
 
1711
        has it, then an error is raised.
 
1712
        """
 
1713
        error_tuple = ('ReadError',)
 
1714
        server_error = errors.ErrorFromSmartServer(error_tuple)
 
1715
        translated_error = self.translateErrorFromSmartServer(server_error)
 
1716
        self.assertEqual(server_error, translated_error)
 
1717
        # In addition to re-raising ErrorFromSmartServer, some debug info has
 
1718
        # been muttered to the log file for developer to look at.
 
1719
        self.assertContainsRe(
 
1720
            self._get_log(keep_log_file=True), "Missing key 'path' in context")
 
1721
 
1592
1722
 
1593
1723
class TestStacking(tests.TestCaseWithTransport):
1594
1724
    """Tests for operations on stacked remote repositories.
1633
1763
                'message')
1634
1764
        finally:
1635
1765
            remote_repo.unlock()
 
1766
 
 
1767
    def prepare_stacked_remote_branch(self):
 
1768
        smart_server = server.SmartTCPServer_for_testing()
 
1769
        smart_server.setUp()
 
1770
        self.addCleanup(smart_server.tearDown)
 
1771
        tree1 = self.make_branch_and_tree('tree1')
 
1772
        tree1.commit('rev1', rev_id='rev1')
 
1773
        tree2 = self.make_branch_and_tree('tree2', format='1.6')
 
1774
        tree2.branch.set_stacked_on_url(tree1.branch.base)
 
1775
        branch2 = Branch.open(smart_server.get_url() + '/tree2')
 
1776
        branch2.lock_read()
 
1777
        self.addCleanup(branch2.unlock)
 
1778
        return branch2
 
1779
 
 
1780
    def test_stacked_get_parent_map(self):
 
1781
        # the public implementation of get_parent_map obeys stacking
 
1782
        branch = self.prepare_stacked_remote_branch()
 
1783
        repo = branch.repository
 
1784
        self.assertEqual(['rev1'], repo.get_parent_map(['rev1']).keys())
 
1785
 
 
1786
    def test_stacked__get_parent_map(self):
 
1787
        # the private variant of _get_parent_map ignores stacking
 
1788
        branch = self.prepare_stacked_remote_branch()
 
1789
        repo = branch.repository
 
1790
        self.assertEqual([], repo._get_parent_map(['rev1']).keys())
 
1791
 
 
1792
 
 
1793
class TestRemoteBranchEffort(tests.TestCaseWithTransport):
 
1794
 
 
1795
    def setUp(self):
 
1796
        super(TestRemoteBranchEffort, self).setUp()
 
1797
        # Create a smart server that publishes whatever the backing VFS server
 
1798
        # does.
 
1799
        self.smart_server = server.SmartTCPServer_for_testing()
 
1800
        self.smart_server.setUp(self.get_server())
 
1801
        self.addCleanup(self.smart_server.tearDown)
 
1802
        # Log all HPSS calls into self.hpss_calls.
 
1803
        _SmartClient.hooks.install_named_hook(
 
1804
            'call', self.capture_hpss_call, None)
 
1805
        self.hpss_calls = []
 
1806
 
 
1807
    def capture_hpss_call(self, params):
 
1808
        self.hpss_calls.append(params.method)
 
1809
 
 
1810
    def test_copy_content_into_avoids_revision_history(self):
 
1811
        local = self.make_branch('local')
 
1812
        remote_backing_tree = self.make_branch_and_tree('remote')
 
1813
        remote_backing_tree.commit("Commit.")
 
1814
        remote_branch_url = self.smart_server.get_url() + 'remote'
 
1815
        remote_branch = bzrdir.BzrDir.open(remote_branch_url).open_branch()
 
1816
        local.repository.fetch(remote_branch.repository)
 
1817
        self.hpss_calls = []
 
1818
        remote_branch.copy_content_into(local)
 
1819
        self.assertFalse('Branch.revision_history' in self.hpss_calls)