Merge lp:~cprov/uci-engine/1335753-glance-creds into lp:uci-engine
- 1335753-glance-creds
- Merge into trunk
Status: | Needs review |
---|---|
Proposed branch: | lp:~cprov/uci-engine/1335753-glance-creds |
Merge into: | lp:uci-engine |
Diff against target: |
332 lines (+203/-32) 5 files modified
ci-utils/ci_utils/tests/test_unit_config.py (+125/-0) ci-utils/ci_utils/unit_config.py (+57/-16) juju-deployer/configs/unit_config.yaml.tmpl (+13/-5) juju-deployer/deploy.py (+6/-6) juju-deployer/test_deploy.py (+2/-5) |
To merge this branch: | bzr merge lp:~cprov/uci-engine/1335753-glance-creds |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
PS Jenkins bot (community) | continuous-integration | Needs Fixing | |
Andy Doan (community) | Approve | ||
Vincent Ladeuil (community) | Needs Fixing | ||
Review via email: mp+225248@code.launchpad.net |
Commit message
Independent set of credentials for ImageBuilder and TestRunner in unit_config.
Description of the change
Resuming Vincent's work for creating an independent set of credentials for using in ImageBuilder and TestRunner, since they may operate in an different environment (cloud) than they are deployed.
Original MP -> https:/
- 634. By Celso Providelo
-
adding missing test.
- 635. By Celso Providelo
-
Adding missing docstring.
PS Jenkins bot (ps-jenkins) wrote : | # |
- 636. By Celso Providelo
-
Fixing test failures.
PS Jenkins bot (ps-jenkins) wrote : | # |
PASSED: Continuous integration, rev:636
http://
Executed test runs:
Click here to trigger a rebuild:
http://
Vincent Ladeuil (vila) wrote : | # |
Typos aside, there is an issue with tests creating and removing unit_config at the root of the branch.
With a full deployment available on hp and GLANCE_* vars defined, I get:
$ ./run-tests
<...>
=======
ERROR: tests.test_
-------
Traceback (most recent call last):
File "tests/
raise_
File "/home/
conn, channel = declare_
File "/home/
raise e
error: [Errno 110] Connection timed out
=======
FAIL: juju-deployer.
-------
Traceback (most recent call last):
File "build/
return func(*args, **keywargs)
File "juju-deployer/
self.
File "/usr/lib/
assertion_
File "/usr/lib/
raise self.failureExc
AssertionError: '' != '<email address hidden>'
Ran 594 tests in 501.909s
FAILED (failures=2)
test_process_tickey is now understood as missing an exposed rabbit.
But re-running:
$ ./run-tests
<...>
=======
ERROR: test_runner.
-------
Traceback (most recent call last):
File "test_runner/
tstrun.
File "test_runner/
with open(path) as f:
IOError: [Errno 2] No such file or directory: '/home/
=======
ERROR: test_runner.
-------
Traceback (most recent call last):
File "test_runner/
tstrun.
File "test_runner/
with open(path) as f:
IOError: [Errno 2] No such file or directory: '/home/
=======
ERROR: test_runner.
-------
Vincent Ladeuil (vila) wrote : | # |
I'll dig further and try to fix those.
- 637. By Celso Providelo
-
merge trunk
- 638. By Celso Providelo
-
FIxing typos and test env var isolation.
Celso Providelo (cprov) wrote : | # |
The fact that we have tests that depend on 'unit_config' on the project root is wrong, in fact. If it's not committed in the VCS it should be handled ad-hoc by a testing fixture.
Also, the only test that needs to exercise disk operations with 'unit_config' is the one I've added in this branch, all the rest of the system should mock get_auth_config() and use whatever result they expect.
PS Jenkins bot (ps-jenkins) wrote : | # |
PASSED: Continuous integration, rev:638
http://
Executed test runs:
Click here to trigger a rebuild:
http://
Vincent Ladeuil (vila) wrote : | # |
> The fact that we have tests that depend on 'unit_config' on the project root
> is wrong, in fact.
> If it's not committed in the VCS it should be handled ad-
> hoc by a testing fixture.
There is more than one way to do it :)
The tests that rely on unit_config do use fixtures but still let the user decide whether or not he want to run those tests by creating that file or not.
If you have a better way that doesn't break the existing tests, I'm fine with that.
>
> Also, the only test that needs to exercise disk operations with 'unit_config'
> is the one I've added in this branch, all the rest of the system should mock
> get_auth_config() and use whatever result they expect.
Yes, that's the point I raised when you introduced deploy.
Andy Doan (doanac) wrote : | # |
I mostly like it. I noticed a bug a though. I think any test failing because it assumes the location of the unit-config should be considered broken. I've got MP's on the way:
https:/
that are placing unit_config *outside* our code directory, so moving forward this assumption will definitely not work.
Celso Providelo (cprov) wrote : | # |
Thanks for the review Andy, comments addressed inline.
- 639. By Celso Providelo
-
Re-implement unit_config module get() for not breaking possibly untested code.
PS Jenkins bot (ps-jenkins) wrote : | # |
PASSED: Continuous integration, rev:639
http://
Executed test runs:
Click here to trigger a rebuild:
http://
- 640. By Celso Providelo
-
unit_config.get() not deprecated anymore, it's useful.
PS Jenkins bot (ps-jenkins) wrote : | # |
PASSED: Continuous integration, rev:640
http://
Executed test runs:
Click here to trigger a rebuild:
http://
- 641. By Celso Providelo
-
merge trunk
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:641
http://
Executed test runs:
Click here to trigger a rebuild:
http://
Unmerged revisions
- 641. By Celso Providelo
-
merge trunk
- 640. By Celso Providelo
-
unit_config.get() not deprecated anymore, it's useful.
- 639. By Celso Providelo
-
Re-implement unit_config module get() for not breaking possibly untested code.
- 638. By Celso Providelo
-
FIxing typos and test env var isolation.
- 637. By Celso Providelo
-
merge trunk
- 636. By Celso Providelo
-
Fixing test failures.
- 635. By Celso Providelo
-
Adding missing docstring.
- 634. By Celso Providelo
-
adding missing test.
- 633. By Celso Providelo
-
Making GLANCE_* variables optional and adding tests for ci_utils.
unit_config.
Preview Diff
1 | === added file 'ci-utils/ci_utils/tests/test_unit_config.py' | |||
2 | --- ci-utils/ci_utils/tests/test_unit_config.py 1970-01-01 00:00:00 +0000 | |||
3 | +++ ci-utils/ci_utils/tests/test_unit_config.py 2014-07-04 21:48:29 +0000 | |||
4 | @@ -0,0 +1,125 @@ | |||
5 | 1 | #!/usr/bin/env python | ||
6 | 2 | # Ubuntu CI Engine | ||
7 | 3 | # Copyright 2014 Canonical Ltd. | ||
8 | 4 | |||
9 | 5 | # This program is free software: you can redistribute it and/or modify it | ||
10 | 6 | # under the terms of the GNU Affero General Public License version 3, as | ||
11 | 7 | # published by the Free Software Foundation. | ||
12 | 8 | |||
13 | 9 | # This program is distributed in the hope that it will be useful, but | ||
14 | 10 | # WITHOUT ANY WARRANTY; without even the implied warranties of | ||
15 | 11 | # MERCHANTABILITY, SATISFACTORY QUALITY, or FITNESS FOR A PARTICULAR | ||
16 | 12 | # PURPOSE. See the GNU Affero General Public License for more details. | ||
17 | 13 | |||
18 | 14 | # You should have received a copy of the GNU Affero General Public License | ||
19 | 15 | # along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
20 | 16 | """Tests for the 'unit_config' loader.""" | ||
21 | 17 | import os | ||
22 | 18 | import unittest | ||
23 | 19 | |||
24 | 20 | from ci_utils import unit_config | ||
25 | 21 | |||
26 | 22 | |||
27 | 23 | class TestUnitConfig(unittest.TestCase): | ||
28 | 24 | |||
29 | 25 | sample_content = { | ||
30 | 26 | 'auth_user': 'a_user', | ||
31 | 27 | } | ||
32 | 28 | |||
33 | 29 | def setUp(self): | ||
34 | 30 | """Reset configuration cache.""" | ||
35 | 31 | unit_config._reset_config() | ||
36 | 32 | self.config_path = unit_config._get_config_path() | ||
37 | 33 | |||
38 | 34 | def test_asserts_exists(self): | ||
39 | 35 | # `get_auth_config` asserts the 'unit_config' path exists. | ||
40 | 36 | with self.assertRaises(AssertionError) as cm: | ||
41 | 37 | unit_config.get_auth_config() | ||
42 | 38 | msg = 'unit_config does not exist! ({})'.format(self.config_path) | ||
43 | 39 | self.assertEqual(msg, cm.exception.message) | ||
44 | 40 | |||
45 | 41 | def test_asserts_not_empty(self): | ||
46 | 42 | # `get_auth_config` asserts the 'unit_config' is not an empty file. | ||
47 | 43 | with open(self.config_path, 'w') as fd: | ||
48 | 44 | fd.write('') | ||
49 | 45 | with self.assertRaises(AssertionError) as cm: | ||
50 | 46 | unit_config.get_auth_config() | ||
51 | 47 | msg = 'unit_config is empty! ({})'.format(self.config_path) | ||
52 | 48 | self.assertEqual(msg, cm.exception.message) | ||
53 | 49 | |||
54 | 50 | def create_config(self, content=None): | ||
55 | 51 | """Creates a 'unit_config' pseudo-YAML for tests.""" | ||
56 | 52 | options = self.sample_content.copy() | ||
57 | 53 | if content is not None: | ||
58 | 54 | options.update(content) | ||
59 | 55 | with open(self.config_path, 'w') as fd: | ||
60 | 56 | for k, v in options.iteritems(): | ||
61 | 57 | fd.write('{}: {}\n'.format(k, v)) | ||
62 | 58 | |||
63 | 59 | def drop_if_exists(): | ||
64 | 60 | if os.path.exists(self.config_path): | ||
65 | 61 | os.remove(self.config_path) | ||
66 | 62 | # Delete testing config if it exists. | ||
67 | 63 | self.addCleanup(drop_if_exists) | ||
68 | 64 | |||
69 | 65 | def test_loading(self): | ||
70 | 66 | # `get_auth_config` returns a dictionary corresponding to the | ||
71 | 67 | # YAML content. 'auth_*' attributes are mirrored to 'glance_auth_*' | ||
72 | 68 | self.create_config() | ||
73 | 69 | config = unit_config.get_auth_config() | ||
74 | 70 | self.assertEqual( | ||
75 | 71 | {'auth_user': 'a_user', 'glance_auth_user': 'a_user'}, config) | ||
76 | 72 | |||
77 | 73 | def test_get(self): | ||
78 | 74 | # `get` returns specific configuration options/attributes. | ||
79 | 75 | self.create_config() | ||
80 | 76 | self.assertEqual('a_user', unit_config.get('auth_user')) | ||
81 | 77 | self.assertEqual('a_user', unit_config.get('glance_auth_user')) | ||
82 | 78 | |||
83 | 79 | def test_loading_glance(self): | ||
84 | 80 | # `get_auth_config` preserves original 'glance_auth_*' | ||
85 | 81 | # attributes if 'glance_auth_user' is not empty. | ||
86 | 82 | glance_spec = { | ||
87 | 83 | 'auth_url': 'a_url', | ||
88 | 84 | 'glance_auth_user': 'another_user', | ||
89 | 85 | 'glance_auth_url': 'another_url', | ||
90 | 86 | } | ||
91 | 87 | self.create_config(content=glance_spec) | ||
92 | 88 | config = unit_config.get_auth_config() | ||
93 | 89 | self.assertEqual( | ||
94 | 90 | {'auth_url': 'a_url', | ||
95 | 91 | 'auth_user': 'a_user', | ||
96 | 92 | 'glance_auth_url': 'another_url', | ||
97 | 93 | 'glance_auth_user': 'another_user'}, | ||
98 | 94 | config) | ||
99 | 95 | |||
100 | 96 | def test_cache(self): | ||
101 | 97 | # `get_auth_config` loads configuration file contents only once | ||
102 | 98 | # and caches it's (parsed) results. `_reset_config` is a testing | ||
103 | 99 | # artifact for cleaning its cache (use with care!). | ||
104 | 100 | self.create_config() | ||
105 | 101 | config = unit_config.get_auth_config() | ||
106 | 102 | self.create_config(content={'auth_user': 'fresh'}) | ||
107 | 103 | cached = unit_config.get_auth_config() | ||
108 | 104 | self.assertEqual(cached, config) | ||
109 | 105 | unit_config._reset_config() | ||
110 | 106 | fresh = unit_config.get_auth_config() | ||
111 | 107 | self.assertEqual( | ||
112 | 108 | {'auth_user': 'fresh', 'glance_auth_user': 'fresh'}, | ||
113 | 109 | fresh) | ||
114 | 110 | |||
115 | 111 | def test_no_cache_poisoning(self): | ||
116 | 112 | # `get_auth_config` returns a copy of the configuration cache, | ||
117 | 113 | # so its cache cannot be *poisoned*. | ||
118 | 114 | self.create_config() | ||
119 | 115 | config = unit_config.get_auth_config() | ||
120 | 116 | config['auth_user'] = 'someone-else' | ||
121 | 117 | config['auth_poison'] = 'bad-data' | ||
122 | 118 | new_config = unit_config.get_auth_config() | ||
123 | 119 | self.assertEqual( | ||
124 | 120 | {'auth_user': 'a_user', 'glance_auth_user': 'a_user'}, | ||
125 | 121 | new_config) | ||
126 | 122 | |||
127 | 123 | |||
128 | 124 | if __name__ == "__main__": | ||
129 | 125 | unittest.main() | ||
130 | 0 | 126 | ||
131 | === modified file 'ci-utils/ci_utils/unit_config.py' | |||
132 | --- ci-utils/ci_utils/unit_config.py 2014-05-14 09:11:00 +0000 | |||
133 | +++ ci-utils/ci_utils/unit_config.py 2014-07-04 21:48:29 +0000 | |||
134 | @@ -12,35 +12,76 @@ | |||
135 | 12 | 12 | ||
136 | 13 | # You should have received a copy of the GNU Affero General Public License | 13 | # You should have received a copy of the GNU Affero General Public License |
137 | 14 | # along with this program. If not, see <http://www.gnu.org/licenses/>. | 14 | # along with this program. If not, see <http://www.gnu.org/licenses/>. |
139 | 15 | 15 | """Application 'unit_config' loader.""" | |
140 | 16 | import os | 16 | import os |
141 | 17 | |||
142 | 18 | import yaml | 17 | import yaml |
143 | 19 | 18 | ||
144 | 20 | 19 | ||
145 | 21 | HERE = os.path.abspath(os.path.dirname(__file__)) | 20 | HERE = os.path.abspath(os.path.dirname(__file__)) |
146 | 22 | |||
147 | 23 | |||
148 | 24 | _unit_config = None | 21 | _unit_config = None |
149 | 25 | 22 | ||
150 | 26 | 23 | ||
153 | 27 | def _load(): | 24 | def _reset_config(): |
154 | 28 | path = os.path.join(HERE, '../../unit_config') | 25 | """Testing utility for reseting unit_config cache.""" |
155 | 26 | global _unit_config | ||
156 | 27 | _unit_config = None | ||
157 | 28 | |||
158 | 29 | |||
159 | 30 | def _get_config_path(): | ||
160 | 31 | """Testing utility for retrieving the configuration path.""" | ||
161 | 32 | return os.path.join(HERE, '../../unit_config') | ||
162 | 33 | |||
163 | 34 | |||
164 | 35 | def _load_config(): | ||
165 | 36 | """Load the configuration file as YAML and cache it. | ||
166 | 37 | |||
167 | 38 | Asserts the expected 'unit_config' exists and contains valid YAML. | ||
168 | 39 | """ | ||
169 | 40 | global _unit_config | ||
170 | 41 | path = _get_config_path() | ||
171 | 42 | assert os.path.exists(path), ( | ||
172 | 43 | 'unit_config does not exist! ({})'.format(path)) | ||
173 | 29 | with open(path) as f: | 44 | with open(path) as f: |
174 | 30 | global _unit_config | ||
175 | 31 | _unit_config = yaml.safe_load(f) | 45 | _unit_config = yaml.safe_load(f) |
176 | 46 | assert _unit_config is not None, ( | ||
177 | 47 | 'unit_config is empty! ({})'.format(path)) | ||
178 | 48 | |||
179 | 49 | |||
180 | 50 | def get_auth_config(): | ||
181 | 51 | """Return a configuration dictionary for applications. | ||
182 | 52 | |||
183 | 53 | Loads the deployment 'unit_config' YAML file, if it wasn't loaded | ||
184 | 54 | before, and return the corresponding python dictionary. | ||
185 | 55 | |||
186 | 56 | If 'glance_auth_user' is undefined (empty), 'glance_*' parameters | ||
187 | 57 | are filled with the corresponding 'auth_*' values, i.e., GLANCE_* | ||
188 | 58 | variables only have to be defined when the ci-airline 'testbed' | ||
189 | 59 | environment is different than where the system is deployed e.g.: | ||
190 | 60 | - stagingstack + scalingstack | ||
191 | 61 | - stagingstack + hpcloud | ||
192 | 62 | """ | ||
193 | 63 | global _unit_config | ||
194 | 64 | if _unit_config is None: | ||
195 | 65 | _load_config() | ||
196 | 66 | |||
197 | 67 | # Apply configuration defaults/overrides in a copy of the cached | ||
198 | 68 | # configuration dictionary. This way applications will not be able | ||
199 | 69 | # to poisoning the cached value. | ||
200 | 70 | cfg = _unit_config.copy() | ||
201 | 71 | |||
202 | 72 | # 'glance_*' defaults. | ||
203 | 73 | if cfg.get('glance_auth_user') is None: | ||
204 | 74 | auth_keys = [k for k in cfg.keys() if k.startswith('auth_')] | ||
205 | 75 | for auth_key in auth_keys: | ||
206 | 76 | glance_key = 'glance_' + auth_key | ||
207 | 77 | cfg[glance_key] = cfg[auth_key] | ||
208 | 78 | |||
209 | 79 | return cfg | ||
210 | 32 | 80 | ||
211 | 33 | 81 | ||
212 | 34 | def get(key): | 82 | def get(key): |
222 | 35 | if not _unit_config: | 83 | """Get specific 'unit_config' options.""" |
223 | 36 | _load() | 84 | return get_auth_config()[key] |
215 | 37 | return _unit_config[key] | ||
216 | 38 | |||
217 | 39 | |||
218 | 40 | def get_auth_config(): | ||
219 | 41 | if not _unit_config: | ||
220 | 42 | _load() | ||
221 | 43 | return _unit_config | ||
224 | 44 | 85 | ||
225 | 45 | 86 | ||
226 | 46 | def is_hpcloud(string=None): | 87 | def is_hpcloud(string=None): |
227 | 47 | 88 | ||
228 | === modified file 'juju-deployer/configs/unit_config.yaml.tmpl' | |||
229 | --- juju-deployer/configs/unit_config.yaml.tmpl 2014-07-01 15:58:10 +0000 | |||
230 | +++ juju-deployer/configs/unit_config.yaml.tmpl 2014-07-04 21:48:29 +0000 | |||
231 | @@ -1,26 +1,34 @@ | |||
233 | 1 | # for nova direct access (swift, image builder, test runner among others) | 1 | #-------------------------------------------------------------- |
234 | 2 | # This file is managed by Juju; ANY CHANGES WILL BE OVERWRITTEN | ||
235 | 3 | #-------------------------------------------------------------- | ||
236 | 4 | # CI-Airline unit configuration file. | ||
237 | 5 | |||
238 | 6 | # Options for system deployment and common Swift access. | ||
239 | 2 | auth_url: $OS_AUTH_URL | 7 | auth_url: $OS_AUTH_URL |
240 | 3 | auth_user: $OS_USERNAME | 8 | auth_user: $OS_USERNAME |
241 | 4 | auth_password: $OS_PASSWORD | 9 | auth_password: $OS_PASSWORD |
242 | 5 | auth_tenant_name: $OS_TENANT_NAME | 10 | auth_tenant_name: $OS_TENANT_NAME |
243 | 6 | auth_region: $OS_REGION_NAME | 11 | auth_region: $OS_REGION_NAME |
244 | 7 | 12 | ||
245 | 13 | # Options for Gatekeeper Swift tempurl generation and upload | ||
246 | 14 | # signature validation. | ||
247 | 8 | auth_access_key_id: $HP_ACCESS_KEY_ID | 15 | auth_access_key_id: $HP_ACCESS_KEY_ID |
248 | 9 | auth_tenant_id: $HP_TENANT_ID | 16 | auth_tenant_id: $HP_TENANT_ID |
249 | 10 | tempurl_signing_key: $CI_TEMPURL_SIGNING_KEY | 17 | tempurl_signing_key: $CI_TEMPURL_SIGNING_KEY |
250 | 11 | tempurl_expires: $CI_TEMPURL_EXPIRES | 18 | tempurl_expires: $CI_TEMPURL_EXPIRES |
251 | 12 | tempurl_public_host: $CI_TEMPURL_PUBLIC_HOST | 19 | tempurl_public_host: $CI_TEMPURL_PUBLIC_HOST |
252 | 20 | keyring_uri: $CI_KEYRING_URI | ||
253 | 21 | keyserver_url: $CI_KEYSERVER_URL | ||
254 | 13 | 22 | ||
255 | 23 | # Options for acessing a isolated environment for | ||
256 | 24 | # Image-builder (Glance) and Test-runner (Nova). | ||
257 | 25 | # If not provided (empty), the system environment is used. | ||
258 | 14 | glance_auth_url: $GLANCE_OS_AUTH_URL | 26 | glance_auth_url: $GLANCE_OS_AUTH_URL |
259 | 15 | glance_auth_user: $GLANCE_OS_USERNAME | 27 | glance_auth_user: $GLANCE_OS_USERNAME |
260 | 16 | glance_auth_password: $GLANCE_OS_PASSWORD | 28 | glance_auth_password: $GLANCE_OS_PASSWORD |
261 | 17 | glance_auth_tenant_name: $GLANCE_OS_TENANT_NAME | 29 | glance_auth_tenant_name: $GLANCE_OS_TENANT_NAME |
262 | 18 | glance_auth_region: $GLANCE_OS_REGION_NAME | 30 | glance_auth_region: $GLANCE_OS_REGION_NAME |
263 | 19 | 31 | ||
264 | 20 | |||
265 | 21 | keyring_uri: $CI_KEYRING_URI | ||
266 | 22 | keyserver_url: $CI_KEYSERVER_URL | ||
267 | 23 | |||
268 | 24 | # for launchpad apis | 32 | # for launchpad apis |
269 | 25 | # and see: https://help.launchpad.net/API/SigningRequests | 33 | # and see: https://help.launchpad.net/API/SigningRequests |
270 | 26 | # and see ../../create_lp_creds.py | 34 | # and see ../../create_lp_creds.py |
271 | 27 | 35 | ||
272 | === modified file 'juju-deployer/deploy.py' | |||
273 | --- juju-deployer/deploy.py 2014-07-03 17:25:58 +0000 | |||
274 | +++ juju-deployer/deploy.py 2014-07-04 21:48:29 +0000 | |||
275 | @@ -94,11 +94,11 @@ | |||
276 | 94 | ''' | 94 | ''' |
277 | 95 | cheetah_vars = { | 95 | cheetah_vars = { |
278 | 96 | 'OS_USERNAME': None, | 96 | 'OS_USERNAME': None, |
284 | 97 | 'GLANCE_OS_USERNAME': None, | 97 | 'GLANCE_OS_USERNAME': '', |
285 | 98 | 'GLANCE_OS_AUTH_URL': None, | 98 | 'GLANCE_OS_AUTH_URL': '', |
286 | 99 | 'GLANCE_OS_PASSWORD': None, | 99 | 'GLANCE_OS_PASSWORD': '', |
287 | 100 | 'GLANCE_OS_TENANT_NAME': None, | 100 | 'GLANCE_OS_TENANT_NAME': '', |
288 | 101 | 'GLANCE_OS_REGION_NAME': None, | 101 | 'GLANCE_OS_REGION_NAME': '', |
289 | 102 | 'CI_CODE_SOURCE': 'branch', | 102 | 'CI_CODE_SOURCE': 'branch', |
290 | 103 | 'CI_BRANCH': 'lp:uci-engine', | 103 | 'CI_BRANCH': 'lp:uci-engine', |
291 | 104 | 'CI_PAYLOAD_URL': 'n/a', | 104 | 'CI_PAYLOAD_URL': 'n/a', |
292 | @@ -154,7 +154,7 @@ | |||
293 | 154 | ERROR: Missing required environment variables: | 154 | ERROR: Missing required environment variables: |
294 | 155 | {} | 155 | {} |
295 | 156 | Please ensure the novarc file has been sourced.''') | 156 | Please ensure the novarc file has been sourced.''') |
297 | 157 | sys.exit(template.format('\n '.join(missing_required))) | 157 | sys.exit(template.format('\n '.join(sorted(missing_required)))) |
298 | 158 | 158 | ||
299 | 159 | 159 | ||
300 | 160 | def bootstrap(): | 160 | def bootstrap(): |
301 | 161 | 161 | ||
302 | === modified file 'juju-deployer/test_deploy.py' | |||
303 | --- juju-deployer/test_deploy.py 2014-07-03 17:25:58 +0000 | |||
304 | +++ juju-deployer/test_deploy.py 2014-07-04 21:48:29 +0000 | |||
305 | @@ -36,11 +36,6 @@ | |||
306 | 36 | 36 | ||
307 | 37 | DEFAULT_ENV = { | 37 | DEFAULT_ENV = { |
308 | 38 | 'OS_USERNAME': 'os-user', | 38 | 'OS_USERNAME': 'os-user', |
309 | 39 | 'GLANCE_OS_USERNAME': 'glance-os-user', | ||
310 | 40 | 'GLANCE_OS_AUTH_URL': 'glance-url', | ||
311 | 41 | 'GLANCE_OS_REGION_NAME': 'glance-region', | ||
312 | 42 | 'GLANCE_OS_TENANT_NAME': 'glance-tenant', | ||
313 | 43 | 'GLANCE_OS_PASSWORD': 'glance-password', | ||
314 | 44 | 'OS_AUTH_URL': 'something.stack', | 39 | 'OS_AUTH_URL': 'something.stack', |
315 | 45 | 'CI_OAUTH_CONSUMER_KEY': 'key', | 40 | 'CI_OAUTH_CONSUMER_KEY': 'key', |
316 | 46 | 'CI_OAUTH_TOKEN': 'token', | 41 | 'CI_OAUTH_TOKEN': 'token', |
317 | @@ -61,6 +56,7 @@ | |||
318 | 61 | 'CI_TEMPURL_SIGNING_KEY': None, | 56 | 'CI_TEMPURL_SIGNING_KEY': None, |
319 | 62 | 'CI_KEYRING_URI': None, | 57 | 'CI_KEYRING_URI': None, |
320 | 63 | 'CI_KEYSERVER_URL': None, | 58 | 'CI_KEYSERVER_URL': None, |
321 | 59 | 'GLANCE_OS_USERNAME': None, | ||
322 | 64 | 'HP_ACCESS_KEY_ID': None, | 60 | 'HP_ACCESS_KEY_ID': None, |
323 | 65 | 'HP_TENANT_ID': None, | 61 | 'HP_TENANT_ID': None, |
324 | 66 | } | 62 | } |
325 | @@ -79,6 +75,7 @@ | |||
326 | 79 | self.assertEqual(os.environ['CI_KEYRING_URI'], '') | 75 | self.assertEqual(os.environ['CI_KEYRING_URI'], '') |
327 | 80 | self.assertEqual( | 76 | self.assertEqual( |
328 | 81 | os.environ['CI_KEYSERVER_URL'], 'keyserver.ubuntu.com') | 77 | os.environ['CI_KEYSERVER_URL'], 'keyserver.ubuntu.com') |
329 | 78 | self.assertEqual('', os.environ['GLANCE_OS_USERNAME']) | ||
330 | 82 | # CI_TEMPURL_SIGNING_KEY used for canonistack/prodstack TempURL | 79 | # CI_TEMPURL_SIGNING_KEY used for canonistack/prodstack TempURL |
331 | 83 | # generation and `deploy.py` generated a new random HMAC-SHA1 | 80 | # generation and `deploy.py` generated a new random HMAC-SHA1 |
332 | 84 | # (40 chars) key for each deployment. | 81 | # (40 chars) key for each deployment. |
FAILED: Continuous integration, rev:635 s-jenkins. ubuntu- ci:8080/ job/uci- engine- ci/990/
http://
Executed test runs:
Click here to trigger a rebuild: s-jenkins. ubuntu- ci:8080/ job/uci- engine- ci/990/ rebuild
http://