Merge lp:~gmb/maas-test/fix-up-proxy-config-dir-for-tests into lp:maas-test
- fix-up-proxy-config-dir-for-tests
- Merge into trunk
Status: | Merged |
---|---|
Merged at revision: | 78 |
Proposed branch: | lp:~gmb/maas-test/fix-up-proxy-config-dir-for-tests |
Merge into: | lp:maas-test |
Diff against target: |
321 lines (+50/-42) 6 files modified
maastest/cases.py (+2/-1) maastest/kvmfixture.py (+9/-2) maastest/proxyfixture.py (+10/-9) maastest/tests/test_kvmfixture.py (+3/-8) maastest/tests/test_proxyfixture.py (+24/-22) packages.txt (+2/-0) |
To merge this branch: | bzr merge lp:~gmb/maas-test/fix-up-proxy-config-dir-for-tests |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Gavin Panella (community) | Approve | ||
Review via email: mp+196918@code.launchpad.net |
Commit message
Description of the change
This branch makes the config_dir of LocalProxyFixture, and the ssh_key_dir of KVMFixture configurable. It also adds a command-line option, --config-dir, which sets both of the above (there's an argument for having ssh_key_dir separate, I suppose; I'm happy to do that if it's a better fit).
- 77. By Graham Binns
-
Fixed a typo.
- 78. By Graham Binns
-
Removed TODO that was TODONE.
Julian Edwards (julian-edwards) wrote : | # |
On Wednesday 27 Nov 2013 16:28:29 you wrote:
> Review: Needs Information
>
> Looks good, but I'm concerned about punting everything to the user.
>
>
> [1]
>
> + # maas-test config
> + parser.
> + '--config-dir', type=text_type,
> + default=
> + help="The directory in which to store maas-test config and cache "
> + "files. Defaults to %(default)s")
>
> I think we should use the xdg stuff I mentioned to rvb yesterday, and
> not have yet another configuration option. Or is there a compelling
> use-case for allowing this? This feels like getting the user to choose
> because we can't make a decision.
+1 to removing config where sane and and possible.
Graham Binns (gmb) wrote : | # |
On 27 November 2013 22:51, Julian Edwards <email address hidden> wrote:
>> I think we should use the xdg stuff I mentioned to rvb yesterday, and
>> not have yet another configuration option. Or is there a compelling
>> use-case for allowing this? This feels like getting the user to choose
>> because we can't make a decision.
I saw that whizz past in a merge proposal and promptly forgot about
it. That makes perfect sense to me.
Julian Edwards (julian-edwards) wrote : | # |
On Thursday 28 Nov 2013 07:21:34 you wrote:
> On 27 November 2013 22:51, Julian Edwards <email address hidden>
wrote:
> >> I think we should use the xdg stuff I mentioned to rvb yesterday, and
> >> not have yet another configuration option. Or is there a compelling
> >> use-case for allowing this? This feels like getting the user to choose
> >> because we can't make a decision.
>
> I saw that whizz past in a merge proposal and promptly forgot about
> it. That makes perfect sense to me.
For the record, I didn't say that, Gavin did :)
Graham Binns (gmb) wrote : | # |
On 28 November 2013 07:24, Julian Edwards <email address hidden> wrote:
> For the record, I didn't say that, Gavin did :)
Yeah, trimming fail.
- 79. By Graham Binns
-
Removed config-dir option stuff; we'll use xdg instead.
- 80. By Graham Binns
-
XDG conversion.
- 81. By Graham Binns
-
Merged trunk.
- 82. By Graham Binns
-
Added dependencies.
- 83. By Graham Binns
-
Trimmed some lint.
- 84. By Graham Binns
-
Removed a TODO.
Gavin Panella (allenap) wrote : | # |
Tip top. One more small thing:
[2]
- os.path.
+ BaseDirectory.
No need for the leading . on .maas-test.
This appears elsewhere too.
Also, fwiw, any number of components can passed to save_config_path(),
for example:
would create a directory at $XDG_CONFIG_
Graham Binns (gmb) wrote : | # |
On 28 November 2013 10:03, Gavin Panella <email address hidden> wrote:
> Review: Approve
>
> Tip top. One more small thing:
>
>
> [2]
>
> - os.path.
> + BaseDirectory.
>
> No need for the leading . on .maas-test.
>
> This appears elsewhere too.
On it.
> Also, fwiw, any number of components can passed to save_config_path(),
> for example:
>
> BaseDirectory.
>
> would create a directory at $XDG_CONFIG_
Ah, but we don't want to create a directory there (I've improved the
code so that's more obvious). vm_ssh_id_rsa is the name of the
keyfile, so we need to make sure the directory is there and then
create the path to the file from it. As I said, I've improved the
clarity.
- 85. By Graham Binns
-
Fixed an assortment of wonderful things.
- 86. By Graham Binns
-
Removed unused imports.
Gavin Panella (allenap) wrote : | # |
> Ah, but we don't want to create a directory there (I've improved the
> code so that's more obvious).
I did understand that - your code was clear - I was just pointing it out
for future reference.
Graham Binns (gmb) wrote : | # |
On 28 November 2013 14:25, Gavin Panella <email address hidden> wrote:
> I did understand that - your code was clear - I was just pointing it out
> for future reference.
Okay, cool. Thanks for the clarification.
Preview Diff
1 | === modified file 'maastest/cases.py' |
2 | --- maastest/cases.py 2013-11-27 17:22:21 +0000 |
3 | +++ maastest/cases.py 2013-11-28 14:16:14 +0000 |
4 | @@ -129,11 +129,12 @@ |
5 | "URL: http://%s/MAAS/\n" |
6 | "Username: %s\n" |
7 | "Password: %s\n" |
8 | - "SSH login: ssh -i ~/.maas-test/vm_ssh_id_rsa %s\n" |
9 | + "SSH login: ssh -i %s %s\n" |
10 | % ( |
11 | self.machine.ip_address(), |
12 | self.maas.admin_user, |
13 | self.maas.admin_password, |
14 | + self.machine.ssh_private_key_file, |
15 | self.machine.identity(), |
16 | )) |
17 | |
18 | |
19 | === modified file 'maastest/kvmfixture.py' |
20 | --- maastest/kvmfixture.py 2013-11-27 13:36:27 +0000 |
21 | +++ maastest/kvmfixture.py 2013-11-28 14:16:14 +0000 |
22 | @@ -34,6 +34,7 @@ |
23 | import netaddr |
24 | from six import text_type |
25 | from testtools.content import text_content |
26 | +from xdg import BaseDirectory |
27 | |
28 | # Maximum wait for the virtual machine to complete its cloud-init |
29 | # initialization. It can take quite a while, because it performs an |
30 | @@ -67,7 +68,7 @@ |
31 | """ |
32 | def __init__(self, series, architecture, proxy_url, |
33 | direct_interface=None, direct_network=None, name=None, |
34 | - archive=None): |
35 | + archive=None, ssh_key_dir=None): |
36 | """Initialise a KVM-based Virtual Machine fixture. |
37 | |
38 | The VM's network is configured like this: |
39 | @@ -103,6 +104,10 @@ |
40 | :param archive: An optional repository name. If provided, the |
41 | repository will be added onto the VM. |
42 | :type archive: string |
43 | + :param ssh_key_dir: The directory in which to store the SSH keys |
44 | + for connecting to this KVM instance. If None, this defaults |
45 | + to the default XDG config directory. |
46 | + :type ssh_key_dir: string. |
47 | """ |
48 | super(KVMFixture, self).__init__() |
49 | self.command_count = itertools.count(1) |
50 | @@ -124,8 +129,10 @@ |
51 | if name is None: |
52 | name = text_type(uuid1()) |
53 | self.name = name |
54 | + if ssh_key_dir is None: |
55 | + ssh_key_dir = BaseDirectory.save_config_path('maas-test') |
56 | self.ssh_private_key_file = os.path.join( |
57 | - os.path.expanduser('~'), '.maas-test', 'vm_ssh_id_rsa') |
58 | + ssh_key_dir, 'vm_ssh_id_rsa') |
59 | self.running = False |
60 | |
61 | def setUp(self): |
62 | |
63 | === modified file 'maastest/proxyfixture.py' |
64 | --- maastest/proxyfixture.py 2013-11-27 13:36:27 +0000 |
65 | +++ maastest/proxyfixture.py 2013-11-28 14:16:14 +0000 |
66 | @@ -23,10 +23,9 @@ |
67 | from maastest import utils |
68 | from netaddr import IPNetwork |
69 | import netifaces |
70 | +from xdg import BaseDirectory |
71 | |
72 | -# TODO: '.maas-test' shouln't be harcoded like that, it should |
73 | -# be a parameter passed to LocalProxyFixture(). |
74 | -DISK_CACHE_ROOT = '~/.maas-test/proxy_cache/' |
75 | +DISK_CACHE_ROOT = '%(config_dir)s/proxy_cache/' |
76 | |
77 | PROXY_CONFIG_ITEMS = { |
78 | 'daemonise': 'true', |
79 | @@ -59,7 +58,7 @@ |
80 | |
81 | #TODO: port should be determined at runtime from the set of |
82 | # available ports rather than being an arbitrary one as it is here. |
83 | - def __init__(self, port=42676): |
84 | + def __init__(self, config_dir=None, port=42676): |
85 | """Create a `LocalProxyFixture` object. |
86 | |
87 | :param url: The URL of the proxy to use. If None, LocalProxyFixture |
88 | @@ -68,13 +67,15 @@ |
89 | :param port: The port on which to start a local caching proxy. |
90 | If URL is specified, this parameter is ignored. |
91 | :type port: int |
92 | + :param config_dir: The directory in which to put the proxy's |
93 | + config, pid file and cache. |
94 | + :type config_dir: string |
95 | """ |
96 | super(LocalProxyFixture, self).__init__() |
97 | self.port = port |
98 | - # TODO: '.maas-test' shouln't be harcoded like that, it should |
99 | - # be a parameter passed to LocalProxyFixture(). |
100 | - self.config_dir = os.path.join( |
101 | - os.path.expanduser('~'), '.maas-test') |
102 | + if config_dir is None: |
103 | + config_dir = BaseDirectory.save_config_path('maas-test') |
104 | + self.config_dir = config_dir |
105 | self.pid_file = os.path.join(self.config_dir, 'proxy.pid') |
106 | self._network_address = None |
107 | |
108 | @@ -132,7 +133,7 @@ |
109 | logging.info("Done starting proxy.") |
110 | |
111 | def create_cache_root(self): |
112 | - cache_root = os.path.expanduser(DISK_CACHE_ROOT) |
113 | + cache_root = DISK_CACHE_ROOT % {'config_dir': self.config_dir} |
114 | try: |
115 | os.makedirs(cache_root) |
116 | except OSError as error: |
117 | |
118 | === modified file 'maastest/tests/test_kvmfixture.py' |
119 | --- maastest/tests/test_kvmfixture.py 2013-11-27 17:44:58 +0000 |
120 | +++ maastest/tests/test_kvmfixture.py 2013-11-28 14:16:14 +0000 |
121 | @@ -13,8 +13,6 @@ |
122 | __all__ = [] |
123 | |
124 | import itertools |
125 | -import os |
126 | -import os.path |
127 | import random |
128 | from random import randint |
129 | import textwrap |
130 | @@ -49,9 +47,7 @@ |
131 | # KVMFixture.generate_ssh_key() generates an ssh key in ~/.maas-test, |
132 | # creating that directory if necessary. Set up a fake home directory |
133 | # so it can do what it needs to. |
134 | - home_dir = self.useFixture(fixtures.TempDir()).path |
135 | - self.patch( |
136 | - os.path, 'expanduser', mock.MagicMock(return_value=home_dir)) |
137 | + self.home_dir = self.useFixture(fixtures.TempDir()).path |
138 | |
139 | def patch_run_command(self, return_value=0, stdout=b'', stderr=b''): |
140 | """Patch out `kvmfixture` calls to `run_command`. |
141 | @@ -84,7 +80,7 @@ |
142 | series, architecture, name=name, |
143 | direct_interface=direct_interface, |
144 | direct_network=direct_network, archive=archive, |
145 | - proxy_url=proxy_url) |
146 | + proxy_url=proxy_url, ssh_key_dir=self.home_dir) |
147 | # Hack to get fixture.addDetail to work without actually calling |
148 | # fixture.setUp(). |
149 | fixture._details = {} |
150 | @@ -288,7 +284,6 @@ |
151 | self.logger.output.strip().split("\n")) |
152 | |
153 | def test_generate_ssh_key_sets_up_temporary_key_pair(self): |
154 | - home_dir = os.path.expanduser('~') |
155 | fixture = self.make_KVMFixture() |
156 | fixtures.Fixture.setUp(fixture) |
157 | |
158 | @@ -297,7 +292,7 @@ |
159 | self.assertThat(fixture.ssh_private_key_file, FileExists()) |
160 | self.assertThat(fixture.get_ssh_public_key_file(), FileExists()) |
161 | self.assertThat( |
162 | - fixture.ssh_private_key_file, StartsWith(home_dir + '/')) |
163 | + fixture.ssh_private_key_file, StartsWith(self.home_dir + '/')) |
164 | |
165 | self.assertThat( |
166 | fixture.ssh_private_key_file, |
167 | |
168 | === modified file 'maastest/tests/test_proxyfixture.py' |
169 | --- maastest/tests/test_proxyfixture.py 2013-11-26 22:51:09 +0000 |
170 | +++ maastest/tests/test_proxyfixture.py 2013-11-28 14:16:14 +0000 |
171 | @@ -39,24 +39,23 @@ |
172 | 'netmask': '255.255.255.0', |
173 | }]} |
174 | self.patch(netifaces, 'ifaddresses', mock_ifaddresses) |
175 | + self.temp_dir = self.useFixture(TempDir()).path |
176 | |
177 | def get_random_port_number(self): |
178 | return random.randint(1, 65535) |
179 | |
180 | def test_init_sets_properties(self): |
181 | port = self.get_random_port_number() |
182 | - proxy_fixture = LocalProxyFixture(port=port) |
183 | - expected_config_path = os.path.join( |
184 | - os.path.expanduser('~'), '.maas-test') |
185 | + proxy_fixture = LocalProxyFixture(port=port, config_dir=self.temp_dir) |
186 | self.assertEqual(port, proxy_fixture.port) |
187 | - self.assertEqual(expected_config_path, proxy_fixture.config_dir) |
188 | + self.assertEqual(self.temp_dir, proxy_fixture.config_dir) |
189 | self.assertEqual( |
190 | - os.path.join(expected_config_path, 'proxy.pid'), |
191 | + os.path.join(self.temp_dir, 'proxy.pid'), |
192 | proxy_fixture.pid_file) |
193 | |
194 | def test_get_url_returns_proxy_url(self): |
195 | port = self.get_random_port_number() |
196 | - proxy_fixture = LocalProxyFixture(port=port) |
197 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir, port=port) |
198 | self.assertEqual( |
199 | "http://192.168.0.1:%s" % port, |
200 | proxy_fixture.get_url()) |
201 | @@ -65,8 +64,9 @@ |
202 | self.patch(LocalProxyFixture, 'create_cache_root', mock.MagicMock()) |
203 | self.patch(LocalProxyFixture, 'start_proxy', mock.MagicMock()) |
204 | |
205 | - random_port = self.get_random_port_number() |
206 | - with LocalProxyFixture(port=random_port) as fixture: |
207 | + port = self.get_random_port_number() |
208 | + config_dir = self.temp_dir |
209 | + with LocalProxyFixture(config_dir=config_dir, port=port) as fixture: |
210 | pass |
211 | |
212 | self.assertEqual( |
213 | @@ -79,7 +79,8 @@ |
214 | def test_start_proxy_starts_proxy(self): |
215 | mock_run_command = mock.MagicMock() |
216 | self.patch(utils, 'run_command', mock_run_command) |
217 | - proxy_fixture = LocalProxyFixture(port=self.get_random_port_number()) |
218 | + proxy_fixture = LocalProxyFixture( |
219 | + config_dir=self.temp_dir, port=self.get_random_port_number()) |
220 | |
221 | proxy_fixture.start_proxy() |
222 | |
223 | @@ -90,26 +91,27 @@ |
224 | mock_run_command.mock_calls[-1]) |
225 | |
226 | def test_create_cache_root_creates_directory(self): |
227 | - temp_dir = self.useFixture(TempDir()).path |
228 | - test_cache_path = temp_dir + "path" |
229 | - self.patch(proxyfixture, 'DISK_CACHE_ROOT', test_cache_path) |
230 | - proxy_fixture = LocalProxyFixture(port=self.get_random_port_number()) |
231 | + proxy_fixture = LocalProxyFixture( |
232 | + config_dir=self.temp_dir, port=self.get_random_port_number()) |
233 | |
234 | proxy_fixture.create_cache_root() |
235 | - |
236 | - self.assertThat(test_cache_path, DirExists()) |
237 | + expected_cache_path = proxyfixture.DISK_CACHE_ROOT % { |
238 | + 'config_dir': self.temp_dir} |
239 | + self.assertThat(expected_cache_path, DirExists()) |
240 | |
241 | def test_create_cache_root_ignores_existing_directory(self): |
242 | temp_dir = self.useFixture(TempDir()).path |
243 | self.patch(proxyfixture, 'DISK_CACHE_ROOT', temp_dir) |
244 | - proxy_fixture = LocalProxyFixture(port=self.get_random_port_number()) |
245 | + proxy_fixture = LocalProxyFixture( |
246 | + config_dir=self.temp_dir, port=self.get_random_port_number()) |
247 | |
248 | proxy_fixture.create_cache_root() |
249 | |
250 | self.assertThat(temp_dir, DirExists()) |
251 | |
252 | def test_get_network_address(self): |
253 | - proxy_fixture = LocalProxyFixture(port=self.get_random_port_number()) |
254 | + proxy_fixture = LocalProxyFixture( |
255 | + config_dir=self.temp_dir, port=self.get_random_port_number()) |
256 | proxy_adddress = proxy_fixture._get_network_address() |
257 | self.assertEqual('192.168.0.1', proxy_adddress.ip.format()) |
258 | self.assertEqual(24, proxy_adddress.prefixlen) |
259 | @@ -120,7 +122,7 @@ |
260 | mock_read_file = mock.MagicMock() |
261 | mock_read_file.return_value = bytes(self.getUniqueInteger()) |
262 | self.patch(utils, 'read_file', mock_read_file) |
263 | - proxy_fixture = LocalProxyFixture() |
264 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir) |
265 | proxy_fixture.kill_running_proxy() |
266 | self.assertEqual( |
267 | mock.call(['kill', mock_read_file.return_value], check_call=True), |
268 | @@ -132,7 +134,7 @@ |
269 | mock_read_file = mock.MagicMock() |
270 | mock_read_file.side_effect = Exception(self.getUniqueString()) |
271 | self.patch(utils, 'read_file', mock_read_file) |
272 | - proxy_fixture = LocalProxyFixture() |
273 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir) |
274 | proxy_fixture.kill_running_proxy() |
275 | mock_log_error.assert_has_calls([ |
276 | mock.call("Unable to kill proxy:"), |
277 | @@ -147,7 +149,7 @@ |
278 | mock_read_file = mock.MagicMock() |
279 | mock_read_file.return_value = bytes(self.getUniqueInteger()) |
280 | self.patch(utils, 'read_file', mock_read_file) |
281 | - proxy_fixture = LocalProxyFixture() |
282 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir) |
283 | proxy_fixture.kill_running_proxy() |
284 | mock_log_error.assert_has_calls([ |
285 | mock.call("Unable to kill proxy:"), |
286 | @@ -162,7 +164,7 @@ |
287 | mock_kill_running_proxy = mock.MagicMock() |
288 | |
289 | port = self.get_random_port_number() |
290 | - proxy_fixture = LocalProxyFixture(port) |
291 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir, port=port) |
292 | self.patch( |
293 | proxy_fixture, 'kill_running_proxy', mock_kill_running_proxy) |
294 | |
295 | @@ -174,5 +176,5 @@ |
296 | mock_exists = mock.MagicMock() |
297 | mock_exists.return_value = True |
298 | self.patch(os.path, 'exists', mock_exists) |
299 | - proxy_fixture = LocalProxyFixture() |
300 | + proxy_fixture = LocalProxyFixture(config_dir=self.temp_dir) |
301 | self.assertRaises(Exception, proxy_fixture.setUp) |
302 | |
303 | === modified file 'packages.txt' |
304 | --- packages.txt 2013-11-26 13:10:43 +0000 |
305 | +++ packages.txt 2013-11-28 14:16:14 +0000 |
306 | @@ -11,6 +11,7 @@ |
307 | python-testresources |
308 | python-testtools |
309 | python-virtualenv |
310 | +python-xdg |
311 | python3-fixtures |
312 | python3-lxml |
313 | python3-mock |
314 | @@ -18,6 +19,7 @@ |
315 | python3-six |
316 | python3-testresources |
317 | python3-testtools |
318 | +python3-xdg |
319 | qemu-kvm |
320 | uvtool |
321 | uvtool-libvirt |
Looks good, but I'm concerned about punting everything to the user.
[1]
+ # maas-test config add_argument( "~/.maas- test",
+ parser.
+ '--config-dir', type=text_type,
+ default=
+ help="The directory in which to store maas-test config and cache "
+ "files. Defaults to %(default)s")
I think we should use the xdg stuff I mentioned to rvb yesterday, and
not have yet another configuration option. Or is there a compelling
use-case for allowing this? This feels like getting the user to choose
because we can't make a decision.