~bzr-pqm/bzr/bzr.dev

2018.18.12 by Martin Pool
small test cleanups
1
# Copyright (C) 2004, 2005, 2006, 2007 Canonical Ltd
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
2
#
907.1.48 by John Arbash Meinel
Updated LocalTransport by passing it through the transport_test suite, and got it to pass.
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.
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
7
#
907.1.48 by John Arbash Meinel
Updated LocalTransport by passing it through the transport_test suite, and got it to pass.
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.
1887.1.1 by Adeodato Simó
Do not separate paragraphs in the copyright statement with blank lines,
12
#
907.1.48 by John Arbash Meinel
Updated LocalTransport by passing it through the transport_test suite, and got it to pass.
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
1185.11.22 by John Arbash Meinel
Major refactoring of testtransport.
18
from cStringIO import StringIO
1442.1.44 by Robert Collins
Many transport related tweaks:
19
2018.18.12 by Martin Pool
small test cleanups
20
import bzrlib
2018.18.4 by Martin Pool
Change Transport.local_abspath to raise NotLocalUrl, and test.
21
from bzrlib import (
22
    errors,
2804.4.1 by Alexander Belchenko
some win32-specific fixes for selftest
23
    osutils,
2018.18.4 by Martin Pool
Change Transport.local_abspath to raise NotLocalUrl, and test.
24
    urlutils,
25
    )
2892.1.1 by Andrew Bennetts
Fix bug 146715: bzr+ssh:// and sftp:// should not assume port-not-specified means port 22
26
from bzrlib.errors import (DependencyNotPresent,
2379.2.1 by Robert Collins
Rewritten chroot transport that prevents accidental chroot escapes when
27
                           FileExists,
28
                           InvalidURLJoin,
29
                           NoSuchFile,
30
                           PathNotChild,
2052.6.1 by Robert Collins
``Transport.get`` has had its interface made more clear for ease of use.
31
                           ReadError,
1843.1.1 by John Arbash Meinel
Update get_transport to raise a nicer error which includes dependency info
32
                           UnsupportedProtocol,
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
33
                           )
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
34
from bzrlib.tests import TestCase, TestCaseInTempDir
2745.5.3 by Robert Collins
* Move transport logging into a new transport class
35
from bzrlib.transport import (_clear_protocol_handlers,
36
                              _CoalescedOffset,
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
37
                              ConnectedTransport,
1864.5.9 by John Arbash Meinel
Switch to returning an object to make the api more understandable.
38
                              _get_protocol_handlers,
2241.2.2 by ghigo
Create the TransportList class
39
                              _set_protocol_handlers,
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
40
                              _get_transport_modules,
1534.4.9 by Robert Collins
Add a readonly decorator for transports.
41
                              get_transport,
2052.6.1 by Robert Collins
``Transport.get`` has had its interface made more clear for ease of use.
42
                              LateReadError,
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
43
                              register_lazy_transport,
2241.2.2 by ghigo
Create the TransportList class
44
                              register_transport_proto,
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
45
                              Transport,
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
46
                              )
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
47
from bzrlib.transport.chroot import ChrootServer
1540.3.6 by Martin Pool
[merge] update from bzr.dev
48
from bzrlib.transport.memory import MemoryTransport
2245.6.1 by Alexander Belchenko
win32 UNC path: recursive cloning UNC path to root stops on //HOST, not on //
49
from bzrlib.transport.local import (LocalTransport,
2245.6.2 by Alexander Belchenko
Fix name of emulated Win32LocalTransport as Robert suggested.
50
                                    EmulatedWin32LocalTransport)
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
51
52
53
# TODO: Should possibly split transport-specific tests into their own files.
1185.58.2 by John Arbash Meinel
Added mode to the appropriate transport functions, and tests to make sure they work.
54
55
1185.58.3 by John Arbash Meinel
code cleanup
56
class TestTransport(TestCase):
57
    """Test the non transport-concrete class functionality."""
58
2241.3.1 by ghigo
uncomment test test__get_set_protocol_handlers
59
    def test__get_set_protocol_handlers(self):
60
        handlers = _get_protocol_handlers()
61
        self.assertNotEqual([], handlers.keys( ))
62
        try:
63
            _clear_protocol_handlers()
64
            self.assertEqual([], _get_protocol_handlers().keys())
65
        finally:
66
            _set_protocol_handlers(handlers)
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
67
68
    def test_get_transport_modules(self):
69
        handlers = _get_protocol_handlers()
2745.5.3 by Robert Collins
* Move transport logging into a new transport class
70
        # don't pollute the current handlers
71
        _clear_protocol_handlers()
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
72
        class SampleHandler(object):
73
            """I exist, isnt that enough?"""
74
        try:
2241.2.2 by ghigo
Create the TransportList class
75
            _clear_protocol_handlers()
76
            register_transport_proto('foo')
3004.2.1 by Vincent Ladeuil
Fix 150860 by leaving port as user specified it.
77
            register_lazy_transport('foo', 'bzrlib.tests.test_transport',
78
                                    'TestTransport.SampleHandler')
2241.2.2 by ghigo
Create the TransportList class
79
            register_transport_proto('bar')
3004.2.1 by Vincent Ladeuil
Fix 150860 by leaving port as user specified it.
80
            register_lazy_transport('bar', 'bzrlib.tests.test_transport',
81
                                    'TestTransport.SampleHandler')
82
            self.assertEqual([SampleHandler.__module__,
83
                              'bzrlib.transport.chroot'],
1530.1.11 by Robert Collins
Push the transport permutations list into each transport module allowing for automatic testing of new modules that are registered as transports.
84
                             _get_transport_modules())
85
        finally:
86
            _set_protocol_handlers(handlers)
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
87
88
    def test_transport_dependency(self):
