2ae475843cc842ea0038788177f23a29c6f8e8f8
[so.git] /
1 #########
2 # Copyright (c) 2014 GigaSpaces Technologies Ltd. All rights reserved
3 #
4 # Licensed under the Apache License, Version 2.0 (the "License");
5 # you may not use this file except in compliance with the License.
6 # You may obtain a copy of the License at
7 #
8 #       http://www.apache.org/licenses/LICENSE-2.0
9 #
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS,
12 #  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 #  * See the License for the specific language governing permissions and
14 #  * limitations under the License.
15
16
17 import unittest
18
19 import mock
20 from novaclient import exceptions as nova_exceptions
21
22 import nova_plugin.server as server
23 from cloudify.exceptions import NonRecoverableError
24 from cloudify.mocks import MockCloudifyContext
25
26
27 class TestServerImageAndFlavor(unittest.TestCase):
28
29     def test_no_image_and_no_flavor(self):
30         node_props = {
31             'image': '',
32             'flavor': ''
33         }
34         with mock.patch('nova_plugin.server.ctx',
35                         self._get_mock_ctx_with_node_properties(node_props)):
36             nova_client = self._get_mocked_nova_client()
37
38             serv = {}
39             self.assertRaises(NonRecoverableError,
40                               server._handle_image_or_flavor,
41                               serv, nova_client, 'image')
42             self.assertRaises(NonRecoverableError,
43                               server._handle_image_or_flavor,
44                               serv, nova_client, 'flavor')
45
46     def test_image_and_flavor_properties_as_names(self):
47         node_props = {
48             'image': 'some-image-name',
49             'flavor': 'some-flavor-name'
50         }
51         with mock.patch('nova_plugin.server.ctx',
52                         self._get_mock_ctx_with_node_properties(node_props)):
53             nova_client = self._get_mocked_nova_client()
54
55             serv = {}
56             server._handle_image_or_flavor(serv, nova_client, 'image')
57             server._handle_image_or_flavor(serv, nova_client, 'flavor')
58
59         self.assertEquals('some-image-id', serv.get('image'))
60         self.assertEquals('some-flavor-id', serv.get('flavor'))
61
62     def test_image_and_flavor_properties_as_ids(self):
63         node_props = {
64             'image': 'some-image-id',
65             'flavor': 'some-flavor-id'
66         }
67         with mock.patch('nova_plugin.server.ctx',
68                         self._get_mock_ctx_with_node_properties(node_props)):
69             nova_client = self._get_mocked_nova_client()
70
71             serv = {}
72             server._handle_image_or_flavor(serv, nova_client, 'image')
73             server._handle_image_or_flavor(serv, nova_client, 'flavor')
74
75         self.assertEquals('some-image-id', serv.get('image'))
76         self.assertEquals('some-flavor-id', serv.get('flavor'))
77
78     def test_image_id_and_flavor_id(self):
79         node_props = {
80             'image': '',
81             'flavor': ''
82         }
83         with mock.patch('nova_plugin.server.ctx',
84                         self._get_mock_ctx_with_node_properties(node_props)):
85             nova_client = self._get_mocked_nova_client()
86
87             serv = {}
88             serv['image'] = 'some-image-id'
89             serv['flavor'] = 'some-flavor-id'
90             server._handle_image_or_flavor(serv, nova_client, 'image')
91             server._handle_image_or_flavor(serv, nova_client, 'flavor')
92
93         self.assertEquals('some-image-id', serv.get('image'))
94         self.assertEquals('some-flavor-id', serv.get('flavor'))
95
96     def test_image_name_and_flavor_name(self):
97         node_props = {
98             'image': '',
99             'flavor': ''
100         }
101         with mock.patch('nova_plugin.server.ctx',
102                         self._get_mock_ctx_with_node_properties(node_props)):
103             nova_client = self._get_mocked_nova_client()
104
105             serv = {}
106             serv['image_name'] = 'some-image-name'
107             serv['flavor_name'] = 'some-flavor-name'
108             server._handle_image_or_flavor(serv, nova_client, 'image')
109             server._handle_image_or_flavor(serv, nova_client, 'flavor')
110
111         self.assertEquals('some-image-id', serv.get('image'))
112         self.assertNotIn('image_name', serv)
113         self.assertEquals('some-flavor-id', serv.get('flavor'))
114         self.assertNotIn('flavor_name', serv)
115
116     def test_unknown_image_name_and_flavor_name(self):
117         node_props = {
118             'image': '',
119             'flavor': ''
120         }
121         with mock.patch('nova_plugin.server.ctx',
122                         self._get_mock_ctx_with_node_properties(node_props)):
123             nova_client = self._get_mocked_nova_client()
124
125             serv = {}
126             serv['image_name'] = 'some-unknown-image-name'
127             serv['flavor_name'] = 'some-unknown-flavor-name'
128
129             self.assertRaises(nova_exceptions.NotFound,
130                               server._handle_image_or_flavor,
131                               serv, nova_client, 'image')
132             self.assertRaises(nova_exceptions.NotFound,
133                               server._handle_image_or_flavor,
134                               serv, nova_client, 'flavor')
135
136     def test_image_id_and_flavor_id_override_on_properties(self):
137         node_props = {
138             'image': 'properties-image-id',
139             'flavor': 'properties-flavor-id'
140         }
141         with mock.patch('nova_plugin.server.ctx',
142                         self._get_mock_ctx_with_node_properties(node_props)):
143             nova_client = self._get_mocked_nova_client()
144
145             serv = {}
146             serv['image'] = 'some-image-id'
147             serv['flavor'] = 'some-flavor-id'
148             server._handle_image_or_flavor(serv, nova_client, 'image')
149             server._handle_image_or_flavor(serv, nova_client, 'flavor')
150
151         self.assertEquals('some-image-id', serv.get('image'))
152         self.assertEquals('some-flavor-id', serv.get('flavor'))
153
154     def test_image_name_and_flavor_name_override_on_properties(self):
155         node_props = {
156             'image': 'properties-image-id',
157             'flavor': 'properties-flavor-id'
158         }
159         with mock.patch('nova_plugin.server.ctx',
160                         self._get_mock_ctx_with_node_properties(node_props)):
161             nova_client = self._get_mocked_nova_client()
162
163             serv = {}
164             serv['image_name'] = 'some-image-name'
165             serv['flavor_name'] = 'some-flavor-name'
166             server._handle_image_or_flavor(serv, nova_client, 'image')
167             server._handle_image_or_flavor(serv, nova_client, 'flavor')
168
169         self.assertEquals('some-image-id', serv.get('image'))
170         self.assertNotIn('image_name', serv)
171         self.assertEquals('some-flavor-id', serv.get('flavor'))
172         self.assertNotIn('flavor_name', serv)
173
174     def test_image_name_and_flavor_name_override_on_image_and_flavor_ids(self):
175         node_props = {
176             'image': '',
177             'flavor': ''
178         }
179         with mock.patch('nova_plugin.server.ctx',
180                         self._get_mock_ctx_with_node_properties(node_props)):
181             nova_client = self._get_mocked_nova_client()
182
183             serv = {}
184             serv['image'] = 'some-bad-image-id'
185             serv['image_name'] = 'some-image-name'
186             serv['flavor'] = 'some-bad-flavor-id'
187             serv['flavor_name'] = 'some-flavor-name'
188             server._handle_image_or_flavor(serv, nova_client, 'image')
189             server._handle_image_or_flavor(serv, nova_client, 'flavor')
190
191         self.assertEquals('some-image-id', serv.get('image'))
192         self.assertNotIn('image_name', serv)
193         self.assertEquals('some-flavor-id', serv.get('flavor'))
194         self.assertNotIn('flavor_name', serv)
195
196     @staticmethod
197     def _get_mocked_nova_client():
198         nova_client = mock.MagicMock()
199
200         def mock_get_if_exists(prop_name, **kwargs):
201             is_image = prop_name == 'image'
202             searched_name = kwargs.get('name')
203             if (is_image and searched_name == 'some-image-name') or \
204                     (not is_image and searched_name == 'some-flavor-name'):
205                 result = mock.MagicMock()
206                 result.id = 'some-image-id' if \
207                     is_image else 'some-flavor-id'
208                 return result
209             return []
210
211         def mock_find_generator(prop_name):
212             def mock_find(**kwargs):
213                 result = mock_get_if_exists(prop_name, **kwargs)
214                 if not result:
215                     raise nova_exceptions.NotFound(404)
216                 return result
217             return mock_find
218
219         nova_client.cosmo_plural = lambda x: '{0}s'.format(x)
220         nova_client.cosmo_get_if_exists = mock_get_if_exists
221         nova_client.images.find = mock_find_generator('image')
222         nova_client.flavors.find = mock_find_generator('flavor')
223         return nova_client
224
225     @staticmethod
226     def _get_mock_ctx_with_node_properties(properties):
227         return MockCloudifyContext(node_id='test_node_id',
228                                    properties=properties)