~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/tests/test_selftest.py

  • Committer: Robert Collins
  • Date: 2007-07-04 08:08:13 UTC
  • mfrom: (2572 +trunk)
  • mto: This revision was merged to the branch mainline in revision 2587.
  • Revision ID: robertc@robertcollins.net-20070704080813-wzebx0r88fvwj5rq
Merge bzr.dev.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright (C) 2005, 2006 by Canonical Ltd
 
1
# Copyright (C) 2005, 2006, 2007 Canonical Ltd
2
2
#
3
3
# This program is free software; you can redistribute it and/or modify
4
 
# it under the terms of the GNU General Public License version 2 as published by
5
 
# the Free Software Foundation.
 
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.
6
7
#
7
8
# This program is distributed in the hope that it will be useful,
8
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
23
24
import unittest
24
25
import warnings
25
26
 
26
 
from bzrlib import osutils
27
27
import bzrlib
 
28
from bzrlib import (
 
29
    bzrdir,
 
30
    errors,
 
31
    memorytree,
 
32
    osutils,
 
33
    repository,
 
34
    symbol_versioning,
 
35
    )
28
36
from bzrlib.progress import _BaseProgressBar
 
37
from bzrlib.repofmt import weaverepo
 
38
from bzrlib.symbol_versioning import zero_ten, zero_eleven
29
39
from bzrlib.tests import (
30
40
                          ChrootedTestCase,
 
41
                          ExtendedTestResult,
 
42
                          Feature,
 
43
                          KnownFailure,
31
44
                          TestCase,
32
45
                          TestCaseInTempDir,
 
46
                          TestCaseWithMemoryTransport,
33
47
                          TestCaseWithTransport,
34
48
                          TestSkipped,
35
49
                          TestSuite,
 
50
                          TestUtil,
36
51
                          TextTestRunner,
 
52
                          UnavailableFeature,
 
53
                          clean_selftest_output,
 
54
                          iter_suite_tests,
 
55
                          filter_suite_by_re,
 
56
                          sort_suite_by_re,
 
57
                          test_lsprof,
 
58
                          test_suite,
37
59
                          )
38
60
from bzrlib.tests.test_sftp_transport import TestCaseWithSFTPServer
39
61
from bzrlib.tests.TestUtil import _load_module_by_name
40
 
import bzrlib.errors as errors
41
 
from bzrlib import symbol_versioning
42
 
from bzrlib.symbol_versioning import zero_ten, zero_eleven
43
62
from bzrlib.trace import note
44
63
from bzrlib.transport.memory import MemoryServer, MemoryTransport
45
64
from bzrlib.version import _get_bzr_source_tree
56
75
                          _load_module_by_name,
57
76
                          'bzrlib.no-name-yet')
58
77
 
59
 
 
60
78
class MetaTestLog(TestCase):
61
79
 
62
80
    def test_logging(self):
96
114
            def get_test_permutations(self):
97
115
                return sample_permutation
98
116
        sample_permutation = [(1,2), (3,4)]
99
 
        from bzrlib.transport import TransportTestProviderAdapter
 
117
        from bzrlib.tests.test_transport_implementations \
 
118
            import TransportTestProviderAdapter
100
119
        adapter = TransportTestProviderAdapter()
101
120
        self.assertEqual(sample_permutation,
102
121
                         adapter.get_transport_test_permutations(MockModule()))
107
126
        # - we assume if this matches its probably doing the right thing
108
127
        # especially in combination with the tests for setting the right
109
128
        # classes below.
110
 
        from bzrlib.transport import (TransportTestProviderAdapter,
111
 
                                      _get_transport_modules
112
 
                                      )
 
129
        from bzrlib.tests.test_transport_implementations \
 
130
            import TransportTestProviderAdapter
 
131
        from bzrlib.transport import _get_transport_modules
113
132
        modules = _get_transport_modules()
114
133
        permutation_count = 0
115
134
        for module in modules:
132
151
        # This test used to know about all the possible transports and the
133
152
        # order they were returned but that seems overly brittle (mbp
134
153
        # 20060307)
135
 
        input_test = TestTransportProviderAdapter(
136
 
            "test_adapter_sets_transport_class")
137
 
        from bzrlib.transport import TransportTestProviderAdapter
138
 
        suite = TransportTestProviderAdapter().adapt(input_test)
139
 
        tests = list(iter(suite))
140
 
        self.assertTrue(len(tests) > 6)
 
154
        from bzrlib.tests.test_transport_implementations \
 
155
            import TransportTestProviderAdapter
 
156
        scenarios = TransportTestProviderAdapter().scenarios
141
157
        # there are at least that many builtin transports
142
 
        one_test = tests[0]