89
        """Transport with missing dependency causes no error"""
90
        saved_handlers = _get_protocol_handlers()
2745.5.3 by Robert Collins
* Move transport logging into a new transport class
91
        # don't pollute the current handlers
92
        _clear_protocol_handlers()
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
93
        try:
2241.2.2 by ghigo
Create the TransportList class
94
            register_transport_proto('foo')
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
95
            register_lazy_transport('foo', 'bzrlib.tests.test_transport',
96
                    'BadTransportHandler')
1843.1.1 by John Arbash Meinel
Update get_transport to raise a nicer error which includes dependency info
97
            try:
98
                get_transport('foo://fooserver/foo')
99
            except UnsupportedProtocol, e:
100
                e_str = str(e)
101
                self.assertEquals('Unsupported protocol'
102
                                  ' for url "foo://fooserver/foo":'
103
                                  ' Unable to import library "some_lib":'
104
                                  ' testing missing dependency', str(e))
105
            else:
106
                self.fail('Did not raise UnsupportedProtocol')
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
107
        finally:
1540.3.10 by Martin Pool
[broken] keep hooking pycurl into test framework
108
            # restore original values
109
            _set_protocol_handlers(saved_handlers)
110
            
111
    def test_transport_fallback(self):
112
        """Transport with missing dependency causes no error"""
113
        saved_handlers = _get_protocol_handlers()
114
        try:
2241.2.2 by ghigo
Create the TransportList class
115
            _clear_protocol_handlers()
116
            register_transport_proto('foo')
1540.3.10 by Martin Pool
[broken] keep hooking pycurl into test framework
117
            register_lazy_transport('foo', 'bzrlib.tests.test_transport',
118
                    'BackupTransportHandler')
119
            register_lazy_transport('foo', 'bzrlib.tests.test_transport',
120
                    'BadTransportHandler')
121
            t = get_transport('foo://fooserver/foo')
122
            self.assertTrue(isinstance(t, BackupTransportHandler))
123
        finally:
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
124
            _set_protocol_handlers(saved_handlers)
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
125
2052.6.1 by Robert Collins
``Transport.get`` has had its interface made more clear for ease of use.
126
    def test_LateReadError(self):
127
        """The LateReadError helper should raise on read()."""
128
        a_file = LateReadError('a path')
129
        try:
130
            a_file.read()
131
        except ReadError, error:
132
            self.assertEqual('a path', error.path)
133
        self.assertRaises(ReadError, a_file.read, 40)
134
        a_file.close()
135
1996.3.20 by John Arbash Meinel
[merge] bzr.dev 2063
136
    def test__combine_paths(self):
137
        t = Transport('/')
138
        self.assertEqual('/home/sarah/project/foo',
139
                         t._combine_paths('/home/sarah', 'project/foo'))
140
        self.assertEqual('/etc',
141
                         t._combine_paths('/home/sarah', '../../etc'))
2070.3.2 by Andrew Bennetts
Merge from bzr.dev
142
        self.assertEqual('/etc',
143
                         t._combine_paths('/home/sarah', '../../../etc'))
144
        self.assertEqual('/etc',
145
                         t._combine_paths('/home/sarah', '/etc'))
1996.3.20 by John Arbash Meinel
[merge] bzr.dev 2063
146
2018.18.4 by Martin Pool
Change Transport.local_abspath to raise NotLocalUrl, and test.
147
    def test_local_abspath_non_local_transport(self):
148
        # the base implementation should throw
149
        t = MemoryTransport()
150
        e = self.assertRaises(errors.NotLocalUrl, t.local_abspath, 't')
151
        self.assertEqual('memory:///t is not a local path.', str(e))
152
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
153
154
class TestCoalesceOffsets(TestCase):
3059.2.17 by Vincent Ladeuil
Limit GET requests by body size instead of number of ranges.
155
156
    def check(self, expected, offsets, limit=0, max_size=0, fudge=0):
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
157
        coalesce = Transport._coalesce_offsets
1864.5.9 by John Arbash Meinel
Switch to returning an object to make the api more understandable.
158
        exp = [_CoalescedOffset(*x) for x in expected]
3059.2.17 by Vincent Ladeuil
Limit GET requests by body size instead of number of ranges.
159
        out = list(coalesce(offsets, limit=limit, fudge_factor=fudge,
160
                            max_size=max_size))
1864.5.9 by John Arbash Meinel
Switch to returning an object to make the api more understandable.
161
        self.assertEqual(exp, out)
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
162
163
    def test_coalesce_empty(self):
164
        self.check([], [])
165
166
    def test_coalesce_simple(self):
167
        self.check([(0, 10, [(0, 10)])], [(0, 10)])
168
169
    def test_coalesce_unrelated(self):
170
        self.check([(0, 10, [(0, 10)]),
171
                    (20, 10, [(0, 10)]),
172
                   ], [(0, 10), (20, 10)])
3059.2.17 by Vincent Ladeuil
Limit GET requests by body size instead of number of ranges.
173
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
174
    def test_coalesce_unsorted(self):
175
        self.check([(20, 10, [(0, 10)]),
176
                    (0, 10, [(0, 10)]),
177
                   ], [(20, 10), (0, 10)])
178
179
    def test_coalesce_nearby(self):
180
        self.check([(0, 20, [(0, 10), (10, 10)])],
181
                   [(0, 10), (10, 10)])
182
183
    def test_coalesce_overlapped(self):
3686.1.9 by John Arbash Meinel
Overlapping ranges are not allowed anymore.
184
        self.assertRaises(ValueError,
185
            self.check, [(0, 15, [(0, 10), (5, 10)])],
186
                        [(0, 10), (5, 10)])
