Revision history for this message
Gavin Panella (allenap) wrote : | # |
1 | === modified file 'lib/lp/testing/__init__.py' |
2 | --- lib/lp/testing/__init__.py 2010-03-11 16:37:22 +0000 |
3 | +++ lib/lp/testing/__init__.py 2010-03-12 10:58:17 +0000 |
4 | @@ -593,22 +593,12 @@ |
5 | class ZopeTestInSubProcess: |
6 | """Run tests in a sub-process, respecting Zope idiosyncrasies. |
7 | |
8 | - Use this as a mixin with an interesting `TestCase` or `TestSuite` |
9 | - subclass to quickly isolate tests with side-effects. |
10 | - |
11 | - When mixed-in with a `TestCase`: |
12 | - |
13 | - Each and every test *method* in the test case is run in a new, |
14 | - forked, sub-process. This will slow down your tests, so use it |
15 | - sparingly. However, when you need to, for example, start the |
16 | - Twisted reactor (which cannot currently be safely stopped and |
17 | - restarted in process) it is invaluable. |
18 | - |
19 | - When mixed-in with a `TestSuite`: |
20 | - |
21 | - All tests in this suite are run in a single, newly forked, |
22 | - sub-process. This isolates the parent process from side-effects, |
23 | - but the tests in this suite are not isolated from one another. |
24 | + Use this as a mixin with an interesting `TestCase` to isolate |
25 | + tests with side-effects. Each and every test *method* in the test |
26 | + case is run in a new, forked, sub-process. This will slow down |
27 | + your tests, so use it sparingly. However, when you need to, for |
28 | + example, start the Twisted reactor (which cannot currently be |
29 | + safely stopped and restarted in process) it is invaluable. |
30 | |
31 | This is basically a reimplementation of subunit's |
32 | `IsolatedTestCase` or `IsolatedTestSuite`, but adjusted to work |
33 | |
34 | === modified file 'lib/lp/testing/tests/test_zope_test_in_subprocess.py' |
35 | --- lib/lp/testing/tests/test_zope_test_in_subprocess.py 2010-03-11 21:37:41 +0000 |
36 | +++ lib/lp/testing/tests/test_zope_test_in_subprocess.py 2010-03-15 11:46:49 +0000 |
37 | @@ -1,7 +1,18 @@ |
38 | # Copyright 2010 Canonical Ltd. This software is licensed under the |
39 | # GNU Affero General Public License version 3 (see the file LICENSE). |
40 | |
41 | -"""Test `lp.testing.ZopeTestInSubProcess`.""" |
42 | +"""Test `lp.testing.ZopeTestInSubProcess`. |
43 | + |
44 | +How does it do this? |
45 | + |
46 | +A `TestCase`, mixed-in with `ZopeTestInSubProcess`, is run by the Zope |
47 | +test runner. This test case sets its own layer, to keep track of the |
48 | +PIDs when certain methods are called. It also records pids for its own |
49 | +methods. Assertions are made as these methods are called to ensure that |
50 | +they are running in the correct process - the parent or the child. |
51 | + |
52 | +Recording of the PIDs is handled using the `record_pid` decorator. |
53 | +""" |
54 | |
55 | __metaclass__ = type |
56 | |
57 | @@ -37,11 +48,13 @@ |
58 | because the test case runs before these methods are called. In the |
59 | interests of symmetry and clarity, the assertions for setUp() and |
60 | testSetUp() are done here too. |
61 | + |
62 | + This layer expects to be *instantiated*, which is not the norm for |
63 | + Zope layers. See `TestZopeTestInSubProcess` for its use. |
64 | """ |
65 | |
66 | @record_pid |
67 | - def __init__(self, test): |
68 | - self.test = test |
69 | + def __init__(self): |
70 | # These are needed to satisfy the requirements of the |
71 | # byzantine Zope layer machinery. |
72 | self.__name__ = self.__class__.__name__ |
73 | @@ -54,12 +67,6 @@ |
74 | "layer.setUp() not called in parent process.") |
75 | |
76 | @record_pid |
77 | - def tearDown(self): |
78 | - # Runs in the parent process. |
79 | - assert self.pid_in___init__ == self.pid_in_tearDown, ( |
80 | - "layer.tearDown() not called in parent process.") |
81 | - |
82 | - @record_pid |
83 | def testSetUp(self): |
84 | # Runs in the child process. |
85 | assert self.pid_in___init__ != self.pid_in_testSetUp, ( |
86 | @@ -71,19 +78,30 @@ |
87 | assert self.pid_in_testSetUp == self.pid_in_testTearDown, ( |
88 | "layer.testTearDown() not called in same process as testSetUp().") |
89 | |
90 | + @record_pid |
91 | + def tearDown(self): |
92 | + # Runs in the parent process. |
93 | + assert self.pid_in___init__ == self.pid_in_tearDown, ( |
94 | + "layer.tearDown() not called in parent process.") |
95 | + |
96 | |
97 | class TestZopeTestInSubProcess(ZopeTestInSubProcess, unittest.TestCase): |
98 | """Test `ZopeTestInSubProcess`. |
99 | |
100 | Assert that setUp(), test() and tearDown() are called in the child |
101 | process. |
102 | + |
103 | + Sets its own layer attribute. This layer is then responsible for |
104 | + recording the PID at interesting moments. Specifically, |
105 | + layer.testSetUp() must be called in the same process as |
106 | + test.setUp(). |
107 | """ |
108 | |
109 | @record_pid |
110 | def __init__(self, method_name='runTest'): |
111 | # Runs in the parent process. |
112 | super(TestZopeTestInSubProcess, self).__init__(method_name) |
113 | - self.layer = TestZopeTestInSubProcessLayer(self) |
114 | + self.layer = TestZopeTestInSubProcessLayer() |
115 | |
116 | @record_pid |
117 | def setUp(self): |
118 | @@ -110,9 +128,4 @@ |
119 | |
120 | |
121 | def test_suite(): |
122 | - suite = unittest.TestSuite() |
123 | - loader = unittest.TestLoader() |
124 | - suite.addTests( |
125 | - loader.loadTestsFromTestCase( |
126 | - TestZopeTestInSubProcess)) |
127 | - return suite |
128 | + return unittest.TestLoader().loadTestsFromName(__name__) |
Latest incremental diff, r10440..