143
 
        self.assertTrue(issubclass(one_test.transport_class, 
 
158
        self.assertTrue(len(scenarios) > 6)
 
159
        one_scenario = scenarios[0]
 
160
        self.assertIsInstance(one_scenario[0], str)
 
161
        self.assertTrue(issubclass(one_scenario[1]["transport_class"],
144
162
                                   bzrlib.transport.Transport))
145
 
        self.assertTrue(issubclass(one_test.transport_server, 
 
163
        self.assertTrue(issubclass(one_scenario[1]["transport_server"],
146
164
                                   bzrlib.transport.Server))
147
165
 
148
166
 
149
167
class TestBranchProviderAdapter(TestCase):
150
168
    """A group of tests that test the branch implementation test adapter."""
151
169
 
152
 
    def test_adapted_tests(self):
 
170
    def test_constructor(self):
153
171
        # check that constructor parameters are passed through to the adapted
154
172
        # test.
155
 
        from bzrlib.branch import BranchTestProviderAdapter
156
 
        input_test = TestBranchProviderAdapter(
157
 
            "test_adapted_tests")
 
173
        from bzrlib.tests.branch_implementations import BranchTestProviderAdapter
158
174
        server1 = "a"
159
175
        server2 = "b"
160
176
        formats = [("c", "C"), ("d", "D")]
161
177
        adapter = BranchTestProviderAdapter(server1, server2, formats)
162
 
        suite = adapter.adapt(input_test)
163
 
        tests = list(iter(suite))
164
 
        self.assertEqual(2, len(tests))
165
 
        self.assertEqual(tests[0].branch_format, formats[0][0])
166
 
        self.assertEqual(tests[0].bzrdir_format, formats[0][1])
167
 
        self.assertEqual(tests[0].transport_server, server1)
168
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
169
 
        self.assertEqual(tests[1].branch_format, formats[1][0])
170
 
        self.assertEqual(tests[1].bzrdir_format, formats[1][1])
171
 
        self.assertEqual(tests[1].transport_server, server1)
172
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
178
        self.assertEqual(2, len(adapter.scenarios))
 
179
        self.assertEqual([
 
180
            ('str',
 
181
             {'branch_format': 'c',
 
182
              'bzrdir_format': 'C',
 
183
              'transport_readonly_server': 'b',
 
184
              'transport_server': 'a'}),
 
185
            ('str',
 
186
             {'branch_format': 'd',
 
187
              'bzrdir_format': 'D',
 
188
              'transport_readonly_server': 'b',
 
189
              'transport_server': 'a'})],
 
190
            adapter.scenarios)
173
191
 
174
192
 
175
193
class TestBzrDirProviderAdapter(TestCase):
178
196
    def test_adapted_tests(self):
179
197
        # check that constructor parameters are passed through to the adapted
180
198
        # test.
181
 
        from bzrlib.bzrdir import BzrDirTestProviderAdapter
182
 
        input_test = TestBzrDirProviderAdapter(
183
 
            "test_adapted_tests")
 
199
        from bzrlib.tests.bzrdir_implementations import BzrDirTestProviderAdapter
 
200
        vfs_factory = "v"
184
201
        server1 = "a"
185
202
        server2 = "b"
186
203
        formats = ["c", "d"]
187
 
        adapter = BzrDirTestProviderAdapter(server1, server2, formats)
188
 
        suite = adapter.adapt(input_test)
189
 
        tests = list(iter(suite))
190
 
        self.assertEqual(2, len(tests))
191
 
        self.assertEqual(tests[0].bzrdir_format, formats[0])
192
 
        self.assertEqual(tests[0].transport_server, server1)
193
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
194
 
        self.assertEqual(tests[1].bzrdir_format, formats[1])
195
 
        self.assertEqual(tests[1].transport_server, server1)
196
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
204
        adapter = BzrDirTestProviderAdapter(vfs_factory,
 
205
            server1, server2, formats)
 
206
        self.assertEqual([
 
207
            ('str',
 
208
             {'bzrdir_format': 'c',
 
209
              'transport_readonly_server': 'b',
 
210
              'transport_server': 'a',
 
211
              'vfs_transport_factory': 'v'}),
 
212
            ('str',
 
213
             {'bzrdir_format': 'd',
 
214
              'transport_readonly_server': 'b',
 
215
              'transport_server': 'a',
 
216
              'vfs_transport_factory': 'v'})],
 
217
            adapter.scenarios)
197
218
 
198
219
 
199
220
class TestRepositoryProviderAdapter(TestCase):
200
221
    """A group of tests that test the repository implementation test adapter."""
201
222
 
202
 
    def test_adapted_tests(self):
203
 
        # check that constructor parameters are passed through to the adapted
204
 
        # test.
205
 
        from bzrlib.repository import RepositoryTestProviderAdapter
206
 
        input_test = TestRepositoryProviderAdapter(
207
 
            "test_adapted_tests")
 
223
    def test_constructor(self):
 
224
        # check that constructor parameters are passed through to the
 
225
        # scenarios.
 
226
        from bzrlib.tests.repository_implementations import RepositoryTestProviderAdapter
208
227
        server1 = "a"
209
228
        server2 = "b"
210
229
        formats = [("c", "C"), ("d", "D")]
211
230
        adapter = RepositoryTestProviderAdapter(server1, server2, formats)
212
 
        suite = adapter.adapt(input_test)
213
 
        tests = list(iter(suite))
214
 
        self.assertEqual(2, len(tests))
215
 
        self.assertEqual(tests[0].bzrdir_format, formats[0][1])
216
 
        self.assertEqual(tests[0].repository_format, formats[0][0])
217
 
        self.assertEqual(tests[0].transport_server, server1)
218
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
219
 
        self.assertEqual(tests[1].bzrdir_format, formats[1][1])
220
 
        self.assertEqual(tests[1].repository_format, formats[1][0])
221
 
        self.assertEqual(tests[1].transport_server, server1)
222
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
231
        self.assertEqual([
 
232
            ('str',
 
233
             {'bzrdir_format': 'C',
 
234
              'repository_format': 'c',
 
235
              'transport_readonly_server': 'b',
 
236
              'transport_server': 'a'}),
 
237
            ('str',
 
238
             {'bzrdir_format': 'D',
 
239
              'repository_format': 'd',
 
240
              'transport_readonly_server': 'b',
 
241
              'transport_server': 'a'})],
 
242
            adapter.scenarios)
 
243
 
 
244
    def test_setting_vfs_transport(self):
 
245
        """The vfs_transport_factory can be set optionally."""
 
246
        from bzrlib.tests.repository_implementations import RepositoryTestProviderAdapter
 
247
        formats = [("a", "b"), ("c", "d")]
 
248
        adapter = RepositoryTestProviderAdapter(None, None, formats,
 
249
            vfs_transport_factory="vfs")
 
250
        self.assertEqual([
 
251
            ('str',
 
252
             {'bzrdir_format': 'b',
 
253
              'repository_format': 'a',
 
254
              'transport_readonly_server': None,
 
255
              'transport_server': None,
 
256
              'vfs_transport_factory': 'vfs'}),
 
257
            ('str',
 
258
             {'bzrdir_format': 'd',
 
259
              'repository_format': 'c',
 
260
              'transport_readonly_server': None,
 
261
              'transport_server': None,
 
262
              'vfs_transport_factory': 'vfs'})],
 
263
            adapter.scenarios)
 
264
 
 
265
    def test_formats_to_scenarios(self):
 
266
        """The adapter can generate all the scenarios needed."""
 
267
        from bzrlib.tests.repository_implementations import RepositoryTestProviderAdapter
 
268
        no_vfs_adapter = RepositoryTestProviderAdapter("server", "readonly",
 
269
            [], None)
 
270
        vfs_adapter = RepositoryTestProviderAdapter("server", "readonly",
 
271
            [], vfs_transport_factory="vfs")
 
272
        # no_vfs generate scenarios without vfs_transport_factor
 
273
        formats = [("c", "C"), (1, "D")]
 
274
        self.assertEqual([
 
275
            ('str',
 
276
             {'bzrdir_format': 'C',
 
277
              'repository_format': 'c',
 
278
              'transport_readonly_server': 'readonly',
 
279
              'transport_server': 'server'}),
 
280
            ('int',
 
281
             {'bzrdir_format': 'D',
 
282
              'repository_format': 1,
 
283
              'transport_readonly_server': 'readonly',
 
284
              'transport_server': 'server'})],
 
285
            no_vfs_adapter.formats_to_scenarios(formats))
 
286
        self.assertEqual([
 
287
            ('str',
 
288
             {'bzrdir_format': 'C',
 
289
              'repository_format': 'c',
 
290
              'transport_readonly_server': 'readonly',
 
291
              'transport_server': 'server',
 
292
              'vfs_transport_factory': 'vfs'}),
 
293
            ('int',
 
294
             {'bzrdir_format': 'D',
 
295
              'repository_format': 1,
 
296
              'transport_readonly_server': 'readonly',
 
297
              'transport_server': 'server',
 
298
              'vfs_transport_factory': 'vfs'})],
 
299
            vfs_adapter.formats_to_scenarios(formats))
 
300
 
 
301
 
 
302
class TestTestScenarioApplier(TestCase):
 
303
    """Tests for the test adaption facilities."""
 
304
 
 
305
    def test_adapt_applies_scenarios(self):
 
306
        from bzrlib.tests.repository_implementations import TestScenarioApplier
 
307
        input_test = TestTestScenarioApplier("test_adapt_test_to_scenario")
 
308
        adapter = TestScenarioApplier()
 
309
        adapter.scenarios = [("1", "dict"), ("2", "settings")]
 
310
        calls = []
 
311
        def capture_call(test, scenario):
 
312
            calls.append((test, scenario))
 
313
            return test
 
314
        adapter.adapt_test_to_scenario = capture_call
 
315
        adapter.adapt(input_test)
 
316
        self.assertEqual([(input_test, ("1", "dict")),
 
317
            (input_test, ("2", "settings"))], calls)
 
318
 
 
319
    def test_adapt_test_to_scenario(self):
 
320
        from bzrlib.tests.repository_implementations import TestScenarioApplier
 
321
        input_test = TestTestScenarioApplier("test_adapt_test_to_scenario")
 
322
        adapter = TestScenarioApplier()
 
323
        # setup two adapted tests
 
324
        adapted_test1 = adapter.adapt_test_to_scenario(input_test,
 
325
            ("new id",
 
326
            {"bzrdir_format":"bzr_format",
 
327
             "repository_format":"repo_fmt",
 
328
             "transport_server":"transport_server",
 
329
             "transport_readonly_server":"readonly-server"}))
 
330
        adapted_test2 = adapter.adapt_test_to_scenario(input_test,
 
331
            ("new id 2", {"bzrdir_format":None}))
 
332
        # input_test should have been altered.
 
333
        self.assertRaises(AttributeError, getattr, input_test, "bzrdir_format")
 
334
        # the new tests are mutually incompatible, ensuring it has 
 
335
        # made new ones, and unspecified elements in the scenario
 
336
        # should not have been altered.
 
337
        self.assertEqual("bzr_format", adapted_test1.bzrdir_format)
 
338
        self.assertEqual("repo_fmt", adapted_test1.repository_format)
 
339
        self.assertEqual("transport_server", adapted_test1.transport_server)
 
340
        self.assertEqual("readonly-server",
 
341
            adapted_test1.transport_readonly_server)
 
342
        self.assertEqual(
 
343
            "bzrlib.tests.test_selftest.TestTestScenarioApplier."
 
344
            "test_adapt_test_to_scenario(new id)",
 
345
            adapted_test1.id())
 
346
        self.assertEqual(None, adapted_test2.bzrdir_format)
 
347
        self.assertEqual(
 
348
            "bzrlib.tests.test_selftest.TestTestScenarioApplier."
 
349
            "test_adapt_test_to_scenario(new id 2)",
 
350
            adapted_test2.id())
223
351
 
224
352
 
225
353
class TestInterRepositoryProviderAdapter(TestCase):
228
356
    def test_adapted_tests(self):
229
357
        # check that constructor parameters are passed through to the adapted
230
358
        # test.
231
 
        from bzrlib.repository import InterRepositoryTestProviderAdapter
232
 
        input_test = TestInterRepositoryProviderAdapter(
233
 
            "test_adapted_tests")
 
359
        from bzrlib.tests.interrepository_implementations import \
 
360
            InterRepositoryTestProviderAdapter
234
361
        server1 = "a"
235
362
        server2 = "b"
236
363
        formats = [(str, "C1", "C2"), (int, "D1", "D2")]
237
364
        adapter = InterRepositoryTestProviderAdapter(server1, server2, formats)
238
 
        suite = adapter.adapt(input_test)
239
 
        tests = list(iter(suite))
240
 
        self.assertEqual(2, len(tests))
241
 
        self.assertEqual(tests[0].interrepo_class, formats[0][0])
242
 
        self.assertEqual(tests[0].repository_format, formats[0][1])
243
 
        self.assertEqual(tests[0].repository_format_to, formats[0][2])
244
 
        self.assertEqual(tests[0].transport_server, server1)
245
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
246
 
        self.assertEqual(tests[1].interrepo_class, formats[1][0])
247
 
        self.assertEqual(tests[1].repository_format, formats[1][1])
248
 
        self.assertEqual(tests[1].repository_format_to, formats[1][2])
249
 
        self.assertEqual(tests[1].transport_server, server1)
250
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
365
        self.assertEqual([
 
366
            ('str',
 
367
             {'interrepo_class': str,
 
368
              'repository_format': 'C1',
 
369
              'repository_format_to': 'C2',
 
370
              'transport_readonly_server': 'b',
 
371
              'transport_server': 'a'}),
 
372
            ('int',
 
373
             {'interrepo_class': int,
 
374
              'repository_format': 'D1',
 
375
              'repository_format_to': 'D2',
 
376
              'transport_readonly_server': 'b',
 
377
              'transport_server': 'a'})],
 
378
            adapter.formats_to_scenarios(formats))
251
379
 
252
380
 
253
381
class TestInterVersionedFileProviderAdapter(TestCase):
254
382
    """A group of tests that test the InterVersionedFile test adapter."""
255
383
 
256
 
    def test_adapted_tests(self):
 
384
    def test_scenarios(self):
257
385
        # check that constructor parameters are passed through to the adapted
258
386
        # test.
259
 
        from bzrlib.versionedfile import InterVersionedFileTestProviderAdapter
260
 
        input_test = TestInterRepositoryProviderAdapter(
261
 
            "test_adapted_tests")
 
387
        from bzrlib.tests.interversionedfile_implementations \
 
388
            import InterVersionedFileTestProviderAdapter
262
389
        server1 = "a"
263
390
        server2 = "b"
264
391
        formats = [(str, "C1", "C2"), (int, "D1", "D2")]
265
392
        adapter = InterVersionedFileTestProviderAdapter(server1, server2, formats)
266
 
        suite = adapter.adapt(input_test)
267
 
        tests = list(iter(suite))
268
 
        self.assertEqual(2, len(tests))
269
 
        self.assertEqual(tests[0].interversionedfile_class, formats[0][0])
270
 
        self.assertEqual(tests[0].versionedfile_factory, formats[0][1])
271
 
        self.assertEqual(tests[0].versionedfile_factory_to, formats[0][2])
272
 
        self.assertEqual(tests[0].transport_server, server1)
273
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
274
 
        self.assertEqual(tests[1].interversionedfile_class, formats[1][0])
275
 
        self.assertEqual(tests[1].versionedfile_factory, formats[1][1])
276
 
        self.assertEqual(tests[1].versionedfile_factory_to, formats[1][2])
277
 
        self.assertEqual(tests[1].transport_server, server1)
278
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
393
        self.assertEqual([
 
394
            ('str',
 
395
             {'interversionedfile_class':str,
 
396
              'transport_readonly_server': 'b',
 
397
              'transport_server': 'a',
 
398
              'versionedfile_factory': 'C1',
 
399
              'versionedfile_factory_to': 'C2'}),
 
400
            ('int',
 
401
             {'interversionedfile_class': int,
 
402
              'transport_readonly_server': 'b',
 
403
              'transport_server': 'a',
 
404
              'versionedfile_factory': 'D1',
 
405
              'versionedfile_factory_to': 'D2'})],
 
406
            adapter.scenarios)
279
407
 
280
408
 
281
409
class TestRevisionStoreProviderAdapter(TestCase):
282
410
    """A group of tests that test the RevisionStore test adapter."""
283
411
 
284
 
    def test_adapted_tests(self):
 
412
    def test_scenarios(self):
285
413
        # check that constructor parameters are passed through to the adapted
286
414
        # test.
287
 
        from bzrlib.store.revision import RevisionStoreTestProviderAdapter
288
 
        input_test = TestRevisionStoreProviderAdapter(
289
 
            "test_adapted_tests")
 
415
        from bzrlib.tests.revisionstore_implementations \
 
416
            import RevisionStoreTestProviderAdapter
290
417
        # revision stores need a store factory - i.e. RevisionKnit
291
418
        #, a readonly and rw transport 
292
419
        # transport servers:
294
421
        server2 = "b"
295
422
        store_factories = ["c", "d"]
296
423
        adapter = RevisionStoreTestProviderAdapter(server1, server2, store_factories)
297
 
        suite = adapter.adapt(input_test)
298
 
        tests = list(iter(suite))
299
 
        self.assertEqual(2, len(tests))
300
 
        self.assertEqual(tests[0].store_factory, store_factories[0][0])
301
 
        self.assertEqual(tests[0].transport_server, server1)
302
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
303
 
        self.assertEqual(tests[1].store_factory, store_factories[1][0])
304
 
        self.assertEqual(tests[1].transport_server, server1)
305
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
424
        self.assertEqual([
 
425
            ('c',
 
426
             {'store_factory': 'c',
 
427
              'transport_readonly_server': 'b',
 
428
              'transport_server': 'a'}),
 
429
            ('d',
 
430
             {'store_factory': 'd',
 
431
              'transport_readonly_server': 'b',
 
432
              'transport_server': 'a'})],
 
433
            adapter.scenarios)
306
434
 
307
435
 
308
436
class TestWorkingTreeProviderAdapter(TestCase):
309
437
    """A group of tests that test the workingtree implementation test adapter."""
310
438
 
311
 
    def test_adapted_tests(self):
 
439
    def test_scenarios(self):
312
440
        # check that constructor parameters are passed through to the adapted
313
441
        # test.
314
 
        from bzrlib.workingtree import WorkingTreeTestProviderAdapter
315
 
        input_test = TestWorkingTreeProviderAdapter(
316
 
            "test_adapted_tests")
 
442
        from bzrlib.tests.workingtree_implementations \
 
443
            import WorkingTreeTestProviderAdapter
317
444
        server1 = "a"
318
445
        server2 = "b"
319
446
        formats = [("c", "C"), ("d", "D")]
320
447
        adapter = WorkingTreeTestProviderAdapter(server1, server2, formats)
321
 
        suite = adapter.adapt(input_test)
322
 
        tests = list(iter(suite))
323
 
        self.assertEqual(2, len(tests))
324
 
        self.assertEqual(tests[0].workingtree_format, formats[0][0])
325
 
        self.assertEqual(tests[0].bzrdir_format, formats[0][1])
326
 
        self.assertEqual(tests[0].transport_server, server1)
327
 
        self.assertEqual(tests[0].transport_readonly_server, server2)
328
 
        self.assertEqual(tests[1].workingtree_format, formats[1][0])
329
 
        self.assertEqual(tests[1].bzrdir_format, formats[1][1])
330
 
        self.assertEqual(tests[1].transport_server, server1)
331
 
        self.assertEqual(tests[1].transport_readonly_server, server2)
 
448
        self.assertEqual([
 
449
            ('str',
 
450
             {'bzrdir_format': 'C',
 
451
              'transport_readonly_server': 'b',
 
452
              'transport_server': 'a',
 
453
              'workingtree_format': 'c'}),
 
454
            ('str',
 
455
             {'bzrdir_format': 'D',
 
456
              'transport_readonly_server': 'b',
 
457
              'transport_server': 'a',
 
458
              'workingtree_format': 'd'})],
 
459
            adapter.scenarios)
332
460
 
333
461
 
334
462
class TestTreeProviderAdapter(TestCase):
347
475
            return_parameter,
348
476
            revision_tree_from_workingtree
349
477
            )
350
 
        from bzrlib.workingtree import WorkingTreeFormat
 
478
        from bzrlib.workingtree import WorkingTreeFormat, WorkingTreeFormat3
351
479
        input_test = TestTreeProviderAdapter(
352
480
            "test_adapted_tests")
353
481
        server1 = "a"
356
484
        adapter = TreeTestProviderAdapter(server1, server2, formats)
357
485
        suite = adapter.adapt(input_test)
358
486
        tests = list(iter(suite))
359
 
        self.assertEqual(3, len(tests))
360
 
        default_format = WorkingTreeFormat.get_default_format()
 
487
        self.assertEqual(4, len(tests))
 
488
        # this must match the default format setp up in
 
489
        # TreeTestProviderAdapter.adapt
 
490
        default_format = WorkingTreeFormat3
361
491
        self.assertEqual(tests[0].workingtree_format, formats[0][0])
362
492
        self.assertEqual(tests[0].bzrdir_format, formats[0][1])
363
493
        self.assertEqual(tests[0].transport_server, server1)
368
498
        self.assertEqual(tests[1].transport_server, server1)
369
499
        self.assertEqual(tests[1].transport_readonly_server, server2)
370
500
        self.assertEqual(tests[1].workingtree_to_test_tree, return_parameter)
371
 
        self.assertEqual(tests[2].workingtree_format, default_format)
372
 
        self.assertEqual(tests[2].bzrdir_format, default_format._matchingbzrdir)
 
501
        self.assertIsInstance(tests[2].workingtree_format, default_format)
 
502
        #self.assertEqual(tests[2].bzrdir_format,
 
503
        #                 default_format._matchingbzrdir)
373
504
        self.assertEqual(tests[2].transport_server, server1)
374
505
        self.assertEqual(tests[2].transport_readonly_server, server2)
375
506
        self.assertEqual(tests[2].workingtree_to_test_tree,
403
534
        server2 = "b"
404
535
        format1 = WorkingTreeFormat2()
405
536
        format2 = WorkingTreeFormat3()
406
 
        formats = [(str, format1, format2, False, True),
407
 
            (int, format2, format1, False, True)]
 
537
        formats = [(str, format1, format2, "converter1"),
 
538
            (int, format2, format1, "converter2")]
408
539
        adapter = InterTreeTestProviderAdapter(server1, server2, formats)
409
540
        suite = adapter.adapt(input_test)
410
541
        tests = list(iter(suite))
411
542
        self.assertEqual(2, len(tests))
412
543
        self.assertEqual(tests[0].intertree_class, formats[0][0])
413
544
        self.assertEqual(tests[0].workingtree_format, formats[0][1])
414
 
        self.assertEqual(tests[0].workingtree_to_test_tree, formats[0][2])
415
 
        self.assertEqual(tests[0].workingtree_format_to, formats[0][3])
416
 
        self.assertEqual(tests[0].workingtree_to_test_tree_to, formats[0][4])
 
545
        self.assertEqual(tests[0].workingtree_format_to, formats[0][2])
 
546
        self.assertEqual(tests[0].mutable_trees_to_test_trees, formats[0][3])
 
547
        self.assertEqual(tests[0].workingtree_to_test_tree, return_parameter)
417
548
        self.assertEqual(tests[0].transport_server, server1)
418
549
        self.assertEqual(tests[0].transport_readonly_server, server2)
419
550
        self.assertEqual(tests[1].intertree_class, formats[1][0])
420
551
        self.assertEqual(tests[1].workingtree_format, formats[1][1])
421
 
        self.assertEqual(tests[1].workingtree_to_test_tree, formats[1][2])
422
 
        self.assertEqual(tests[1].workingtree_format_to, formats[1][3])
423
 
        self.assertEqual(tests[1].workingtree_to_test_tree_to, formats[1][4])
 
552
        self.assertEqual(tests[1].workingtree_format_to, formats[1][2])
 
553
        self.assertEqual(tests[1].mutable_trees_to_test_trees, formats[1][3])
 
554
        self.assertEqual(tests[1].workingtree_to_test_tree, return_parameter)
424
555
        self.assertEqual(tests[1].transport_server, server1)
425
556
        self.assertEqual(tests[1].transport_readonly_server, server2)
426
557
 
434
565
        self.assertEqual(self.test_home_dir, os.environ['HOME'])
435
566
 
436
567
 
 
568
class TestTestCaseWithMemoryTransport(TestCaseWithMemoryTransport):
 
569
 
 
570
    def test_home_is_non_existant_dir_under_root(self):
 
571
        """The test_home_dir for TestCaseWithMemoryTransport is missing.
 
572
 
 
573
        This is because TestCaseWithMemoryTransport is for tests that do not
 
574
        need any disk resources: they should be hooked into bzrlib in such a 
 
575
        way that no global settings are being changed by the test (only a 
 
576
        few tests should need to do that), and having a missing dir as home is
 
577
        an effective way to ensure that this is the case.
 
578
        """
 
579
        self.assertEqual(self.TEST_ROOT + "/MemoryTransportMissingHomeDir",
 
580
            self.test_home_dir)
 
581
        self.assertEqual(self.test_home_dir, os.environ['HOME'])
 
582
        
 
583
    def test_cwd_is_TEST_ROOT(self):
 
584
        self.assertEqual(self.test_dir, self.TEST_ROOT)
 
585
        cwd = osutils.getcwd()
 
586
        self.assertEqual(self.test_dir, cwd)
 
587
 
 
588
    def test_make_branch_and_memory_tree(self):
 
589
        """In TestCaseWithMemoryTransport we should not make the branch on disk.
 
590
 
 
591
        This is hard to comprehensively robustly test, so we settle for making
 
592
        a branch and checking no directory was created at its relpath.
 
593
        """
 
594
        tree = self.make_branch_and_memory_tree('dir')
 
595
        # Guard against regression into MemoryTransport leaking
 
596
        # files to disk instead of keeping them in memory.
 
597
        self.failIf(osutils.lexists('dir'))
 
598
        self.assertIsInstance(tree, memorytree.MemoryTree)
 
599
 
 
600
    def test_make_branch_and_memory_tree_with_format(self):
 
601
        """make_branch_and_memory_tree should accept a format option."""
 
602
        format = bzrdir.BzrDirMetaFormat1()
 
603
        format.repository_format = weaverepo.RepositoryFormat7()
 
604
        tree = self.make_branch_and_memory_tree('dir', format=format)
 
605
        # Guard against regression into MemoryTransport leaking
 
606
        # files to disk instead of keeping them in memory.
 
607
        self.failIf(osutils.lexists('dir'))
 
608
        self.assertIsInstance(tree, memorytree.MemoryTree)
 
609
        self.assertEqual(format.repository_format.__class__,
 
610
            tree.branch.repository._format.__class__)
 
611
 
 
612
 
437
613
class TestTestCaseWithTransport(TestCaseWithTransport):
438
614
    """Tests for the convenience functions TestCaseWithTransport introduces."""
439
615
 
441
617
        from bzrlib.transport import get_transport
442
618
        from bzrlib.transport.memory import MemoryServer
443
619
        from bzrlib.transport.readonly import ReadonlyTransportDecorator
444
 
        self.transport_server = MemoryServer
 
620
        self.vfs_transport_factory = MemoryServer
445
621
        self.transport_readonly_server = None
446
622
        # calling get_readonly_transport() constructs a decorator on the url
447
623
        # for the server
454
630
        self.assertEqual(t2.base[:-1], t.abspath('foo/bar'))
455
631
 
456
632
    def test_get_readonly_url_http(self):
 
633
        from bzrlib.tests.HttpServer import HttpServer
457
634
        from bzrlib.transport import get_transport
458
 
        from bzrlib.transport.local import LocalRelpathServer
459
 
        from bzrlib.transport.http import HttpServer, HttpTransportBase
460
 
        self.transport_server = LocalRelpathServer
 
635
        from bzrlib.transport.local import LocalURLServer
 
636
        from bzrlib.transport.http import HttpTransportBase
 
637
        self.transport_server = LocalURLServer
461
638
        self.transport_readonly_server = HttpServer
462
639
        # calling get_readonly_transport() gives us a HTTP server instance.
463
640
        url = self.get_readonly_url()
482
659
 
483
660
    def setUp(self):
484
661
        super(TestTestCaseTransports, self).setUp()
485
 
        self.transport_server = MemoryServer
 
662
        self.vfs_transport_factory = MemoryServer
486
663
 
487
664
    def test_make_bzrdir_preserves_transport(self):
488
665
        t = self.get_transport()
527
704
 
528
705
class TestTestResult(TestCase):
529
706
 
530
 
    def test_progress_bar_style_quiet(self):
531
 
        # test using a progress bar.
532
 
        dummy_test = TestTestResult('test_progress_bar_style_quiet')
533
 
        dummy_error = (Exception, None, [])
534
 
        mypb = MockProgress()
535
 
        mypb.update('Running tests', 0, 4)
536
 
        last_calls = mypb.calls[:]
537
 
 
538
 
        result = bzrlib.tests._MyResult(self._log_file,
539
 
                                        descriptions=0,
540
 
                                        verbosity=1,
541
 
                                        pb=mypb)
542
 
        self.assertEqual(last_calls, mypb.calls)
543
 
 
544
 
        def shorten(s):
545
 
            """Shorten a string based on the terminal width"""
546
 
            return result._ellipsise_unimportant_words(s,
547
 
                                 osutils.terminal_width())
548
 
 
549
 
        # an error 
550
 
        result.startTest(dummy_test)
551
 
        # starting a test prints the test name
552
 
        last_calls += [('update', '...tyle_quiet', 0, None)]
553
 
        self.assertEqual(last_calls, mypb.calls)
554
 
        result.addError(dummy_test, dummy_error)
555
 
        last_calls += [('update', 'ERROR        ', 1, None),
556
 
                       ('note', shorten(dummy_test.id() + ': ERROR'), ())
557
 
                      ]
558
 
        self.assertEqual(last_calls, mypb.calls)
559
 
 
560
 
        # a failure
561
 
        result.startTest(dummy_test)
562
 
        last_calls += [('update', '...tyle_quiet', 1, None)]
563
 
        self.assertEqual(last_calls, mypb.calls)
564
 
        last_calls += [('update', 'FAIL         ', 2, None),
565
 
                       ('note', shorten(dummy_test.id() + ': FAIL'), ())
566
 
                      ]
567
 
        result.addFailure(dummy_test, dummy_error)
568
 
        self.assertEqual(last_calls, mypb.calls)
569
 
 
570
 
        # a success
571
 
        result.startTest(dummy_test)
572
 
        last_calls += [('update', '...tyle_quiet', 2, None)]
573
 
        self.assertEqual(last_calls, mypb.calls)
574
 
        result.addSuccess(dummy_test)
575
 
        last_calls += [('update', 'OK           ', 3, None)]
576
 
        self.assertEqual(last_calls, mypb.calls)
577
 
 
578
 
        # a skip
579
 
        result.startTest(dummy_test)
580
 
        last_calls += [('update', '...tyle_quiet', 3, None)]
581
 
        self.assertEqual(last_calls, mypb.calls)
582
 
        result.addSkipped(dummy_test, dummy_error)
583
 
        last_calls += [('update', 'SKIP         ', 4, None)]
584
 
        self.assertEqual(last_calls, mypb.calls)
585
 
 
586
707
    def test_elapsed_time_with_benchmarking(self):
587
 
        result = bzrlib.tests._MyResult(self._log_file,
 
708
        result = bzrlib.tests.TextTestResult(self._log_file,
588
709
                                        descriptions=0,
589
710
                                        verbosity=1,
590
711
                                        )
593
714
        result.extractBenchmarkTime(self)
594
715
        timed_string = result._testTimeString()
595
716
        # without explicit benchmarking, we should get a simple time.
596
 
        self.assertContainsRe(timed_string, "^         [ 1-9][0-9]ms$")
 
717
        self.assertContainsRe(timed_string, "^ +[0-9]+ms$")
597
718
        # if a benchmark time is given, we want a x of y style result.
598
719
        self.time(time.sleep, 0.001)
599
720
        result.extractBenchmarkTime(self)
600
721
        timed_string = result._testTimeString()
601
 
        self.assertContainsRe(timed_string, "^   [ 1-9][0-9]ms/   [ 1-9][0-9]ms$")
 
722
        self.assertContainsRe(
 
723
            timed_string, "^ +[0-9]+ms/ +[0-9]+ms$")
602
724
        # extracting the time from a non-bzrlib testcase sets to None
603
725
        result._recordTestStartTime()
604
726
        result.extractBenchmarkTime(
605
727
            unittest.FunctionTestCase(self.test_elapsed_time_with_benchmarking))
606
728
        timed_string = result._testTimeString()
607
 
        self.assertContainsRe(timed_string, "^         [ 1-9][0-9]ms$")
 
729
        self.assertContainsRe(timed_string, "^ +[0-9]+ms$")
608
730
        # cheat. Yes, wash thy mouth out with soap.
609
731
        self._benchtime = None
610
732
 
611
733
    def test_assigned_benchmark_file_stores_date(self):
612
734
        output = StringIO()
613
 
        result = bzrlib.tests._MyResult(self._log_file,
 
735
        result = bzrlib.tests.TextTestResult(self._log_file,
614
736
                                        descriptions=0,
615
737
                                        verbosity=1,
616
738
                                        bench_history=output
617
739
                                        )
618
740
        output_string = output.getvalue()
 
741
        
619
742
        # if you are wondering about the regexp please read the comment in
620
743
        # test_bench_history (bzrlib.tests.test_selftest.TestRunner)
621
744
        # XXX: what comment?  -- Andrew Bennetts
623
746
 
624
747
    def test_benchhistory_records_test_times(self):
625
748
        result_stream = StringIO()
626
 
        result = bzrlib.tests._MyResult(
 
749
        result = bzrlib.tests.TextTestResult(
627
750
            self._log_file,
628
751
            descriptions=0,
629
752
            verbosity=1,
651
774
 
652
775
    def test_lsprofiling(self):
653
776
        """Verbose test result prints lsprof statistics from test cases."""
654
 
        try:
655
 
            import bzrlib.lsprof
656
 
        except ImportError:
657
 
            raise TestSkipped("lsprof not installed.")
 
777
        self.requireFeature(test_lsprof.LSProfFeature)
658
778
        result_stream = StringIO()
659
 
        result = bzrlib.tests._MyResult(
 
779
        result = bzrlib.tests.VerboseTestResult(
660
780
            unittest._WritelnDecorator(result_stream),
661
781
            descriptions=0,
662
782
            verbosity=2,
689
809
        self.assertContainsRe(output,
690
810
            r"LSProf output for <type 'unicode'>\(\('world',\), {'errors': 'replace'}\)\n")
691
811
 
 
812
    def test_known_failure(self):
 
813
        """A KnownFailure being raised should trigger several result actions."""
 
814
        class InstrumentedTestResult(ExtendedTestResult):
 
815
 
 
816
            def report_test_start(self, test): pass
 
817
            def report_known_failure(self, test, err):
 
818
                self._call = test, err
 
819
        result = InstrumentedTestResult(None, None, None, None)
 
820
        def test_function():
 
821
            raise KnownFailure('failed!')
 
822
        test = unittest.FunctionTestCase(test_function)
 
823
        test.run(result)
 
824
        # it should invoke 'report_known_failure'.
 
825
        self.assertEqual(2, len(result._call))
 
826
        self.assertEqual(test, result._call[0])
 
827
        self.assertEqual(KnownFailure, result._call[1][0])
 
828
        self.assertIsInstance(result._call[1][1], KnownFailure)
 
829
        # we dont introspec the traceback, if the rest is ok, it would be
 
830
        # exceptional for it not to be.
 
831
        # it should update the known_failure_count on the object.
 
832
        self.assertEqual(1, result.known_failure_count)
 
833
        # the result should be successful.
 
834
        self.assertTrue(result.wasSuccessful())
 
835
 
 
836
    def test_verbose_report_known_failure(self):
 
837
        # verbose test output formatting
 
838
        result_stream = StringIO()
 
839
        result = bzrlib.tests.VerboseTestResult(
 
840
            unittest._WritelnDecorator(result_stream),
 
841
            descriptions=0,
 
842
            verbosity=2,
 
843
            )
 
844
        test = self.get_passing_test()
 
845
        result.startTest(test)
 
846
        result.extractBenchmarkTime(test)
 
847
        prefix = len(result_stream.getvalue())
 
848
        # the err parameter has the shape:
 
849
        # (class, exception object, traceback)
 
850
        # KnownFailures dont get their tracebacks shown though, so we
 
851
        # can skip that.
 
852
        err = (KnownFailure, KnownFailure('foo'), None)
 
853
        result.report_known_failure(test, err)
 
854
        output = result_stream.getvalue()[prefix:]
 
855
        lines = output.splitlines()
 
856
        self.assertContainsRe(lines[0], r'XFAIL *\d+ms$')
 
857
        self.assertEqual(lines[1], '    foo')
 
858
        self.assertEqual(2, len(lines))
 
859
 
 
860
    def test_text_report_known_failure(self):
 
861
        # text test output formatting
 
862
        pb = MockProgress()
 
863
        result = bzrlib.tests.TextTestResult(
 
864
            None,
 
865
            descriptions=0,
 
866
            verbosity=1,
 
867
            pb=pb,
 
868
            )
 
869
        test = self.get_passing_test()
 
870
        # this seeds the state to handle reporting the test.
 
871
        result.startTest(test)
 
872
        result.extractBenchmarkTime(test)
 
873
        # the err parameter has the shape:
 
874
        # (class, exception object, traceback)
 
875
        # KnownFailures dont get their tracebacks shown though, so we
 
876
        # can skip that.
 
877
        err = (KnownFailure, KnownFailure('foo'), None)
 
878
        result.report_known_failure(test, err)
 
879
        self.assertEqual(
 
880
            [
 
881
            ('update', '[1 in 0s] passing_test', None, None),
 
882
            ('note', 'XFAIL: %s\n%s\n', ('passing_test', err[1]))
 
883
            ],
 
884
            pb.calls)
 
885
        # known_failures should be printed in the summary, so if we run a test
 
886
        # after there are some known failures, the update prefix should match
 
887
        # this.
 
888
        result.known_failure_count = 3
 
889
        test.run(result)
 
890
        self.assertEqual(
 
891
            [
 
892
            ('update', '[2 in 0s, 3 known failures] passing_test', None, None),
 
893
            ],
 
894
            pb.calls[2:])
 
895
 
 
896
    def get_passing_test(self):
 
897
        """Return a test object that can't be run usefully."""
 
898
        def passing_test():
 
899
            pass
 
900
        return unittest.FunctionTestCase(passing_test)
 
901
 
 
902
    def test_add_not_supported(self):
 
903
        """Test the behaviour of invoking addNotSupported."""
 
904
        class InstrumentedTestResult(ExtendedTestResult):
 
905
            def report_test_start(self, test): pass
 
906
            def report_unsupported(self, test, feature):
 
907
                self._call = test, feature
 
908
        result = InstrumentedTestResult(None, None, None, None)
 
909
        test = SampleTestCase('_test_pass')
 
910
        feature = Feature()
 
911
        result.startTest(test)
 
912
        result.addNotSupported(test, feature)
 
913
        # it should invoke 'report_unsupported'.
 
914
        self.assertEqual(2, len(result._call))
 
915
        self.assertEqual(test, result._call[0])
 
916
        self.assertEqual(feature, result._call[1])
 
917
        # the result should be successful.
 
918
        self.assertTrue(result.wasSuccessful())
 
919
        # it should record the test against a count of tests not run due to
 
920
        # this feature.
 
921
        self.assertEqual(1, result.unsupported['Feature'])
 
922
        # and invoking it again should increment that counter
 
923
        result.addNotSupported(test, feature)
 
924
        self.assertEqual(2, result.unsupported['Feature'])
 
925
 
 
926
    def test_verbose_report_unsupported(self):
 
927
        # verbose test output formatting
 
928
        result_stream = StringIO()
 
929
        result = bzrlib.tests.VerboseTestResult(
 
930
            unittest._WritelnDecorator(result_stream),
 
931
            descriptions=0,
 
932
            verbosity=2,
 
933
            )
 
934
        test = self.get_passing_test()
 
935
        feature = Feature()
 
936
        result.startTest(test)
 
937
        result.extractBenchmarkTime(test)
 
938
        prefix = len(result_stream.getvalue())
 
939
        result.report_unsupported(test, feature)
 
940
        output = result_stream.getvalue()[prefix:]
 
941
        lines = output.splitlines()
 
942
        self.assertEqual(lines, ['NODEP                   0ms', "    The feature 'Feature' is not available."])
 
943
    
 
944
    def test_text_report_unsupported(self):
 
945
        # text test output formatting
 
946
        pb = MockProgress()
 
947
        result = bzrlib.tests.TextTestResult(
 
948
            None,
 
949
            descriptions=0,
 
950
            verbosity=1,
 
951
            pb=pb,
 
952
            )
 
953
        test = self.get_passing_test()
 
954
        feature = Feature()
 
955
        # this seeds the state to handle reporting the test.
 
956
        result.startTest(test)
 
957
        result.extractBenchmarkTime(test)
 
958
        result.report_unsupported(test, feature)
 
959
        # no output on unsupported features
 
960
        self.assertEqual(
 
961
            [('update', '[1 in 0s] passing_test', None, None)
 
962
            ],
 
963
            pb.calls)
 
964
        # the number of missing features should be printed in the progress
 
965
        # summary, so check for that.
 
966
        result.unsupported = {'foo':0, 'bar':0}
 
967
        test.run(result)
 
968
        self.assertEqual(
 
969
            [
 
970
            ('update', '[2 in 0s, 2 missing features] passing_test', None, None),
 
971
            ],
 
972
            pb.calls[1:])
 
973
    
 
974
    def test_unavailable_exception(self):
 
975
        """An UnavailableFeature being raised should invoke addNotSupported."""
 
976
        class InstrumentedTestResult(ExtendedTestResult):
 
977
 
 
978
            def report_test_start(self, test): pass
 
979
            def addNotSupported(self, test, feature):
 
980
                self._call = test, feature
 
981
        result = InstrumentedTestResult(None, None, None, None)
 
982
        feature = Feature()
 
983
        def test_function():
 
984
            raise UnavailableFeature(feature)
 
985
        test = unittest.FunctionTestCase(test_function)
 
986
        test.run(result)
 
987
        # it should invoke 'addNotSupported'.
 
988
        self.assertEqual(2, len(result._call))
 
989
        self.assertEqual(test, result._call[0])
 
990
        self.assertEqual(feature, result._call[1])
 
991
        # and not count as an error
 
992
        self.assertEqual(0, result.error_count)
 
993
 
692
994
 
693
995
class TestRunner(TestCase):
694
996
 
711
1013
        finally:
712
1014
            TestCaseInTempDir.TEST_ROOT = old_root
713
1015
 
714
 
    def test_accepts_and_uses_pb_parameter(self):
715
 
        test = TestRunner('dummy_test')
716
 
        mypb = MockProgress()
717
 
        self.assertEqual([], mypb.calls)
718
 
        runner = TextTestRunner(stream=self._log_file, pb=mypb)
719
 
        result = self.run_test_runner(runner, test)
720
 
        self.assertEqual(1, result.testsRun)
721
 
        self.assertEqual(('update', 'Running tests', 0, 1), mypb.calls[0])
722
 
        self.assertEqual(('update', '...dummy_test', 0, None), mypb.calls[1])
723
 
        self.assertEqual(('update', 'OK           ', 1, None), mypb.calls[2])
724
 
        self.assertEqual(('update', 'Cleaning up', 0, 1), mypb.calls[3])
725
 
        self.assertEqual(('clear',), mypb.calls[4])
726
 
        self.assertEqual(5, len(mypb.calls))
 
1016
    def test_known_failure_failed_run(self):
 
1017
        # run a test that generates a known failure which should be printed in
 
1018
        # the final output when real failures occur.
 
1019
        def known_failure_test():
 
1020
            raise KnownFailure('failed')
 
1021
        test = unittest.TestSuite()
 
1022
        test.addTest(unittest.FunctionTestCase(known_failure_test))
 
1023
        def failing_test():
 
1024
            raise AssertionError('foo')
 
1025
        test.addTest(unittest.FunctionTestCase(failing_test))
 
1026
        stream = StringIO()
 
1027
        runner = TextTestRunner(stream=stream)
 
1028
        result = self.run_test_runner(runner, test)
 
1029
        lines = stream.getvalue().splitlines()
 
1030
        self.assertEqual([
 
1031
            '',
 
1032
            '======================================================================',
 
1033
            'FAIL: unittest.FunctionTestCase (failing_test)',
 
1034
            '----------------------------------------------------------------------',
 
1035
            'Traceback (most recent call last):',
 
1036
            '    raise AssertionError(\'foo\')',
 
1037
            'AssertionError: foo',
 
1038
            '',
 
1039
            '----------------------------------------------------------------------',
 
1040
            '',
 
1041
            'FAILED (failures=1, known_failure_count=1)'],
 
1042
            lines[0:5] + lines[6:10] + lines[11:])
 
1043
 
 
1044
    def test_known_failure_ok_run(self):
 
1045
        # run a test that generates a known failure which should be printed in the final output.
 
1046
        def known_failure_test():
 
1047
            raise KnownFailure('failed')
 
1048
        test = unittest.FunctionTestCase(known_failure_test)
 
1049
        stream = StringIO()
 
1050
        runner = TextTestRunner(stream=stream)
 
1051
        result = self.run_test_runner(runner, test)
 
1052
        self.assertContainsRe(stream.getvalue(),
 
1053
            '\n'
 
1054
            '-*\n'
 
1055
            'Ran 1 test in .*\n'
 
1056
            '\n'
 
1057
            'OK \\(known_failures=1\\)\n')
727
1058
 
728
1059
    def test_skipped_test(self):
729
1060
        # run a test that is skipped, and check the suite as a whole still
731
1062
        # skipping_test must be hidden in here so it's not run as a real test
732
1063
        def skipping_test():
733
1064
            raise TestSkipped('test intentionally skipped')
734
 
        runner = TextTestRunner(stream=self._log_file, keep_output=True)
 
1065
 
 
1066
        runner = TextTestRunner(stream=self._log_file)
735
1067
        test = unittest.FunctionTestCase(skipping_test)
736
1068
        result = self.run_test_runner(runner, test)
737
1069
        self.assertTrue(result.wasSuccessful())
738
1070
 
 
1071
    def test_skipped_from_setup(self):
 
1072
        class SkippedSetupTest(TestCase):
 
1073
 
 
1074
            def setUp(self):
 
1075
                self.counter = 1
 
1076
                self.addCleanup(self.cleanup)
 
1077
                raise TestSkipped('skipped setup')
 
1078
 
 
1079
            def test_skip(self):
 
1080
                self.fail('test reached')
 
1081
 
 
1082
            def cleanup(self):
 
1083
                self.counter -= 1
 
1084
 
 
1085
        runner = TextTestRunner(stream=self._log_file)
 
1086
        test = SkippedSetupTest('test_skip')
 
1087
        result = self.run_test_runner(runner, test)
 
1088
        self.assertTrue(result.wasSuccessful())
 
1089
        # Check if cleanup was called the right number of times.
 
1090
        self.assertEqual(0, test.counter)
 
1091
 
 
1092
    def test_skipped_from_test(self):
 
1093
        class SkippedTest(TestCase):
 
1094
 
 
1095
            def setUp(self):
 
1096
                self.counter = 1
 
1097
                self.addCleanup(self.cleanup)
 
1098
 
 
1099
            def test_skip(self):
 
1100
                raise TestSkipped('skipped test')
 
1101
 
 
1102
            def cleanup(self):
 
1103
                self.counter -= 1
 
1104
 
 
1105
        runner = TextTestRunner(stream=self._log_file)
 
1106
        test = SkippedTest('test_skip')
 
1107
        result = self.run_test_runner(runner, test)
 
1108
        self.assertTrue(result.wasSuccessful())
 
1109
        # Check if cleanup was called the right number of times.
 
1110
        self.assertEqual(0, test.counter)
 
1111
 
 
1112
    def test_unsupported_features_listed(self):
 
1113
        """When unsupported features are encountered they are detailed."""
 
1114
        class Feature1(Feature):
 
1115
            def _probe(self): return False
 
1116
        class Feature2(Feature):
 
1117
            def _probe(self): return False
 
1118
        # create sample tests
 
1119
        test1 = SampleTestCase('_test_pass')
 
1120
        test1._test_needs_features = [Feature1()]
 
1121
        test2 = SampleTestCase('_test_pass')
 
1122
        test2._test_needs_features = [Feature2()]
 
1123
        test = unittest.TestSuite()
 
1124
        test.addTest(test1)
 
1125
        test.addTest(test2)
 
1126
        stream = StringIO()
 
1127
        runner = TextTestRunner(stream=stream)
 
1128
        result = self.run_test_runner(runner, test)
 
1129
        lines = stream.getvalue().splitlines()
 
1130
        self.assertEqual([
 
1131
            'OK',
 
1132
            "Missing feature 'Feature1' skipped 1 tests.",
 
1133
            "Missing feature 'Feature2' skipped 1 tests.",
 
1134
            ],
 
1135
            lines[-3:])
 
1136
 
739
1137
    def test_bench_history(self):
740
1138
        # tests that the running the benchmark produces a history file
741
1139
        # containing a timestamp and the revision id of the bzrlib source which
814
1212
        self.assertEqual(log, test._log_contents)
815
1213
 
816
1214
 
 
1215
class SampleTestCase(TestCase):
 
1216
 
 
1217
    def _test_pass(self):
 
1218
        pass
 
1219
 
 
1220
 
817
1221
class TestTestCase(TestCase):
818
1222
    """Tests that test the core bzrlib TestCase."""
819
1223
 
 
1224
    def test_debug_flags_sanitised(self):
 
1225
        """The bzrlib debug flags should be sanitised by setUp."""
 
1226
        # we could set something and run a test that will check
 
1227
        # it gets santised, but this is probably sufficient for now:
 
1228
        # if someone runs the test with -Dsomething it will error.
 
1229
        self.assertEqual(set(), bzrlib.debug.debug_flags)
 
1230
 
820
1231
    def inner_test(self):
821
1232
        # the inner child test
822
1233
        note("inner_test")
825
1236
        # the outer child test
826
1237
        note("outer_start")
827
1238
        self.inner_test = TestTestCase("inner_child")
828
 
        result = bzrlib.tests._MyResult(self._log_file,
 
1239
        result = bzrlib.tests.TextTestResult(self._log_file,
829
1240
                                        descriptions=0,
830
1241
                                        verbosity=1)
831
1242
        self.inner_test.run(result)
845
1256
        # the outer child test
846
1257
        original_trace = bzrlib.trace._trace_file
847
1258
        outer_test = TestTestCase("outer_child")
848
 
        result = bzrlib.tests._MyResult(self._log_file,
 
1259
        result = bzrlib.tests.TextTestResult(self._log_file,
849
1260
                                        descriptions=0,
850
1261
                                        verbosity=1)
851
1262
        outer_test.run(result)
860
1271
        """Test that the TestCase.time() method accumulates a benchmark time."""
861
1272
        sample_test = TestTestCase("method_that_times_a_bit_twice")
862
1273
        output_stream = StringIO()
863
 
        result = bzrlib.tests._MyResult(
 
1274
        result = bzrlib.tests.VerboseTestResult(
864
1275
            unittest._WritelnDecorator(output_stream),
865
1276
            descriptions=0,
866
 
            verbosity=2)
 
1277
            verbosity=2,
 
1278
            num_tests=sample_test.countTestCases())
867
1279
        sample_test.run(result)
868
1280
        self.assertContainsRe(
869
1281
            output_stream.getvalue(),
870
 
            "[1-9][0-9]ms/   [1-9][0-9]ms\n$")
871
 
        
 
1282
            r"\d+ms/ +\d+ms\n$")
 
1283
 
 
1284
    def test_hooks_sanitised(self):
 
1285
        """The bzrlib hooks should be sanitised by setUp."""
 
1286
        self.assertEqual(bzrlib.branch.BranchHooks(),
 
1287
            bzrlib.branch.Branch.hooks)
 
1288
        self.assertEqual(bzrlib.smart.server.SmartServerHooks(),
 
1289
            bzrlib.smart.server.SmartTCPServer.hooks)
 
1290
 
872
1291
    def test__gather_lsprof_in_benchmarks(self):
873
1292
        """When _gather_lsprof_in_benchmarks is on, accumulate profile data.
874
1293
        
875
1294
        Each self.time() call is individually and separately profiled.
876
1295
        """
877
 
        try:
878
 
            import bzrlib.lsprof
879
 
        except ImportError:
880
 
            raise TestSkipped("lsprof not installed.")
 
1296
        self.requireFeature(test_lsprof.LSProfFeature)
881
1297
        # overrides the class member with an instance member so no cleanup 
882
1298
        # needed.
883
1299
        self._gather_lsprof_in_benchmarks = True
889
1305
        self.assertIsInstance(self._benchcalls[0][1], bzrlib.lsprof.Stats)
890
1306
        self.assertIsInstance(self._benchcalls[1][1], bzrlib.lsprof.Stats)
891
1307
 
 
1308
    def test_knownFailure(self):
 
1309
        """Self.knownFailure() should raise a KnownFailure exception."""
 
1310
        self.assertRaises(KnownFailure, self.knownFailure, "A Failure")
 
1311
 
 
1312
    def test_requireFeature_available(self):
 
1313
        """self.requireFeature(available) is a no-op."""
 
1314
        class Available(Feature):
 
1315
            def _probe(self):return True
 
1316
        feature = Available()
 
1317
        self.requireFeature(feature)
 
1318
 
 
1319
    def test_requireFeature_unavailable(self):
 
1320
        """self.requireFeature(unavailable) raises UnavailableFeature."""
 
1321
        class Unavailable(Feature):
 
1322
            def _probe(self):return False
 
1323
        feature = Unavailable()
 
1324
        self.assertRaises(UnavailableFeature, self.requireFeature, feature)
 
1325
 
 
1326
    def test_run_no_parameters(self):
 
1327
        test = SampleTestCase('_test_pass')
 
1328
        test.run()
 
1329
    
 
1330
    def test_run_enabled_unittest_result(self):
 
1331
        """Test we revert to regular behaviour when the test is enabled."""
 
1332
        test = SampleTestCase('_test_pass')
 
1333
        class EnabledFeature(object):
 
1334
            def available(self):
 
1335
                return True
 
1336
        test._test_needs_features = [EnabledFeature()]
 
1337
        result = unittest.TestResult()
 
1338
        test.run(result)
 
1339
        self.assertEqual(1, result.testsRun)
 
1340
        self.assertEqual([], result.errors)
 
1341
        self.assertEqual([], result.failures)
 
1342
 
 
1343
    def test_run_disabled_unittest_result(self):
 
1344
        """Test our compatability for disabled tests with unittest results."""
 
1345
        test = SampleTestCase('_test_pass')
 
1346
        class DisabledFeature(object):
 
1347
            def available(self):
 
1348
                return False
 
1349
        test._test_needs_features = [DisabledFeature()]
 
1350
        result = unittest.TestResult()
 
1351
        test.run(result)
 
1352
        self.assertEqual(1, result.testsRun)
 
1353
        self.assertEqual([], result.errors)
 
1354
        self.assertEqual([], result.failures)
 
1355
 
 
1356
    def test_run_disabled_supporting_result(self):
 
1357
        """Test disabled tests behaviour with support aware results."""
 
1358
        test = SampleTestCase('_test_pass')
 
1359
        class DisabledFeature(object):
 
1360
            def available(self):
 
1361
                return False
 
1362
        the_feature = DisabledFeature()
 
1363
        test._test_needs_features = [the_feature]
 
1364
        class InstrumentedTestResult(unittest.TestResult):
 
1365
            def __init__(self):
 
1366
                unittest.TestResult.__init__(self)
 
1367
                self.calls = []
 
1368
            def startTest(self, test):
 
1369
                self.calls.append(('startTest', test))
 
1370
            def stopTest(self, test):
 
1371
                self.calls.append(('stopTest', test))
 
1372
            def addNotSupported(self, test, feature):
 
1373
                self.calls.append(('addNotSupported', test, feature))
 
1374
        result = InstrumentedTestResult()
 
1375
        test.run(result)
 
1376
        self.assertEqual([
 
1377
            ('startTest', test),
 
1378
            ('addNotSupported', test, the_feature),
 
1379
            ('stopTest', test),
 
1380
            ],
 
1381
            result.calls)
 
1382
 
892
1383
 
893
1384
@symbol_versioning.deprecated_function(zero_eleven)
894
1385
def sample_deprecated_function():
984
1475
        self.assertIsInstance(bzrlib.bzrdir.BzrDir.open('b')._format,
985
1476
                              bzrlib.bzrdir.BzrDirFormat6)
986
1477
 
987
 
    def test_make_branch_and_mutable_tree(self):
 
1478
    def test_make_branch_and_memory_tree(self):
988
1479
        # we should be able to get a new branch and a mutable tree from
989
1480
        # TestCaseWithTransport
990
1481
        tree = self.make_branch_and_memory_tree('a')
1019
1510
        self.apply_redirected(out, err, None, bzrlib.tests.selftest, 
1020
1511
            test_suite_factory=factory)
1021
1512
        self.assertEqual([True], factory_called)
 
1513
 
 
1514
 
 
1515
class TestSelftestCleanOutput(TestCaseInTempDir):
 
1516
 
 
1517
    def test_clean_output(self):
 
1518
        # test functionality of clean_selftest_output()
 
1519
        self.build_tree(['test0000.tmp/', 'test0001.tmp/',
 
1520
                         'bzrlib/', 'tests/',
 
1521
                         'bzr', 'setup.py', 'test9999.tmp'])
 
1522
 
 
1523
        root = os.getcwdu()
 
1524
        before = os.listdir(root)
 
1525
        before.sort()
 
1526
        self.assertEquals(['bzr','bzrlib','setup.py',
 
1527
                           'test0000.tmp','test0001.tmp',
 
1528
                           'test9999.tmp','tests'],
 
1529
                           before)
 
1530
        clean_selftest_output(root, quiet=True)
 
1531
        after = os.listdir(root)
 
1532
        after.sort()
 
1533
        self.assertEquals(['bzr','bzrlib','setup.py',
 
1534
                           'test9999.tmp','tests'],
 
1535
                           after)
 
1536
 
 
1537
    def test_clean_readonly(self):
 
1538
        # test for delete read-only files
 
1539
        self.build_tree(['test0000.tmp/', 'test0000.tmp/foo'])
 
1540
        osutils.make_readonly('test0000.tmp/foo')
 
1541
        root = os.getcwdu()
 
1542
        before = os.listdir(root);  before.sort()
 
1543
        self.assertEquals(['test0000.tmp'], before)
 
1544
        clean_selftest_output(root, quiet=True)
 
1545
        after = os.listdir(root);   after.sort()
 
1546
        self.assertEquals([], after)
 
1547
 
 
1548
 
 
1549
class TestKnownFailure(TestCase):
 
1550
 
 
1551
    def test_known_failure(self):
 
1552
        """Check that KnownFailure is defined appropriately."""
 
1553
        # a KnownFailure is an assertion error for compatability with unaware
 
1554
        # runners.
 
1555
        self.assertIsInstance(KnownFailure(""), AssertionError)
 
1556
 
 
1557
    def test_expect_failure(self):
 
1558
        try:
 
1559
            self.expectFailure("Doomed to failure", self.assertTrue, False)
 
1560
        except KnownFailure, e:
 
1561
            self.assertEqual('Doomed to failure', e.args[0])
 
1562
        try:
 
1563
            self.expectFailure("Doomed to failure", self.assertTrue, True)
 
1564
        except AssertionError, e:
 
1565
            self.assertEqual('Unexpected success.  Should have failed:'
 
1566
                             ' Doomed to failure', e.args[0])
 
1567
        else:
 
1568
            self.fail('Assertion not raised')
 
1569
 
 
1570
 
 
1571
class TestFeature(TestCase):
 
1572
 
 
1573
    def test_caching(self):
 
1574
        """Feature._probe is called by the feature at most once."""
 
1575
        class InstrumentedFeature(Feature):
 
1576
            def __init__(self):
 
1577
                Feature.__init__(self)
 
1578
                self.calls = []
 
1579
            def _probe(self):
 
1580
                self.calls.append('_probe')
 
1581
                return False
 
1582
        feature = InstrumentedFeature()
 
1583
        feature.available()
 
1584
        self.assertEqual(['_probe'], feature.calls)
 
1585
        feature.available()
 
1586
        self.assertEqual(['_probe'], feature.calls)
 
1587
 
 
1588
    def test_named_str(self):
 
1589
        """Feature.__str__ should thunk to feature_name()."""
 
1590
        class NamedFeature(Feature):
 
1591
            def feature_name(self):
 
1592
                return 'symlinks'
 
1593
        feature = NamedFeature()
 
1594
        self.assertEqual('symlinks', str(feature))
 
1595
 
 
1596
    def test_default_str(self):
 
1597
        """Feature.__str__ should default to __class__.__name__."""
 
1598
        class NamedFeature(Feature):
 
1599
            pass
 
1600
        feature = NamedFeature()
 
1601
        self.assertEqual('NamedFeature', str(feature))
 
1602
 
 
1603
 
 
1604
class TestUnavailableFeature(TestCase):
 
1605
 
 
1606
    def test_access_feature(self):
 
1607
        feature = Feature()
 
1608
        exception = UnavailableFeature(feature)
 
1609
        self.assertIs(feature, exception.args[0])
 
1610
 
 
1611
 
 
1612
class TestSelftestFiltering(TestCase):
 
1613
 
 
1614
    def setUp(self):
 
1615
        self.suite = TestUtil.TestSuite()
 
1616
        self.loader = TestUtil.TestLoader()
 
1617
        self.suite.addTest(self.loader.loadTestsFromModuleNames([
 
1618
            'bzrlib.tests.test_selftest']))
 
1619
        self.all_names = [t.id() for t in iter_suite_tests(self.suite)]
 
1620
 
 
1621
    def test_filter_suite_by_re(self):
 
1622
        filtered_suite = filter_suite_by_re(self.suite, 'test_filter')
 
1623
        filtered_names = [t.id() for t in iter_suite_tests(filtered_suite)]
 
1624
        self.assertEqual(filtered_names, ['bzrlib.tests.test_selftest.'
 
1625
            'TestSelftestFiltering.test_filter_suite_by_re'])
 
1626
            
 
1627
    def test_sort_suite_by_re(self):
 
1628
        sorted_suite = sort_suite_by_re(self.suite, 'test_filter')
 
1629
        sorted_names = [t.id() for t in iter_suite_tests(sorted_suite)]
 
1630
        self.assertEqual(sorted_names[0], 'bzrlib.tests.test_selftest.'
 
1631
            'TestSelftestFiltering.test_filter_suite_by_re')
 
1632
        self.assertEquals(sorted(self.all_names), sorted(sorted_names))
 
1633
 
 
1634
 
 
1635
class TestCheckInventoryShape(TestCaseWithTransport):
 
1636
 
 
1637
    def test_check_inventory_shape(self):
 
1638
        files = ['a', 'b/', 'b/c']
 
1639
        tree = self.make_branch_and_tree('.')
 
1640
        self.build_tree(files)
 
1641
        tree.add(files)
 
1642
        tree.lock_read()
 
1643
        try:
 
1644
            self.check_inventory_shape(tree.inventory, files)
 
1645
        finally:
 
1646
            tree.unlock()