1864.5.1 by John Arbash Meinel
Change the readv combining algorithm for one that is easier to test.
187
188
    def test_coalesce_limit(self):
189
        self.check([(10, 50, [(0, 10), (10, 10), (20, 10),
190
                              (30, 10), (40, 10)]),
191
                    (60, 50, [(0, 10), (10, 10), (20, 10),
192
                              (30, 10), (40, 10)]),
193
                   ], [(10, 10), (20, 10), (30, 10), (40, 10),
194
                       (50, 10), (60, 10), (70, 10), (80, 10),
195
                       (90, 10), (100, 10)],
196
                    limit=5)
197
198
    def test_coalesce_no_limit(self):
199
        self.check([(10, 100, [(0, 10), (10, 10), (20, 10),
200
                               (30, 10), (40, 10), (50, 10),
201
                               (60, 10), (70, 10), (80, 10),
202
                               (90, 10)]),
203
                   ], [(10, 10), (20, 10), (30, 10), (40, 10),
204
                       (50, 10), (60, 10), (70, 10), (80, 10),
205
                       (90, 10), (100, 10)])
206
1864.5.3 by John Arbash Meinel
Allow collapsing ranges even if they are just 'close'
207
    def test_coalesce_fudge(self):
208
        self.check([(10, 30, [(0, 10), (20, 10)]),
209
                    (100, 10, [(0, 10),]),
210
                   ], [(10, 10), (30, 10), (100, 10)],
211
                   fudge=10
212
                  )
3059.2.17 by Vincent Ladeuil
Limit GET requests by body size instead of number of ranges.
213
    def test_coalesce_max_size(self):
214
        self.check([(10, 20, [(0, 10), (10, 10)]),
215
                    (30, 50, [(0, 50)]),
216
                    # If one range is above max_size, it gets its own coalesced
217
                    # offset
218
                    (100, 80, [(0, 80),]),],
219
                   [(10, 10), (20, 10), (30, 50), (100, 80)],
220
                   max_size=50
221
                  )
222
223
    def test_coalesce_no_max_size(self):
224
        self.check([(10, 170, [(0, 10), (10, 10), (20, 50), (70, 100)]),],
225
                   [(10, 10), (20, 10), (30, 50), (80, 100)],
226
                  )
1864.5.3 by John Arbash Meinel
Allow collapsing ranges even if they are just 'close'
227
1540.3.3 by Martin Pool
Review updates of pycurl transport
228
1442.1.44 by Robert Collins
Many transport related tweaks:
229
class TestMemoryTransport(TestCase):
230
231
    def test_get_transport(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
232
        MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
233
234
    def test_clone(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
235
        transport = MemoryTransport()
236
        self.assertTrue(isinstance(transport, MemoryTransport))
1910.15.3 by Andrew Bennetts
Make memory transport pass tests.
237
        self.assertEqual("memory:///", transport.clone("/").base)
1442.1.44 by Robert Collins
Many transport related tweaks:
238
239
    def test_abspath(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
240
        transport = MemoryTransport()
1685.1.42 by John Arbash Meinel
A couple more fixes to make sure memory:/// works correctly.
241
        self.assertEqual("memory:///relpath", transport.abspath('relpath'))
1442.1.44 by Robert Collins
Many transport related tweaks:
242
1910.15.1 by Andrew Bennetts
More tests for abspath and clone behaviour
243
    def test_abspath_of_root(self):
244
        transport = MemoryTransport()
245
        self.assertEqual("memory:///", transport.base)
246
        self.assertEqual("memory:///", transport.abspath('/'))
247
2070.3.1 by Andrew Bennetts
Fix memory_transport.abspath('/foo')
248
    def test_abspath_of_relpath_starting_at_root(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
249
        transport = MemoryTransport()
2070.3.1 by Andrew Bennetts
Fix memory_transport.abspath('/foo')
250
        self.assertEqual("memory:///foo", transport.abspath('/foo'))
1442.1.44 by Robert Collins
Many transport related tweaks:
251
252
    def test_append_and_get(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
253
        transport = MemoryTransport()
1955.3.16 by John Arbash Meinel
Switch over to Transport.append_bytes or append_files
254
        transport.append_bytes('path', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
255
        self.assertEqual(transport.get('path').read(), 'content')
1955.3.16 by John Arbash Meinel
Switch over to Transport.append_bytes or append_files
256
        transport.append_file('path', StringIO('content'))
1442.1.44 by Robert Collins
Many transport related tweaks:
257
        self.assertEqual(transport.get('path').read(), 'contentcontent')
258
259
    def test_put_and_get(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
260
        transport = MemoryTransport()
1955.3.7 by John Arbash Meinel
Fix the deprecation warnings in the transport tests themselves
261
        transport.put_file('path', StringIO('content'))
1442.1.44 by Robert Collins
Many transport related tweaks:
262
        self.assertEqual(transport.get('path').read(), 'content')
1955.3.7 by John Arbash Meinel
Fix the deprecation warnings in the transport tests themselves
263
        transport.put_bytes('path', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
264
        self.assertEqual(transport.get('path').read(), 'content')
265
266
    def test_append_without_dir_fails(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
267
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
268
        self.assertRaises(NoSuchFile,
1955.3.16 by John Arbash Meinel
Switch over to Transport.append_bytes or append_files
269
                          transport.append_bytes, 'dir/path', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
270
271
    def test_put_without_dir_fails(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
272
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
273
        self.assertRaises(NoSuchFile,
1955.3.7 by John Arbash Meinel
Fix the deprecation warnings in the transport tests themselves
274
                          transport.put_file, 'dir/path', StringIO('content'))
1442.1.44 by Robert Collins
Many transport related tweaks:
275
276
    def test_get_missing(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
277
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
278
        self.assertRaises(NoSuchFile, transport.get, 'foo')
279
280
    def test_has_missing(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
281
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
282
        self.assertEquals(False, transport.has('foo'))
283
284
    def test_has_present(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
285
        transport = MemoryTransport()
1955.3.16 by John Arbash Meinel
Switch over to Transport.append_bytes or append_files
286
        transport.append_bytes('foo', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
287
        self.assertEquals(True, transport.has('foo'))
288
2120.3.1 by John Arbash Meinel
Fix MemoryTransport.list_dir() implementation, and update tests
289
    def test_list_dir(self):
290
        transport = MemoryTransport()
291
        transport.put_bytes('foo', 'content')
292
        transport.mkdir('dir')
293
        transport.put_bytes('dir/subfoo', 'content')
294
        transport.put_bytes('dirlike', 'content')
295
296
        self.assertEquals(['dir', 'dirlike', 'foo'], sorted(transport.list_dir('.')))
297
        self.assertEquals(['subfoo'], sorted(transport.list_dir('dir')))
298
1442.1.44 by Robert Collins
Many transport related tweaks:
299
    def test_mkdir(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
300
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
301
        transport.mkdir('dir')
1955.3.16 by John Arbash Meinel
Switch over to Transport.append_bytes or append_files
302
        transport.append_bytes('dir/path', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
303
        self.assertEqual(transport.get('dir/path').read(), 'content')
304
305
    def test_mkdir_missing_parent(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
306
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
307
        self.assertRaises(NoSuchFile,
308
                          transport.mkdir, 'dir/dir')
309
310
    def test_mkdir_twice(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
311
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
312
        transport.mkdir('dir')
313
        self.assertRaises(FileExists, transport.mkdir, 'dir')
1530.1.5 by Robert Collins
Reinstate Memory parameter tests.
314
315
    def test_parameters(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
316
        transport = MemoryTransport()
1530.1.5 by Robert Collins
Reinstate Memory parameter tests.
317
        self.assertEqual(True, transport.listable())
318
        self.assertEqual(False, transport.is_readonly())
1442.1.44 by Robert Collins
Many transport related tweaks:
319
320
    def test_iter_files_recursive(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
321
        transport = MemoryTransport()
1442.1.44 by Robert Collins
Many transport related tweaks:
322
        transport.mkdir('dir')
1955.3.7 by John Arbash Meinel
Fix the deprecation warnings in the transport tests themselves
323
        transport.put_bytes('dir/foo', 'content')
324
        transport.put_bytes('dir/bar', 'content')
325
        transport.put_bytes('bar', 'content')
1442.1.44 by Robert Collins
Many transport related tweaks:
326
        paths = set(transport.iter_files_recursive())
327
        self.assertEqual(set(['dir/foo', 'dir/bar', 'bar']), paths)
328
329
    def test_stat(self):
1540.3.6 by Martin Pool
[merge] update from bzr.dev
330
        transport = MemoryTransport()
1955.3.7 by John Arbash Meinel
Fix the deprecation warnings in the transport tests themselves
331
        transport.put_bytes('foo', 'content')
332
        transport.put_bytes('bar', 'phowar')
1442.1.44 by Robert Collins
Many transport related tweaks:
333
        self.assertEqual(7, transport.stat('foo').st_size)
334
        self.assertEqual(6, transport.stat('bar').st_size)
1185.35.31 by Aaron Bentley
Throw ConnectionError instead of NoSuchFile except when we get a 404
335
2070.5.1 by Andrew Bennetts
Add ChrootTransportDecorator.
336
337
class ChrootDecoratorTransportTest(TestCase):
338
    """Chroot decoration specific tests."""
339
2018.5.54 by Andrew Bennetts
Fix ChrootTransportDecorator's abspath method to be consistent with its clone
340
    def test_abspath(self):
341
        # The abspath is always relative to the chroot_url.
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
342
        server = ChrootServer(get_transport('memory:///foo/bar/'))
343
        server.setUp()
344
        transport = get_transport(server.get_url())
345
        self.assertEqual(server.get_url(), transport.abspath('/'))
2018.5.54 by Andrew Bennetts
Fix ChrootTransportDecorator's abspath method to be consistent with its clone
346
347
        subdir_transport = transport.clone('subdir')
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
348
        self.assertEqual(server.get_url(), subdir_transport.abspath('/'))
349
        server.tearDown()
2379.2.1 by Robert Collins
Rewritten chroot transport that prevents accidental chroot escapes when
350
351
    def test_clone(self):
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
352
        server = ChrootServer(get_transport('memory:///foo/bar/'))
353
        server.setUp()
354
        transport = get_transport(server.get_url())
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
355
        # relpath from root and root path are the same
356
        relpath_cloned = transport.clone('foo')
357
        abspath_cloned = transport.clone('/foo')
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
358
        self.assertEqual(server, relpath_cloned.server)
359
        self.assertEqual(server, abspath_cloned.server)
360
        server.tearDown()
2018.5.46 by Andrew Bennetts
Fix ChrootTransportDecorator's clone to pass less surprising offsets to the decorated transport's clone.
361
    
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
362
    def test_chroot_url_preserves_chroot(self):
363
        """Calling get_transport on a chroot transport's base should produce a
364
        transport with exactly the same behaviour as the original chroot
365
        transport.
366
367
        This is so that it is not possible to escape a chroot by doing::
368
            url = chroot_transport.base
369
            parent_url = urlutils.join(url, '..')
370
            new_transport = get_transport(parent_url)
371
        """
372
        server = ChrootServer(get_transport('memory:///path/subpath'))
373
        server.setUp()
374
        transport = get_transport(server.get_url())
375
        new_transport = get_transport(transport.base)
376
        self.assertEqual(transport.server, new_transport.server)
377
        self.assertEqual(transport.base, new_transport.base)
378
        server.tearDown()
379
        
380
    def test_urljoin_preserves_chroot(self):
381
        """Using urlutils.join(url, '..') on a chroot URL should not produce a
382
        URL that escapes the intended chroot.
383
384
        This is so that it is not possible to escape a chroot by doing::
385
            url = chroot_transport.base
386
            parent_url = urlutils.join(url, '..')
387
            new_transport = get_transport(parent_url)
388
        """
389
        server = ChrootServer(get_transport('memory:///path/'))
390
        server.setUp()
391
        transport = get_transport(server.get_url())
392
        self.assertRaises(
393
            InvalidURLJoin, urlutils.join, transport.base, '..')
394
        server.tearDown()
395
396
397
class ChrootServerTest(TestCase):
398
399
    def test_construct(self):
400
        backing_transport = MemoryTransport()
401
        server = ChrootServer(backing_transport)
402
        self.assertEqual(backing_transport, server.backing_transport)
403
404
    def test_setUp(self):
405
        backing_transport = MemoryTransport()
406
        server = ChrootServer(backing_transport)
407
        server.setUp()
2241.3.5 by ghigo
update to the latest bzr.dev
408
        self.assertTrue(server.scheme in _get_protocol_handlers().keys())
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
409
410
    def test_tearDown(self):
411
        backing_transport = MemoryTransport()
412
        server = ChrootServer(backing_transport)
413
        server.setUp()
414
        server.tearDown()
2241.3.5 by ghigo
update to the latest bzr.dev
415
        self.assertFalse(server.scheme in _get_protocol_handlers().keys())
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
416
417
    def test_get_url(self):
418
        backing_transport = MemoryTransport()
419
        server = ChrootServer(backing_transport)
420
        server.setUp()
421
        self.assertEqual('chroot-%d:///' % id(server), server.get_url())
422
        server.tearDown()
2018.5.53 by Andrew Bennetts
Small fix to urlutils.joinpath that was causing a misbehaviour in
423
2156.2.1 by v.ladeuil+lp at free
Make the tests windows compatible.
424
1534.4.9 by Robert Collins
Add a readonly decorator for transports.
425
class ReadonlyDecoratorTransportTest(TestCase):
426
    """Readonly decoration specific tests."""
427
428
    def test_local_parameters(self):
429
        import bzrlib.transport.readonly as readonly
430
        # connect to . in readonly mode
431
        transport = readonly.ReadonlyTransportDecorator('readonly+.')
432
        self.assertEqual(True, transport.listable())
433
        self.assertEqual(True, transport.is_readonly())
434
435
    def test_http_parameters(self):
3102.1.1 by Vincent Ladeuil
Rename bzrlib/test/HTTPTestUtils.py to bzrlib/tests/http_utils.py and fix
436
        from bzrlib.tests.http_server import HttpServer
1534.4.9 by Robert Collins
Add a readonly decorator for transports.
437
        import bzrlib.transport.readonly as readonly
3102.1.1 by Vincent Ladeuil
Rename bzrlib/test/HTTPTestUtils.py to bzrlib/tests/http_utils.py and fix
438
        # connect to '.' via http which is not listable
1534.4.9 by Robert Collins
Add a readonly decorator for transports.
439
        server = HttpServer()
440
        server.setUp()
441
        try:
442
            transport = get_transport('readonly+' + server.get_url())
443
            self.failUnless(isinstance(transport,
444
                                       readonly.ReadonlyTransportDecorator))
445
            self.assertEqual(False, transport.listable())
446
            self.assertEqual(True, transport.is_readonly())
447
        finally:
448
            server.tearDown()
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
449
450
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
451
class FakeNFSDecoratorTests(TestCaseInTempDir):
452
    """NFS decorator specific tests."""
453
454
    def get_nfs_transport(self, url):
455
        import bzrlib.transport.fakenfs as fakenfs
456
        # connect to url with nfs decoration
457
        return fakenfs.FakeNFSTransportDecorator('fakenfs+' + url)
458
459
    def test_local_parameters(self):
2701.1.1 by Martin Pool
Remove Transport.should_cache.
460
        # the listable and is_readonly parameters
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
461
        # are not changed by the fakenfs decorator
462
        transport = self.get_nfs_transport('.')
463
        self.assertEqual(True, transport.listable())
464
        self.assertEqual(False, transport.is_readonly())
465
466
    def test_http_parameters(self):
2701.1.1 by Martin Pool
Remove Transport.should_cache.
467
        # the listable and is_readonly parameters
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
468
        # are not changed by the fakenfs decorator
3102.1.1 by Vincent Ladeuil
Rename bzrlib/test/HTTPTestUtils.py to bzrlib/tests/http_utils.py and fix
469
        from bzrlib.tests.http_server import HttpServer
470
        # connect to '.' via http which is not listable
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
471
        server = HttpServer()
472
        server.setUp()
473
        try:
474
            transport = self.get_nfs_transport(server.get_url())
475
            self.assertIsInstance(
476
                transport, bzrlib.transport.fakenfs.FakeNFSTransportDecorator)
477
            self.assertEqual(False, transport.listable())
478
            self.assertEqual(True, transport.is_readonly())
479
        finally:
480
            server.tearDown()
481
482
    def test_fakenfs_server_default(self):
483
        # a FakeNFSServer() should bring up a local relpath server for itself
484
        import bzrlib.transport.fakenfs as fakenfs
485
        server = fakenfs.FakeNFSServer()
486
        server.setUp()
487
        try:
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
488
            # the url should be decorated appropriately
1951.2.3 by Martin Pool
Localtransport cleanup review (john)
489
            self.assertStartsWith(server.get_url(), 'fakenfs+')
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
490
            # and we should be able to get a transport for it
491
            transport = get_transport(server.get_url())
492
            # which must be a FakeNFSTransportDecorator instance.
493
            self.assertIsInstance(
494
                transport, fakenfs.FakeNFSTransportDecorator)
495
        finally:
496
            server.tearDown()
497
498
    def test_fakenfs_rename_semantics(self):
499
        # a FakeNFS transport must mangle the way rename errors occur to
500
        # look like NFS problems.
501
        transport = self.get_nfs_transport('.')
502
        self.build_tree(['from/', 'from/foo', 'to/', 'to/bar'],
503
                        transport=transport)
2018.18.12 by Martin Pool
small test cleanups
504
        self.assertRaises(errors.ResourceBusy,
1558.10.2 by Robert Collins
Refactor the FakeNFS support into a TransportDecorator.
505
                          transport.rename, 'from', 'to')
506
507
1608.2.4 by Martin Pool
[broken] Add FakeFVATTransport
508
class FakeVFATDecoratorTests(TestCaseInTempDir):
509
    """Tests for simulation of VFAT restrictions"""
510
511
    def get_vfat_transport(self, url):
512
        """Return vfat-backed transport for test directory"""
513
        from bzrlib.transport.fakevfat import FakeVFATTransportDecorator
514
        return FakeVFATTransportDecorator('vfat+' + url)
515
516
    def test_transport_creation(self):
517
        from bzrlib.transport.fakevfat import FakeVFATTransportDecorator
518
        transport = self.get_vfat_transport('.')
519
        self.assertIsInstance(transport, FakeVFATTransportDecorator)
520
521
    def test_transport_mkdir(self):
522
        transport = self.get_vfat_transport('.')
523
        transport.mkdir('HELLO')
524
        self.assertTrue(transport.has('hello'))
525
        self.assertTrue(transport.has('Hello'))
526
1608.2.11 by Martin Pool
(FakeVFAT) add test for detection of invalid characters
527
    def test_forbidden_chars(self):
528
        transport = self.get_vfat_transport('.')
529
        self.assertRaises(ValueError, transport.has, "<NU>")
530
531
1540.3.8 by Martin Pool
Some support for falling back between transport implementations.
532
class BadTransportHandler(Transport):
533
    def __init__(self, base_url):
534
        raise DependencyNotPresent('some_lib', 'testing missing dependency')
535
536
537
class BackupTransportHandler(Transport):
538
    """Test transport that works as a backup for the BadTransportHandler"""
1540.3.10 by Martin Pool
[broken] keep hooking pycurl into test framework
539
    pass
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
540
541
542
class TestTransportImplementation(TestCaseInTempDir):
543
    """Implementation verification for transports.
544
    
545
    To verify a transport we need a server factory, which is a callable
546
    that accepts no parameters and returns an implementation of
547
    bzrlib.transport.Server.
548
    
549
    That Server is then used to construct transport instances and test
550
    the transport via loopback activity.
551
552
    Currently this assumes that the Transport object is connected to the 
553
    current working directory.  So that whatever is done 
554
    through the transport, should show up in the working 
555
    directory, and vice-versa. This is a bug, because its possible to have
556
    URL schemes which provide access to something that may not be 
557
    result in storage on the local disk, i.e. due to file system limits, or 
558
    due to it being a database or some other non-filesystem tool.
559
560
    This also tests to make sure that the functions work with both
561
    generators and lists (assuming iter(list) is effectively a generator)
562
    """
563
    
564
    def setUp(self):
565
        super(TestTransportImplementation, self).setUp()
566
        self._server = self.transport_server()
567
        self._server.setUp()
2018.5.104 by Andrew Bennetts
Completely rework chrooted transports.
568
        self.addCleanup(self._server.tearDown)
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
569
2520.3.1 by Vincent Ladeuil
Fix 110448 by adding a relpath parameter to get_transport.
570
    def get_transport(self, relpath=None):
571
        """Return a connected transport to the local directory.
572
573
        :param relpath: a path relative to the base url.
574
        """
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
575
        base_url = self._server.get_url()
2520.3.1 by Vincent Ladeuil
Fix 110448 by adding a relpath parameter to get_transport.
576
        url = self._adjust_url(base_url, relpath)
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
577
        # try getting the transport via the regular interface:
2520.3.1 by Vincent Ladeuil
Fix 110448 by adding a relpath parameter to get_transport.
578
        t = get_transport(url)
2485.8.39 by Vincent Ladeuil
Add tests around connection reuse.
579
        # vila--20070607 if the following are commented out the test suite
580
        # still pass. Is this really still needed or was it a forgotten
581
        # temporary fix ?
1986.2.5 by Robert Collins
Unbreak transport tests.
582
        if not isinstance(t, self.transport_class):
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
583
            # we did not get the correct transport class type. Override the
584
            # regular connection behaviour by direct construction.
2520.3.1 by Vincent Ladeuil
Fix 110448 by adding a relpath parameter to get_transport.
585
            t = self.transport_class(url)
1871.1.2 by Robert Collins
Reduce code duplication in transport-parameterised tests.
586
        return t
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
587
588
589
class TestLocalTransports(TestCase):
590
591
    def test_get_transport_from_abspath(self):
2804.4.1 by Alexander Belchenko
some win32-specific fixes for selftest
592
        here = osutils.abspath('.')
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
593
        t = get_transport(here)
594
        self.assertIsInstance(t, LocalTransport)
595
        self.assertEquals(t.base, urlutils.local_path_to_url(here) + '/')
596
597
    def test_get_transport_from_relpath(self):
2804.4.1 by Alexander Belchenko
some win32-specific fixes for selftest
598
        here = osutils.abspath('.')
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
599
        t = get_transport('.')
600
        self.assertIsInstance(t, LocalTransport)
1951.2.3 by Martin Pool
Localtransport cleanup review (john)
601
        self.assertEquals(t.base, urlutils.local_path_to_url('.') + '/')
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
602
603
    def test_get_transport_from_local_url(self):
2804.4.1 by Alexander Belchenko
some win32-specific fixes for selftest
604
        here = osutils.abspath('.')
1951.2.1 by Martin Pool
Change to using LocalURLServer for testing.
605
        here_url = urlutils.local_path_to_url(here) + '/'
606
        t = get_transport(here_url)
607
        self.assertIsInstance(t, LocalTransport)
608
        self.assertEquals(t.base, here_url)
2245.6.1 by Alexander Belchenko
win32 UNC path: recursive cloning UNC path to root stops on //HOST, not on //
609
2018.18.4 by Martin Pool
Change Transport.local_abspath to raise NotLocalUrl, and test.
610
    def test_local_abspath(self):
2804.4.1 by Alexander Belchenko
some win32-specific fixes for selftest
611
        here = osutils.abspath('.')
2018.18.4 by Martin Pool
Change Transport.local_abspath to raise NotLocalUrl, and test.
612
        t = get_transport(here)
613
        self.assertEquals(t.local_abspath(''), here)
614
2245.6.1 by Alexander Belchenko
win32 UNC path: recursive cloning UNC path to root stops on //HOST, not on //
615
616
class TestWin32LocalTransport(TestCase):
617
618
    def test_unc_clone_to_root(self):
619
        # Win32 UNC path like \\HOST\path
620
        # clone to root should stop at least at \\HOST part
621
        # not on \\
2245.6.2 by Alexander Belchenko
Fix name of emulated Win32LocalTransport as Robert suggested.
622
        t = EmulatedWin32LocalTransport('file://HOST/path/to/some/dir/')
2245.6.1 by Alexander Belchenko
win32 UNC path: recursive cloning UNC path to root stops on //HOST, not on //
623
        for i in xrange(4):
624
            t = t.clone('..')
625
        self.assertEquals(t.base, 'file://HOST/')
626
        # make sure we reach the root
627
        t = t.clone('..')
628
        self.assertEquals(t.base, 'file://HOST/')
2477.1.7 by Martin Pool
test_transport must provide get_test_permutations
629
2485.8.61 by Vincent Ladeuil
From review comments, use a private scheme for testing.
630
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
631
class TestConnectedTransport(TestCase):
632
    """Tests for connected to remote server transports"""
633
634
    def test_parse_url(self):
2892.1.1 by Andrew Bennetts
Fix bug 146715: bzr+ssh:// and sftp:// should not assume port-not-specified means port 22
635
        t = ConnectedTransport('http://simple.example.com/home/source')
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
636
        self.assertEquals(t._host, 'simple.example.com')
3004.2.1 by Vincent Ladeuil
Fix 150860 by leaving port as user specified it.
637
        self.assertEquals(t._port, None)
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
638
        self.assertEquals(t._path, '/home/source/')
639
        self.failUnless(t._user is None)
640
        self.failUnless(t._password is None)
641
2892.1.1 by Andrew Bennetts
Fix bug 146715: bzr+ssh:// and sftp:// should not assume port-not-specified means port 22
642
        self.assertEquals(t.base, 'http://simple.example.com/home/source/')
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
643
3498.2.1 by Neil Martinsen-Burrell
Fix bug 228058: user names with @ signs should work
644
    def test_parse_url_with_at_in_user(self):
645
        # Bug 228058
646
        t = ConnectedTransport('ftp://user@host.com@www.host.com/')
647
        self.assertEquals(t._user, 'user@host.com')
648
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
649
    def test_parse_quoted_url(self):
650
        t = ConnectedTransport('http://ro%62ey:h%40t@ex%41mple.com:2222/path')
651
        self.assertEquals(t._host, 'exAmple.com')
652
        self.assertEquals(t._port, 2222)
653
        self.assertEquals(t._user, 'robey')
654
        self.assertEquals(t._password, 'h@t')
655
        self.assertEquals(t._path, '/path/')
656
657
        # Base should not keep track of the password
658
        self.assertEquals(t.base, 'http://robey@exAmple.com:2222/path/')
659
660
    def test_parse_invalid_url(self):
661
        self.assertRaises(errors.InvalidURL,
662
                          ConnectedTransport,
663
                          'sftp://lily.org:~janneke/public/bzr/gub')
664
665
    def test_relpath(self):
666
        t = ConnectedTransport('sftp://user@host.com/abs/path')
667
668
        self.assertEquals(t.relpath('sftp://user@host.com/abs/path/sub'), 'sub')
669
        self.assertRaises(errors.PathNotChild, t.relpath,
670
                          'http://user@host.com/abs/path/sub')
671
        self.assertRaises(errors.PathNotChild, t.relpath,
672
                          'sftp://user2@host.com/abs/path/sub')
673
        self.assertRaises(errors.PathNotChild, t.relpath,
674
                          'sftp://user@otherhost.com/abs/path/sub')
675
        self.assertRaises(errors.PathNotChild, t.relpath,
676
                          'sftp://user@host.com:33/abs/path/sub')
677
        # Make sure it works when we don't supply a username
678
        t = ConnectedTransport('sftp://host.com/abs/path')
679
        self.assertEquals(t.relpath('sftp://host.com/abs/path/sub'), 'sub')
680
681
        # Make sure it works when parts of the path will be url encoded
682
        t = ConnectedTransport('sftp://host.com/dev/%path')
683
        self.assertEquals(t.relpath('sftp://host.com/dev/%path/sub'), 'sub')
684
2485.8.32 by Vincent Ladeuil
Keep credentials used at connection creation for reconnection purposes.
685
    def test_connection_sharing_propagate_credentials(self):
2900.2.16 by Vincent Ladeuil
Make hhtp proxy aware of AuthenticationConfig (for password).
686
        t = ConnectedTransport('ftp://user@host.com/abs/path')
687
        self.assertEquals('user', t._user)
688
        self.assertEquals('host.com', t._host)
2485.8.32 by Vincent Ladeuil
Keep credentials used at connection creation for reconnection purposes.
689
        self.assertIs(None, t._get_connection())
690
        self.assertIs(None, t._password)
691
        c = t.clone('subdir')
2900.2.16 by Vincent Ladeuil
Make hhtp proxy aware of AuthenticationConfig (for password).
692
        self.assertIs(None, c._get_connection())
2485.8.32 by Vincent Ladeuil
Keep credentials used at connection creation for reconnection purposes.
693
        self.assertIs(None, t._password)
694
695
        # Simulate the user entering a password
696
        password = 'secret'
697
        connection = object()
698
        t._set_connection(connection, password)
699
        self.assertIs(connection, t._get_connection())
700
        self.assertIs(password, t._get_credentials())
701
        self.assertIs(connection, c._get_connection())
702
        self.assertIs(password, c._get_credentials())
2485.8.30 by Vincent Ladeuil
Implement reliable connection sharing.
703
2485.8.39 by Vincent Ladeuil
Add tests around connection reuse.
704
        # credentials can be updated
705
        new_password = 'even more secret'
706
        c._update_credentials(new_password)
707
        self.assertIs(connection, t._get_connection())
708
        self.assertIs(new_password, t._get_credentials())
709
        self.assertIs(connection, c._get_connection())
710
        self.assertIs(new_password, c._get_credentials())
711
2477.1.7 by Martin Pool
test_transport must provide get_test_permutations
712
2476.3.5 by Vincent Ladeuil
Naive implementation of transport reuse by Transport.get_transport().
713
class TestReusedTransports(TestCase):
2485.8.19 by Vincent Ladeuil
Add a new ConnectedTransport class refactored from [s]ftp and http.
714
    """Tests for transport reuse"""
2476.3.5 by Vincent Ladeuil
Naive implementation of transport reuse by Transport.get_transport().
715
716
    def test_reuse_same_transport(self):
1551.18.10 by Aaron Bentley
get_transport appends to possible_transports if it's an empty list
717
        possible_transports = []
718
        t1 = get_transport('http://foo/',
719
                           possible_transports=possible_transports)
720
        self.assertEqual([t1], possible_transports)
2485.8.37 by Vincent Ladeuil
Fix merge multiple connections. Test suite *not* passing (sftp
721
        t2 = get_transport('http://foo/', possible_transports=[t1])
722
        self.assertIs(t1, t2)
723
724
        # Also check that final '/' are handled correctly
725
        t3 = get_transport('http://foo/path/')
726
        t4 = get_transport('http://foo/path', possible_transports=[t3])
727
        self.assertIs(t3, t4)
728
2485.8.39 by Vincent Ladeuil
Add tests around connection reuse.
729
        t5 = get_transport('http://foo/path')
730
        t6 = get_transport('http://foo/path/', possible_transports=[t5])
731
        self.assertIs(t5, t6)
2476.3.5 by Vincent Ladeuil
Naive implementation of transport reuse by Transport.get_transport().
732
733
    def test_don_t_reuse_different_transport(self):
2485.8.39 by Vincent Ladeuil
Add tests around connection reuse.
734
        t1 = get_transport('http://foo/path')
735
        t2 = get_transport('http://bar/path', possible_transports=[t1])
2485.8.40 by Vincent Ladeuil
Fix typo.
736
        self.assertIsNot(t1, t2)
2476.3.13 by Vincent Ladeuil
merge bzr.dev@2495
737
738
2745.5.3 by Robert Collins
* Move transport logging into a new transport class
739
class TestTransportTrace(TestCase):
740
741
    def test_get(self):
742
        transport = get_transport('trace+memory://')
743
        self.assertIsInstance(
744
            transport, bzrlib.transport.trace.TransportTraceDecorator)
745
746
    def test_clone_preserves_activity(self):
747
        transport = get_transport('trace+memory://')
748
        transport2 = transport.clone('.')
749
        self.assertTrue(transport is not transport2)
750
        self.assertTrue(transport._activity is transport2._activity)
751
752
    # the following specific tests are for the operations that have made use of
753
    # logging in tests; we could test every single operation but doing that
754
    # still won't cause a test failure when the top level Transport API
755
    # changes; so there is little return doing that.
756
    def test_get(self):
757
        transport = get_transport('trace+memory:///')
758
        transport.put_bytes('foo', 'barish')
759
        transport.get('foo')
760
        expected_result = []
761
        # put_bytes records the bytes, not the content to avoid memory
762
        # pressure.
763
        expected_result.append(('put_bytes', 'foo', 6, None))
764
        # get records the file name only.
765
        expected_result.append(('get', 'foo'))
766
        self.assertEqual(expected_result, transport._activity)
767
768
    def test_readv(self):
769
        transport = get_transport('trace+memory:///')
770
        transport.put_bytes('foo', 'barish')
771
        list(transport.readv('foo', [(0, 1), (3, 2)], adjust_for_latency=True,
772
            upper_limit=6))
773
        expected_result = []
774
        # put_bytes records the bytes, not the content to avoid memory
775
        # pressure.
776
        expected_result.append(('put_bytes', 'foo', 6, None))
777
        # readv records the supplied offset request
778
        expected_result.append(('readv', 'foo', [(0, 1), (3, 2)], True, 6))
779
        self.assertEqual(expected_result, transport._activity)