blob: f2370f30ad62726d9c776f6678f66c6251866e48 [file] [log] [blame]
David Patersone41ebca2015-04-09 05:40:12 -04001# Copyright 2015 Dell Inc.
David Patersonce781492014-09-18 01:07:01 -04002#
3# Licensed under the Apache License, Version 2.0 (the "License"); you may
4# not use this file except in compliance with the License. You may obtain
5# a copy of the License at
6#
David Patersone41ebca2015-04-09 05:40:12 -04007# http://www.apache.org/licenses/LICENSE-2.0
David Patersonce781492014-09-18 01:07:01 -04008#
9# Unless required by applicable law or agreed to in writing, software
10# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12# License for the specific language governing permissions and limitations
13# under the License.
David Patersonce781492014-09-18 01:07:01 -040014
songwenping99d6e002021-01-05 03:07:46 +000015from urllib import parse as urllib
16
Doug Hellmann583ce2c2015-03-11 14:55:46 +000017from oslo_log import log as logging
18
ghanshyam009a1f62017-08-08 10:22:57 +030019from tempest import clients
Andrea Frittoli (andreaf)290b3e12015-10-08 10:25:02 +010020from tempest.common import credentials_factory as credentials
Ken'ichi Ohmichi6ea3f982015-11-09 12:41:13 +000021from tempest.common import identity
Andrea Frittolicd368412017-08-14 21:37:56 +010022from tempest.common import utils
Attila Fazekasd7e08a62016-10-07 13:05:05 +020023from tempest.common.utils import net_info
David Patersonce781492014-09-18 01:07:01 -040024from tempest import config
Martin Kopec97857942019-06-12 15:23:21 +000025from tempest.lib import exceptions
David Patersonce781492014-09-18 01:07:01 -040026
Martin Kopeca8578802020-04-07 08:19:14 +000027LOG = logging.getLogger('tempest.cmd.cleanup')
David Patersonce781492014-09-18 01:07:01 -040028CONF = config.CONF
29
David Patersonce781492014-09-18 01:07:01 -040030CONF_FLAVORS = None
31CONF_IMAGES = None
David Patersond6babc52014-10-14 00:11:56 -040032CONF_NETWORKS = []
33CONF_PRIV_NETWORK_NAME = None
34CONF_PUB_NETWORK = None
35CONF_PUB_ROUTER = None
Arx Cruz05fe4bc2017-10-20 10:48:28 +020036CONF_PROJECTS = None
David Patersond6babc52014-10-14 00:11:56 -040037CONF_USERS = None
David Patersonce781492014-09-18 01:07:01 -040038
David Patersonce781492014-09-18 01:07:01 -040039IS_CINDER = None
40IS_GLANCE = None
David Patersonce781492014-09-18 01:07:01 -040041IS_NEUTRON = None
42IS_NOVA = None
43
44
45def init_conf():
David Patersonce781492014-09-18 01:07:01 -040046 global CONF_FLAVORS
47 global CONF_IMAGES
David Patersond6babc52014-10-14 00:11:56 -040048 global CONF_NETWORKS
49 global CONF_PRIV_NETWORK
50 global CONF_PRIV_NETWORK_NAME
51 global CONF_PUB_NETWORK
52 global CONF_PUB_ROUTER
Arx Cruz05fe4bc2017-10-20 10:48:28 +020053 global CONF_PROJECTS
David Patersond6babc52014-10-14 00:11:56 -040054 global CONF_USERS
David Patersonce781492014-09-18 01:07:01 -040055 global IS_CINDER
56 global IS_GLANCE
57 global IS_HEAT
58 global IS_NEUTRON
59 global IS_NOVA
60
David Patersonce781492014-09-18 01:07:01 -040061 IS_CINDER = CONF.service_available.cinder
62 IS_GLANCE = CONF.service_available.glance
David Patersonce781492014-09-18 01:07:01 -040063 IS_NEUTRON = CONF.service_available.neutron
64 IS_NOVA = CONF.service_available.nova
65
David Patersond6babc52014-10-14 00:11:56 -040066 CONF_FLAVORS = [CONF.compute.flavor_ref, CONF.compute.flavor_ref_alt]
67 CONF_IMAGES = [CONF.compute.image_ref, CONF.compute.image_ref_alt]
68 CONF_PRIV_NETWORK_NAME = CONF.compute.fixed_network_name
69 CONF_PUB_NETWORK = CONF.network.public_network_id
70 CONF_PUB_ROUTER = CONF.network.public_router_id
Arx Cruz05fe4bc2017-10-20 10:48:28 +020071 CONF_PROJECTS = [CONF.auth.admin_project_name]
Jeffrey Zhangb5e23212016-07-06 14:18:53 +080072 CONF_USERS = [CONF.auth.admin_username]
David Patersond6babc52014-10-14 00:11:56 -040073
74 if IS_NEUTRON:
David Paterson82234022015-04-12 14:07:40 -040075 CONF_PRIV_NETWORK = _get_network_id(CONF.compute.fixed_network_name,
Daniel Melladod4d0b932016-04-08 08:57:29 +000076 CONF.auth.admin_project_name)
David Patersond6babc52014-10-14 00:11:56 -040077 CONF_NETWORKS = [CONF_PUB_NETWORK, CONF_PRIV_NETWORK]
78
79
Daniel Melladod4d0b932016-04-08 08:57:29 +000080def _get_network_id(net_name, project_name):
ghanshyam009a1f62017-08-08 10:22:57 +030081 am = clients.Manager(
82 credentials.get_configured_admin_credentials())
John Warren94d8faf2015-09-15 12:22:24 -040083 net_cl = am.networks_client
Arx Cruz05fe4bc2017-10-20 10:48:28 +020084 pr_cl = am.projects_client
David Patersond6babc52014-10-14 00:11:56 -040085
David Kranz34e88122014-12-11 15:24:05 -050086 networks = net_cl.list_networks()
Arx Cruz05fe4bc2017-10-20 10:48:28 +020087 project = identity.get_project_by_name(pr_cl, project_name)
88 p_id = project['id']
David Patersond6babc52014-10-14 00:11:56 -040089 n_id = None
90 for net in networks['networks']:
Arx Cruz05fe4bc2017-10-20 10:48:28 +020091 if (net['project_id'] == p_id and net['name'] == net_name):
David Patersond6babc52014-10-14 00:11:56 -040092 n_id = net['id']
93 break
94 return n_id
95
David Patersonce781492014-09-18 01:07:01 -040096
97class BaseService(object):
98 def __init__(self, kwargs):
99 self.client = None
100 for key, value in kwargs.items():
101 setattr(self, key, value)
102
David Paterson82234022015-04-12 14:07:40 -0400103 self.tenant_filter = {}
104 if hasattr(self, 'tenant_id'):
Martin Kopecb37903c2019-01-20 21:39:58 +0000105 self.tenant_filter['project_id'] = self.tenant_id
David Paterson82234022015-04-12 14:07:40 -0400106
David Patersonce781492014-09-18 01:07:01 -0400107 def _filter_by_tenant_id(self, item_list):
Federico Ressi2d6bcaa2018-04-11 12:37:36 +0200108 if (item_list is None or
109 not item_list or
110 not hasattr(self, 'tenant_id') or
111 self.tenant_id is None or
112 'tenant_id' not in item_list[0]):
David Patersonce781492014-09-18 01:07:01 -0400113 return item_list
114
David Patersond6babc52014-10-14 00:11:56 -0400115 return [item for item in item_list
116 if item['tenant_id'] == self.tenant_id]
David Patersonce781492014-09-18 01:07:01 -0400117
118 def list(self):
119 pass
120
121 def delete(self):
122 pass
123
124 def dry_run(self):
125 pass
126
127 def save_state(self):
128 pass
129
130 def run(self):
Martin Kopec97857942019-06-12 15:23:21 +0000131 try:
132 if self.is_dry_run:
133 self.dry_run()
134 elif self.is_save_state:
135 self.save_state()
136 else:
137 self.delete()
138 except exceptions.NotImplemented as exc:
139 # Many OpenStack services use extensions logic to implement the
140 # features or resources. Tempest cleanup tries to clean up the test
141 # resources without having much logic of extensions checks etc.
142 # If any of the extension is missing then, service will return
143 # NotImplemented error.
144 msg = ("Got NotImplemented error in %s, full exception: %s" %
145 (str(self.__class__), str(exc)))
146 LOG.exception(msg)
Martin Kopec219e3222019-08-05 20:02:20 +0000147 self.got_exceptions.append(exc)
David Patersonce781492014-09-18 01:07:01 -0400148
149
150class SnapshotService(BaseService):
151
152 def __init__(self, manager, **kwargs):
153 super(SnapshotService, self).__init__(kwargs)
ghanshyam59928952017-10-26 01:38:45 +0000154 self.client = manager.snapshots_client_latest
David Patersonce781492014-09-18 01:07:01 -0400155
156 def list(self):
157 client = self.client
David Paterson07661de2015-10-29 20:15:04 -0700158 snaps = client.list_snapshots()['snapshots']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000159 if not self.is_save_state:
160 # recreate list removing saved snapshots
161 snaps = [snap for snap in snaps if snap['id']
162 not in self.saved_state_json['snapshots'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100163 LOG.debug("List count, %s Snapshots", len(snaps))
David Patersonce781492014-09-18 01:07:01 -0400164 return snaps
165
166 def delete(self):
167 snaps = self.list()
168 client = self.client
169 for snap in snaps:
170 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000171 LOG.debug("Deleting Snapshot with id %s", snap['id'])
David Patersonce781492014-09-18 01:07:01 -0400172 client.delete_snapshot(snap['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400173 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000174 LOG.exception("Delete Snapshot %s exception.", snap['id'])
David Patersonce781492014-09-18 01:07:01 -0400175
176 def dry_run(self):
177 snaps = self.list()
178 self.data['snapshots'] = snaps
179
Martin Kopec5a884bf2019-02-11 18:10:55 +0000180 def save_state(self):
181 snaps = self.list()
182 self.data['snapshots'] = {}
183 for snap in snaps:
184 self.data['snapshots'][snap['id']] = snap['name']
185
David Patersonce781492014-09-18 01:07:01 -0400186
187class ServerService(BaseService):
188 def __init__(self, manager, **kwargs):
189 super(ServerService, self).__init__(kwargs)
190 self.client = manager.servers_client
David Paterson07661de2015-10-29 20:15:04 -0700191 self.server_groups_client = manager.server_groups_client
David Patersonce781492014-09-18 01:07:01 -0400192
193 def list(self):
194 client = self.client
David Kranzae99b9a2015-02-16 13:37:01 -0500195 servers_body = client.list_servers()
David Patersonce781492014-09-18 01:07:01 -0400196 servers = servers_body['servers']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000197 if not self.is_save_state:
198 # recreate list removing saved servers
199 servers = [server for server in servers if server['id']
200 not in self.saved_state_json['servers'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100201 LOG.debug("List count, %s Servers", len(servers))
David Patersonce781492014-09-18 01:07:01 -0400202 return servers
203
204 def delete(self):
205 client = self.client
206 servers = self.list()
207 for server in servers:
208 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000209 LOG.debug("Deleting Server with id %s", server['id'])
David Patersonce781492014-09-18 01:07:01 -0400210 client.delete_server(server['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400211 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000212 LOG.exception("Delete Server %s exception.", server['id'])
David Patersonce781492014-09-18 01:07:01 -0400213
214 def dry_run(self):
215 servers = self.list()
216 self.data['servers'] = servers
217
Martin Kopec5a884bf2019-02-11 18:10:55 +0000218 def save_state(self):
219 servers = self.list()
220 self.data['servers'] = {}
221 for server in servers:
222 self.data['servers'][server['id']] = server['name']
223
David Patersonce781492014-09-18 01:07:01 -0400224
225class ServerGroupService(ServerService):
226
227 def list(self):
David Paterson07661de2015-10-29 20:15:04 -0700228 client = self.server_groups_client
ghanshyam2dc13452015-08-24 17:39:25 +0900229 sgs = client.list_server_groups()['server_groups']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000230 if not self.is_save_state:
231 # recreate list removing saved server_groups
232 sgs = [sg for sg in sgs if sg['id']
233 not in self.saved_state_json['server_groups'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100234 LOG.debug("List count, %s Server Groups", len(sgs))
David Patersonce781492014-09-18 01:07:01 -0400235 return sgs
236
237 def delete(self):
Martin Kopec5a884bf2019-02-11 18:10:55 +0000238 client = self.server_groups_client
David Patersonce781492014-09-18 01:07:01 -0400239 sgs = self.list()
240 for sg in sgs:
241 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000242 LOG.debug("Deleting Server Group with id %s", sg['id'])
David Patersonce781492014-09-18 01:07:01 -0400243 client.delete_server_group(sg['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400244 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000245 LOG.exception("Delete Server Group %s exception.", sg['id'])
David Patersonce781492014-09-18 01:07:01 -0400246
247 def dry_run(self):
248 sgs = self.list()
249 self.data['server_groups'] = sgs
250
Martin Kopec5a884bf2019-02-11 18:10:55 +0000251 def save_state(self):
252 sgs = self.list()
253 self.data['server_groups'] = {}
254 for sg in sgs:
255 self.data['server_groups'][sg['id']] = sg['name']
256
David Patersonce781492014-09-18 01:07:01 -0400257
David Patersonce781492014-09-18 01:07:01 -0400258class KeyPairService(BaseService):
259 def __init__(self, manager, **kwargs):
260 super(KeyPairService, self).__init__(kwargs)
261 self.client = manager.keypairs_client
262
263 def list(self):
264 client = self.client
ghanshyamdee01f22015-08-17 11:41:47 +0900265 keypairs = client.list_keypairs()['keypairs']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000266 if not self.is_save_state:
267 # recreate list removing saved keypairs
268 keypairs = [keypair for keypair in keypairs
269 if keypair['keypair']['name']
270 not in self.saved_state_json['keypairs'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100271 LOG.debug("List count, %s Keypairs", len(keypairs))
David Patersonce781492014-09-18 01:07:01 -0400272 return keypairs
273
274 def delete(self):
275 client = self.client
276 keypairs = self.list()
277 for k in keypairs:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000278 name = k['keypair']['name']
David Patersonce781492014-09-18 01:07:01 -0400279 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000280 LOG.debug("Deleting keypair %s", name)
David Patersonce781492014-09-18 01:07:01 -0400281 client.delete_keypair(name)
David Patersone41ebca2015-04-09 05:40:12 -0400282 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000283 LOG.exception("Delete Keypair %s exception.", name)
David Patersonce781492014-09-18 01:07:01 -0400284
285 def dry_run(self):
286 keypairs = self.list()
287 self.data['keypairs'] = keypairs
288
Martin Kopec5a884bf2019-02-11 18:10:55 +0000289 def save_state(self):
290 keypairs = self.list()
291 self.data['keypairs'] = {}
292 for keypair in keypairs:
293 keypair = keypair['keypair']
294 self.data['keypairs'][keypair['name']] = keypair
295
David Patersonce781492014-09-18 01:07:01 -0400296
David Patersonce781492014-09-18 01:07:01 -0400297class VolumeService(BaseService):
298 def __init__(self, manager, **kwargs):
299 super(VolumeService, self).__init__(kwargs)
ghanshyam59928952017-10-26 01:38:45 +0000300 self.client = manager.volumes_client_latest
David Patersonce781492014-09-18 01:07:01 -0400301
302 def list(self):
303 client = self.client
John Warren6177c9e2015-08-19 20:00:17 +0000304 vols = client.list_volumes()['volumes']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000305 if not self.is_save_state:
306 # recreate list removing saved volumes
307 vols = [vol for vol in vols if vol['id']
308 not in self.saved_state_json['volumes'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100309 LOG.debug("List count, %s Volumes", len(vols))
David Patersonce781492014-09-18 01:07:01 -0400310 return vols
311
312 def delete(self):
313 client = self.client
314 vols = self.list()
315 for v in vols:
316 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000317 LOG.debug("Deleting volume with id %s", v['id'])
David Patersonce781492014-09-18 01:07:01 -0400318 client.delete_volume(v['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400319 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000320 LOG.exception("Delete Volume %s exception.", v['id'])
David Patersonce781492014-09-18 01:07:01 -0400321
322 def dry_run(self):
323 vols = self.list()
324 self.data['volumes'] = vols
325
Martin Kopec5a884bf2019-02-11 18:10:55 +0000326 def save_state(self):
327 vols = self.list()
328 self.data['volumes'] = {}
329 for vol in vols:
330 self.data['volumes'][vol['id']] = vol['name']
331
David Patersonce781492014-09-18 01:07:01 -0400332
David Paterson35c8df02015-04-05 04:35:31 -0400333class VolumeQuotaService(BaseService):
334 def __init__(self, manager, **kwargs):
335 super(VolumeQuotaService, self).__init__(kwargs)
ghanshyam6c682ff2018-08-06 09:54:45 +0000336 self.client = manager.volume_quotas_client_latest
David Paterson35c8df02015-04-05 04:35:31 -0400337
338 def delete(self):
339 client = self.client
340 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000341 LOG.debug("Deleting Volume Quotas for project with id %s",
342 self.project_id)
Martin Kopecb37903c2019-01-20 21:39:58 +0000343 client.delete_quota_set(self.project_id)
David Patersone41ebca2015-04-09 05:40:12 -0400344 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000345 LOG.exception("Delete Volume Quotas exception for 'project %s'.",
346 self.project_id)
David Paterson35c8df02015-04-05 04:35:31 -0400347
348 def dry_run(self):
Ken'ichi Ohmichi3cf9eaf2016-07-29 11:05:21 -0700349 quotas = self.client.show_quota_set(
Martin Kopecb37903c2019-01-20 21:39:58 +0000350 self.project_id, params={'usage': True})['quota_set']
David Paterson35c8df02015-04-05 04:35:31 -0400351 self.data['volume_quotas'] = quotas
352
353
354class NovaQuotaService(BaseService):
355 def __init__(self, manager, **kwargs):
356 super(NovaQuotaService, self).__init__(kwargs)
357 self.client = manager.quotas_client
358 self.limits_client = manager.limits_client
359
360 def delete(self):
361 client = self.client
362 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000363 LOG.debug("Deleting Nova Quotas for project with id %s",
364 self.project_id)
Martin Kopecb37903c2019-01-20 21:39:58 +0000365 client.delete_quota_set(self.project_id)
David Patersone41ebca2015-04-09 05:40:12 -0400366 except Exception:
Martin Kopeca8578802020-04-07 08:19:14 +0000367 LOG.exception("Delete Nova Quotas exception for 'project %s'.",
Martin Kopecfd01fe92019-02-27 08:46:05 +0000368 self.project_id)
David Paterson35c8df02015-04-05 04:35:31 -0400369
370 def dry_run(self):
371 client = self.limits_client
ghanshyam8a599492015-08-24 15:55:59 +0900372 quotas = client.show_limits()['limits']
Ken'ichi Ohmichib93e6762015-06-15 07:11:29 +0000373 self.data['compute_quotas'] = quotas['absolute']
David Paterson35c8df02015-04-05 04:35:31 -0400374
375
Lukas Piwowarskie530f242019-10-29 11:48:00 +0000376class NetworkQuotaService(BaseService):
377 def __init__(self, manager, **kwargs):
378 super(NetworkQuotaService, self).__init__(kwargs)
379 self.client = manager.network_quotas_client
380
381 def delete(self):
382 client = self.client
383 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000384 LOG.debug("Deleting Network Quotas for project with id %s",
385 self.project_id)
Lukas Piwowarskie530f242019-10-29 11:48:00 +0000386 client.reset_quotas(self.project_id)
387 except Exception:
388 LOG.exception("Delete Network Quotas exception for 'project %s'.",
389 self.project_id)
390
391 def dry_run(self):
392 resp = [quota for quota in self.client.list_quotas()['quotas']
393 if quota['project_id'] == self.project_id]
394 self.data['network_quotas'] = resp
395
396
David Patersonce781492014-09-18 01:07:01 -0400397# Begin network service classes
Martin Kopec5a884bf2019-02-11 18:10:55 +0000398class BaseNetworkService(BaseService):
David Patersonce781492014-09-18 01:07:01 -0400399 def __init__(self, manager, **kwargs):
Martin Kopec5a884bf2019-02-11 18:10:55 +0000400 super(BaseNetworkService, self).__init__(kwargs)
John Warren94d8faf2015-09-15 12:22:24 -0400401 self.networks_client = manager.networks_client
John Warren3961acd2015-10-02 14:38:53 -0400402 self.subnets_client = manager.subnets_client
John Warren49c0fe52015-10-22 12:35:54 -0400403 self.ports_client = manager.ports_client
John Warrenfbf2a892015-11-17 12:36:14 -0500404 self.floating_ips_client = manager.floating_ips_client
John Warren6d0083a2015-11-30 18:12:30 -0500405 self.metering_labels_client = manager.metering_labels_client
John Warrendd20b3e2015-12-03 13:11:28 -0500406 self.metering_label_rules_client = manager.metering_label_rules_client
John Warrenf9606e92015-12-10 12:12:42 -0500407 self.security_groups_client = manager.security_groups_client
ghanshyama25c4192016-03-11 18:38:12 +0900408 self.routers_client = manager.routers_client
Martin Kopece6819982019-02-18 12:34:52 +0000409 self.subnetpools_client = manager.subnetpools_client
David Patersonce781492014-09-18 01:07:01 -0400410
David Patersond6babc52014-10-14 00:11:56 -0400411 def _filter_by_conf_networks(self, item_list):
412 if not item_list or not all(('network_id' in i for i in item_list)):
413 return item_list
414
415 return [item for item in item_list if item['network_id']
416 not in CONF_NETWORKS]
417
Martin Kopec5a884bf2019-02-11 18:10:55 +0000418
419class NetworkService(BaseNetworkService):
420
David Patersonce781492014-09-18 01:07:01 -0400421 def list(self):
John Warren94d8faf2015-09-15 12:22:24 -0400422 client = self.networks_client
David Paterson82234022015-04-12 14:07:40 -0400423 networks = client.list_networks(**self.tenant_filter)
424 networks = networks['networks']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000425
426 if not self.is_save_state:
427 # recreate list removing saved networks
428 networks = [network for network in networks if network['id']
429 not in self.saved_state_json['networks'].keys()]
David Patersonce781492014-09-18 01:07:01 -0400430 # filter out networks declared in tempest.conf
431 if self.is_preserve:
432 networks = [network for network in networks
David Patersond6babc52014-10-14 00:11:56 -0400433 if network['id'] not in CONF_NETWORKS]
Martin Kopeca8578802020-04-07 08:19:14 +0000434 LOG.debug("List count, %s Networks", len(networks))
David Patersonce781492014-09-18 01:07:01 -0400435 return networks
436
437 def delete(self):
John Warren94d8faf2015-09-15 12:22:24 -0400438 client = self.networks_client
David Patersonce781492014-09-18 01:07:01 -0400439 networks = self.list()
440 for n in networks:
441 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000442 LOG.debug("Deleting Network with id %s", n['id'])
David Patersonce781492014-09-18 01:07:01 -0400443 client.delete_network(n['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400444 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000445 LOG.exception("Delete Network %s exception.", n['id'])
David Patersonce781492014-09-18 01:07:01 -0400446
447 def dry_run(self):
448 networks = self.list()
449 self.data['networks'] = networks
450
Martin Kopec5a884bf2019-02-11 18:10:55 +0000451 def save_state(self):
452 networks = self.list()
453 self.data['networks'] = {}
454 for network in networks:
455 self.data['networks'][network['id']] = network
David Patersonce781492014-09-18 01:07:01 -0400456
Martin Kopec5a884bf2019-02-11 18:10:55 +0000457
458class NetworkFloatingIpService(BaseNetworkService):
David Patersonce781492014-09-18 01:07:01 -0400459
460 def list(self):
John Warrenfbf2a892015-11-17 12:36:14 -0500461 client = self.floating_ips_client
David Paterson82234022015-04-12 14:07:40 -0400462 flips = client.list_floatingips(**self.tenant_filter)
David Patersonce781492014-09-18 01:07:01 -0400463 flips = flips['floatingips']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000464
465 if not self.is_save_state:
466 # recreate list removing saved flips
467 flips = [flip for flip in flips if flip['id']
468 not in self.saved_state_json['floatingips'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100469 LOG.debug("List count, %s Network Floating IPs", len(flips))
David Patersonce781492014-09-18 01:07:01 -0400470 return flips
471
472 def delete(self):
Martin Kopec5a884bf2019-02-11 18:10:55 +0000473 client = self.floating_ips_client
David Patersonce781492014-09-18 01:07:01 -0400474 flips = self.list()
475 for flip in flips:
476 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000477 LOG.debug("Deleting Network Floating IP with id %s",
478 flip['id'])
David Patersonce781492014-09-18 01:07:01 -0400479 client.delete_floatingip(flip['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400480 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000481 LOG.exception("Delete Network Floating IP %s exception.",
482 flip['id'])
David Patersonce781492014-09-18 01:07:01 -0400483
484 def dry_run(self):
485 flips = self.list()
Martin Kopec5a884bf2019-02-11 18:10:55 +0000486 self.data['floatingips'] = flips
487
488 def save_state(self):
489 flips = self.list()
490 self.data['floatingips'] = {}
491 for flip in flips:
492 self.data['floatingips'][flip['id']] = flip
David Patersonce781492014-09-18 01:07:01 -0400493
494
Martin Kopec5a884bf2019-02-11 18:10:55 +0000495class NetworkRouterService(BaseNetworkService):
David Patersonce781492014-09-18 01:07:01 -0400496
497 def list(self):
Ken'ichi Ohmichie35f4722015-12-22 04:57:11 +0000498 client = self.routers_client
David Paterson82234022015-04-12 14:07:40 -0400499 routers = client.list_routers(**self.tenant_filter)
David Patersonce781492014-09-18 01:07:01 -0400500 routers = routers['routers']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000501
502 if not self.is_save_state:
503 # recreate list removing saved routers
504 routers = [router for router in routers if router['id']
505 not in self.saved_state_json['routers'].keys()]
David Patersonce781492014-09-18 01:07:01 -0400506 if self.is_preserve:
507 routers = [router for router in routers
508 if router['id'] != CONF_PUB_ROUTER]
509
Jordan Pittier525ec712016-12-07 17:51:26 +0100510 LOG.debug("List count, %s Routers", len(routers))
David Patersonce781492014-09-18 01:07:01 -0400511 return routers
512
513 def delete(self):
Ken'ichi Ohmichie35f4722015-12-22 04:57:11 +0000514 client = self.routers_client
Ken'ichi Ohmichif3110f02016-03-21 12:29:03 -0700515 ports_client = self.ports_client
David Patersonce781492014-09-18 01:07:01 -0400516 routers = self.list()
517 for router in routers:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000518 rid = router['id']
Martin Kopec598b1ae2019-04-01 14:41:53 +0000519 ports = [port for port
520 in ports_client.list_ports(device_id=rid)['ports']
521 if net_info.is_router_interface_port(port)]
522 for port in ports:
523 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000524 LOG.debug("Deleting port with id %s of router with id %s",
525 port['id'], rid)
piyush11078694aca952015-12-17 12:54:44 +0530526 client.remove_router_interface(rid, port_id=port['id'])
Martin Kopec598b1ae2019-04-01 14:41:53 +0000527 except Exception:
528 LOG.exception("Delete Router Interface exception for "
529 "'port %s' of 'router %s'.", port['id'], rid)
530 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000531 LOG.debug("Deleting Router with id %s", rid)
David Patersond6babc52014-10-14 00:11:56 -0400532 client.delete_router(rid)
David Patersone41ebca2015-04-09 05:40:12 -0400533 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000534 LOG.exception("Delete Router %s exception.", rid)
David Patersonce781492014-09-18 01:07:01 -0400535
536 def dry_run(self):
537 routers = self.list()
538 self.data['routers'] = routers
539
Martin Kopec5a884bf2019-02-11 18:10:55 +0000540 def save_state(self):
541 routers = self.list()
542 self.data['routers'] = {}
543 for router in routers:
544 self.data['routers'][router['id']] = router['name']
545
David Patersonce781492014-09-18 01:07:01 -0400546
Alexander Gubanov13379bb2015-05-19 18:57:32 +0300547class NetworkMeteringLabelRuleService(NetworkService):
David Patersonce781492014-09-18 01:07:01 -0400548
549 def list(self):
John Warrendd20b3e2015-12-03 13:11:28 -0500550 client = self.metering_label_rules_client
David Kranz34e88122014-12-11 15:24:05 -0500551 rules = client.list_metering_label_rules()
David Patersonce781492014-09-18 01:07:01 -0400552 rules = rules['metering_label_rules']
553 rules = self._filter_by_tenant_id(rules)
Martin Kopec5a884bf2019-02-11 18:10:55 +0000554
555 if not self.is_save_state:
556 saved_rules = self.saved_state_json['metering_label_rules'].keys()
557 # recreate list removing saved rules
558 rules = [rule for rule in rules if rule['id'] not in saved_rules]
Jordan Pittier525ec712016-12-07 17:51:26 +0100559 LOG.debug("List count, %s Metering Label Rules", len(rules))
David Patersonce781492014-09-18 01:07:01 -0400560 return rules
561
562 def delete(self):
John Warrendd20b3e2015-12-03 13:11:28 -0500563 client = self.metering_label_rules_client
David Patersonce781492014-09-18 01:07:01 -0400564 rules = self.list()
565 for rule in rules:
566 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000567 LOG.debug("Deleting Metering Label Rule with id %s",
568 rule['id'])
David Patersonce781492014-09-18 01:07:01 -0400569 client.delete_metering_label_rule(rule['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400570 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000571 LOG.exception("Delete Metering Label Rule %s exception.",
572 rule['id'])
David Patersonce781492014-09-18 01:07:01 -0400573
574 def dry_run(self):
575 rules = self.list()
Martin Kopec5a884bf2019-02-11 18:10:55 +0000576 self.data['metering_label_rules'] = rules
577
578 def save_state(self):
579 rules = self.list()
580 self.data['metering_label_rules'] = {}
581 for rule in rules:
582 self.data['metering_label_rules'][rule['id']] = rule
David Patersonce781492014-09-18 01:07:01 -0400583
584
Martin Kopec5a884bf2019-02-11 18:10:55 +0000585class NetworkMeteringLabelService(BaseNetworkService):
David Patersonce781492014-09-18 01:07:01 -0400586
587 def list(self):
John Warren6d0083a2015-11-30 18:12:30 -0500588 client = self.metering_labels_client
David Kranz34e88122014-12-11 15:24:05 -0500589 labels = client.list_metering_labels()
David Patersonce781492014-09-18 01:07:01 -0400590 labels = labels['metering_labels']
591 labels = self._filter_by_tenant_id(labels)
Martin Kopec5a884bf2019-02-11 18:10:55 +0000592
593 if not self.is_save_state:
594 # recreate list removing saved labels
595 labels = [label for label in labels if label['id']
596 not in self.saved_state_json['metering_labels'].keys()]
Jordan Pittier525ec712016-12-07 17:51:26 +0100597 LOG.debug("List count, %s Metering Labels", len(labels))
David Patersonce781492014-09-18 01:07:01 -0400598 return labels
599
600 def delete(self):
John Warren6d0083a2015-11-30 18:12:30 -0500601 client = self.metering_labels_client
David Patersonce781492014-09-18 01:07:01 -0400602 labels = self.list()
603 for label in labels:
604 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000605 LOG.debug("Deleting Metering Label with id %s", label['id'])
David Patersonce781492014-09-18 01:07:01 -0400606 client.delete_metering_label(label['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400607 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000608 LOG.exception("Delete Metering Label %s exception.",
609 label['id'])
David Patersonce781492014-09-18 01:07:01 -0400610
611 def dry_run(self):
612 labels = self.list()
Martin Kopec5a884bf2019-02-11 18:10:55 +0000613 self.data['metering_labels'] = labels
614
615 def save_state(self):
616 labels = self.list()
617 self.data['metering_labels'] = {}
618 for label in labels:
619 self.data['metering_labels'][label['id']] = label['name']
David Patersonce781492014-09-18 01:07:01 -0400620
621
Martin Kopec5a884bf2019-02-11 18:10:55 +0000622class NetworkPortService(BaseNetworkService):
David Patersonce781492014-09-18 01:07:01 -0400623
624 def list(self):
John Warren49c0fe52015-10-22 12:35:54 -0400625 client = self.ports_client
David Paterson82234022015-04-12 14:07:40 -0400626 ports = [port for port in
627 client.list_ports(**self.tenant_filter)['ports']
628 if port["device_owner"] == "" or
629 port["device_owner"].startswith("compute:")]
630
Martin Kopec5a884bf2019-02-11 18:10:55 +0000631 if not self.is_save_state:
632 # recreate list removing saved ports
633 ports = [port for port in ports if port['id']
634 not in self.saved_state_json['ports'].keys()]
David Patersond6babc52014-10-14 00:11:56 -0400635 if self.is_preserve:
636 ports = self._filter_by_conf_networks(ports)
David Paterson82234022015-04-12 14:07:40 -0400637
Jordan Pittier525ec712016-12-07 17:51:26 +0100638 LOG.debug("List count, %s Ports", len(ports))
David Patersonce781492014-09-18 01:07:01 -0400639 return ports
640
641 def delete(self):
John Warren49c0fe52015-10-22 12:35:54 -0400642 client = self.ports_client
David Patersonce781492014-09-18 01:07:01 -0400643 ports = self.list()
644 for port in ports:
645 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000646 LOG.debug("Deleting port with id %s", port['id'])
David Patersonce781492014-09-18 01:07:01 -0400647 client.delete_port(port['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400648 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000649 LOG.exception("Delete Port %s exception.", port['id'])
David Patersonce781492014-09-18 01:07:01 -0400650
651 def dry_run(self):
652 ports = self.list()
653 self.data['ports'] = ports
654
Martin Kopec5a884bf2019-02-11 18:10:55 +0000655 def save_state(self):
656 ports = self.list()
657 self.data['ports'] = {}
658 for port in ports:
659 self.data['ports'][port['id']] = port['name']
David Patersonce781492014-09-18 01:07:01 -0400660
Martin Kopec5a884bf2019-02-11 18:10:55 +0000661
662class NetworkSecGroupService(BaseNetworkService):
David Paterson82234022015-04-12 14:07:40 -0400663 def list(self):
John Warrenf9606e92015-12-10 12:12:42 -0500664 client = self.security_groups_client
David Paterson82234022015-04-12 14:07:40 -0400665 filter = self.tenant_filter
666 # cannot delete default sec group so never show it.
667 secgroups = [secgroup for secgroup in
668 client.list_security_groups(**filter)['security_groups']
669 if secgroup['name'] != 'default']
670
Martin Kopec5a884bf2019-02-11 18:10:55 +0000671 if not self.is_save_state:
672 # recreate list removing saved security_groups
673 secgroups = [secgroup for secgroup in secgroups if secgroup['id']
674 not in self.saved_state_json['security_groups'].keys()
675 ]
David Paterson82234022015-04-12 14:07:40 -0400676 if self.is_preserve:
Martin Kopec5a884bf2019-02-11 18:10:55 +0000677 secgroups = [secgroup for secgroup in secgroups
678 if secgroup['security_group_rules'][0]['project_id']
679 not in CONF_PROJECTS]
Jordan Pittier525ec712016-12-07 17:51:26 +0100680 LOG.debug("List count, %s security_groups", len(secgroups))
David Paterson82234022015-04-12 14:07:40 -0400681 return secgroups
682
683 def delete(self):
Martin Kopec5a884bf2019-02-11 18:10:55 +0000684 client = self.security_groups_client
David Paterson82234022015-04-12 14:07:40 -0400685 secgroups = self.list()
686 for secgroup in secgroups:
687 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000688 LOG.debug("Deleting security_group with id %s", secgroup['id'])
Martin Kopec5a884bf2019-02-11 18:10:55 +0000689 client.delete_security_group(secgroup['id'])
David Paterson82234022015-04-12 14:07:40 -0400690 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000691 LOG.exception("Delete security_group %s exception.",
692 secgroup['id'])
David Paterson82234022015-04-12 14:07:40 -0400693
694 def dry_run(self):
695 secgroups = self.list()
Martin Kopec5a884bf2019-02-11 18:10:55 +0000696 self.data['security_groups'] = secgroups
697
698 def save_state(self):
699 secgroups = self.list()
700 self.data['security_groups'] = {}
701 for secgroup in secgroups:
702 self.data['security_groups'][secgroup['id']] = secgroup['name']
David Paterson82234022015-04-12 14:07:40 -0400703
704
Martin Kopec5a884bf2019-02-11 18:10:55 +0000705class NetworkSubnetService(BaseNetworkService):
David Patersonce781492014-09-18 01:07:01 -0400706
707 def list(self):
John Warren3961acd2015-10-02 14:38:53 -0400708 client = self.subnets_client
David Paterson82234022015-04-12 14:07:40 -0400709 subnets = client.list_subnets(**self.tenant_filter)
David Patersonce781492014-09-18 01:07:01 -0400710 subnets = subnets['subnets']
Martin Kopec5a884bf2019-02-11 18:10:55 +0000711 if not self.is_save_state:
712 # recreate list removing saved subnets
713 subnets = [subnet for subnet in subnets if subnet['id']
714 not in self.saved_state_json['subnets'].keys()]
David Patersond6babc52014-10-14 00:11:56 -0400715 if self.is_preserve:
716 subnets = self._filter_by_conf_networks(subnets)
Jordan Pittier525ec712016-12-07 17:51:26 +0100717 LOG.debug("List count, %s Subnets", len(subnets))
David Patersonce781492014-09-18 01:07:01 -0400718 return subnets
719
720 def delete(self):
John Warren3961acd2015-10-02 14:38:53 -0400721 client = self.subnets_client
David Patersonce781492014-09-18 01:07:01 -0400722 subnets = self.list()
723 for subnet in subnets:
724 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000725 LOG.debug("Deleting subnet with id %s", subnet['id'])
David Patersonce781492014-09-18 01:07:01 -0400726 client.delete_subnet(subnet['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400727 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000728 LOG.exception("Delete Subnet %s exception.", subnet['id'])
David Patersonce781492014-09-18 01:07:01 -0400729
730 def dry_run(self):
731 subnets = self.list()
732 self.data['subnets'] = subnets
733
Martin Kopec5a884bf2019-02-11 18:10:55 +0000734 def save_state(self):
735 subnets = self.list()
736 self.data['subnets'] = {}
737 for subnet in subnets:
738 self.data['subnets'][subnet['id']] = subnet['name']
739
David Patersonce781492014-09-18 01:07:01 -0400740
Martin Kopece6819982019-02-18 12:34:52 +0000741class NetworkSubnetPoolsService(BaseNetworkService):
742
743 def list(self):
744 client = self.subnetpools_client
745 pools = client.list_subnetpools(**self.tenant_filter)['subnetpools']
746 if not self.is_save_state:
747 # recreate list removing saved subnet pools
748 pools = [pool for pool in pools if pool['id']
749 not in self.saved_state_json['subnetpools'].keys()]
750 if self.is_preserve:
751 pools = [pool for pool in pools if pool['project_id']
752 not in CONF_PROJECTS]
753 LOG.debug("List count, %s Subnet Pools", len(pools))
754 return pools
755
756 def delete(self):
757 client = self.subnetpools_client
758 pools = self.list()
759 for pool in pools:
760 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000761 LOG.debug("Deleting Subnet Pool with id %s", pool['id'])
Martin Kopece6819982019-02-18 12:34:52 +0000762 client.delete_subnetpool(pool['id'])
763 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000764 LOG.exception("Delete Subnet Pool %s exception.", pool['id'])
Martin Kopece6819982019-02-18 12:34:52 +0000765
766 def dry_run(self):
767 pools = self.list()
768 self.data['subnetpools'] = pools
769
770 def save_state(self):
771 pools = self.list()
772 self.data['subnetpools'] = {}
773 for pool in pools:
774 self.data['subnetpools'][pool['id']] = pool['name']
775
776
David Patersonce781492014-09-18 01:07:01 -0400777# begin global services
Lukas Piwowarski3b1311f2019-11-12 10:43:40 +0000778class RegionService(BaseService):
779
780 def __init__(self, manager, **kwargs):
781 super(RegionService, self).__init__(kwargs)
782 self.client = manager.regions_client
783
784 def list(self):
785 client = self.client
786 regions = client.list_regions()
787 if not self.is_save_state:
788 regions = [region for region in regions['regions'] if region['id']
789 not in self.saved_state_json['regions'].keys()]
Martin Kopeca8578802020-04-07 08:19:14 +0000790 LOG.debug("List count, %s Regions", len(regions))
Lukas Piwowarski3b1311f2019-11-12 10:43:40 +0000791 return regions
792 else:
Martin Kopeca8578802020-04-07 08:19:14 +0000793 LOG.debug("List count, %s Regions", len(regions['regions']))
Lukas Piwowarski3b1311f2019-11-12 10:43:40 +0000794 return regions['regions']
795
796 def delete(self):
797 client = self.client
798 regions = self.list()
799 for region in regions:
800 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000801 LOG.debug("Deleting region with id %s", region['id'])
Lukas Piwowarski3b1311f2019-11-12 10:43:40 +0000802 client.delete_region(region['id'])
803 except Exception:
804 LOG.exception("Delete Region %s exception.", region['id'])
805
806 def dry_run(self):
807 regions = self.list()
808 self.data['regions'] = {}
809 for region in regions:
810 self.data['regions'][region['id']] = region
811
812 def save_state(self):
813 regions = self.list()
814 self.data['regions'] = {}
815 for region in regions:
816 self.data['regions'][region['id']] = region
817
818
David Patersonce781492014-09-18 01:07:01 -0400819class FlavorService(BaseService):
820 def __init__(self, manager, **kwargs):
821 super(FlavorService, self).__init__(kwargs)
822 self.client = manager.flavors_client
823
824 def list(self):
825 client = self.client
ghanshyam19973be2015-08-18 15:46:42 +0900826 flavors = client.list_flavors({"is_public": None})['flavors']
David Patersonce781492014-09-18 01:07:01 -0400827 if not self.is_save_state:
828 # recreate list removing saved flavors
829 flavors = [flavor for flavor in flavors if flavor['id']
830 not in self.saved_state_json['flavors'].keys()]
831
832 if self.is_preserve:
833 flavors = [flavor for flavor in flavors
834 if flavor['id'] not in CONF_FLAVORS]
Jordan Pittier525ec712016-12-07 17:51:26 +0100835 LOG.debug("List count, %s Flavors after reconcile", len(flavors))
David Patersonce781492014-09-18 01:07:01 -0400836 return flavors
837
838 def delete(self):
839 client = self.client
840 flavors = self.list()
841 for flavor in flavors:
842 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000843 LOG.debug("Deleting flavor with id %s", flavor['id'])
David Patersonce781492014-09-18 01:07:01 -0400844 client.delete_flavor(flavor['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400845 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000846 LOG.exception("Delete Flavor %s exception.", flavor['id'])
David Patersonce781492014-09-18 01:07:01 -0400847
848 def dry_run(self):
849 flavors = self.list()
850 self.data['flavors'] = flavors
851
852 def save_state(self):
853 flavors = self.list()
gordon chungc15f1bc2015-02-23 18:00:41 -0500854 self.data['flavors'] = {}
David Patersonce781492014-09-18 01:07:01 -0400855 for flavor in flavors:
gordon chungc15f1bc2015-02-23 18:00:41 -0500856 self.data['flavors'][flavor['id']] = flavor['name']
David Patersonce781492014-09-18 01:07:01 -0400857
858
859class ImageService(BaseService):
860 def __init__(self, manager, **kwargs):
861 super(ImageService, self).__init__(kwargs)
zhufl66275c22018-03-28 15:32:14 +0800862 self.client = manager.image_client_v2
David Patersonce781492014-09-18 01:07:01 -0400863
864 def list(self):
865 client = self.client
Lukas Piwowarski2c831242020-03-11 12:25:11 +0000866 response = client.list_images()
867 images = []
868 images.extend(response['images'])
869 while 'next' in response:
870 parsed = urllib.urlparse(response['next'])
871 marker = urllib.parse_qs(parsed.query)['marker'][0]
872 response = client.list_images(params={"marker": marker})
873 images.extend(response['images'])
874
David Patersonce781492014-09-18 01:07:01 -0400875 if not self.is_save_state:
876 images = [image for image in images if image['id']
877 not in self.saved_state_json['images'].keys()]
878 if self.is_preserve:
879 images = [image for image in images
880 if image['id'] not in CONF_IMAGES]
Jordan Pittier525ec712016-12-07 17:51:26 +0100881 LOG.debug("List count, %s Images after reconcile", len(images))
David Patersonce781492014-09-18 01:07:01 -0400882 return images
883
884 def delete(self):
885 client = self.client
886 images = self.list()
887 for image in images:
888 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000889 LOG.debug("Deleting image with id %s", image['id'])
David Patersonce781492014-09-18 01:07:01 -0400890 client.delete_image(image['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400891 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000892 LOG.exception("Delete Image %s exception.", image['id'])
David Patersonce781492014-09-18 01:07:01 -0400893
894 def dry_run(self):
895 images = self.list()
896 self.data['images'] = images
897
898 def save_state(self):
gordon chungc15f1bc2015-02-23 18:00:41 -0500899 self.data['images'] = {}
David Paterson82234022015-04-12 14:07:40 -0400900 images = self.list()
David Patersonce781492014-09-18 01:07:01 -0400901 for image in images:
gordon chungc15f1bc2015-02-23 18:00:41 -0500902 self.data['images'][image['id']] = image['name']
David Patersonce781492014-09-18 01:07:01 -0400903
904
Daniel Mellado82c83a52015-12-09 15:16:49 +0000905class UserService(BaseService):
906
907 def __init__(self, manager, **kwargs):
908 super(UserService, self).__init__(kwargs)
Arx Cruz05fe4bc2017-10-20 10:48:28 +0200909 self.client = manager.users_v3_client
David Patersonce781492014-09-18 01:07:01 -0400910
911 def list(self):
Daniel Mellado82c83a52015-12-09 15:16:49 +0000912 users = self.client.list_users()['users']
David Patersonce781492014-09-18 01:07:01 -0400913
914 if not self.is_save_state:
915 users = [user for user in users if user['id']
916 not in self.saved_state_json['users'].keys()]
917
918 if self.is_preserve:
919 users = [user for user in users if user['name']
920 not in CONF_USERS]
921
922 elif not self.is_save_state: # Never delete admin user
923 users = [user for user in users if user['name'] !=
David Paterson07661de2015-10-29 20:15:04 -0700924 CONF.auth.admin_username]
David Patersonce781492014-09-18 01:07:01 -0400925
Jordan Pittier525ec712016-12-07 17:51:26 +0100926 LOG.debug("List count, %s Users after reconcile", len(users))
David Patersonce781492014-09-18 01:07:01 -0400927 return users
928
929 def delete(self):
David Patersonce781492014-09-18 01:07:01 -0400930 users = self.list()
931 for user in users:
932 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000933 LOG.debug("Deleting user with id %s", user['id'])
Daniel Mellado82c83a52015-12-09 15:16:49 +0000934 self.client.delete_user(user['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400935 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000936 LOG.exception("Delete User %s exception.", user['id'])
David Patersonce781492014-09-18 01:07:01 -0400937
938 def dry_run(self):
939 users = self.list()
940 self.data['users'] = users
941
942 def save_state(self):
943 users = self.list()
gordon chungc15f1bc2015-02-23 18:00:41 -0500944 self.data['users'] = {}
David Patersonce781492014-09-18 01:07:01 -0400945 for user in users:
gordon chungc15f1bc2015-02-23 18:00:41 -0500946 self.data['users'][user['id']] = user['name']
David Patersonce781492014-09-18 01:07:01 -0400947
948
Daniel Melladob83ea562015-12-18 09:12:49 +0000949class RoleService(BaseService):
David Patersonce781492014-09-18 01:07:01 -0400950
Daniel Mellado6b16b922015-12-07 12:43:08 +0000951 def __init__(self, manager, **kwargs):
952 super(RoleService, self).__init__(kwargs)
Martin Kopecbd5be762019-07-13 22:42:08 +0000953 self.client = manager.roles_v3_client
Daniel Mellado6b16b922015-12-07 12:43:08 +0000954
David Patersonce781492014-09-18 01:07:01 -0400955 def list(self):
David Patersonce781492014-09-18 01:07:01 -0400956 try:
Daniel Mellado6b16b922015-12-07 12:43:08 +0000957 roles = self.client.list_roles()['roles']
David Patersonce781492014-09-18 01:07:01 -0400958 # reconcile roles with saved state and never list admin role
959 if not self.is_save_state:
960 roles = [role for role in roles if
961 (role['id'] not in
Federico Ressi2d6bcaa2018-04-11 12:37:36 +0200962 self.saved_state_json['roles'].keys() and
963 role['name'] != CONF.identity.admin_role)]
Jordan Pittier525ec712016-12-07 17:51:26 +0100964 LOG.debug("List count, %s Roles after reconcile", len(roles))
David Patersonce781492014-09-18 01:07:01 -0400965 return roles
David Patersone41ebca2015-04-09 05:40:12 -0400966 except Exception:
967 LOG.exception("Cannot retrieve Roles.")
David Patersonce781492014-09-18 01:07:01 -0400968 return []
969
970 def delete(self):
David Patersonce781492014-09-18 01:07:01 -0400971 roles = self.list()
972 for role in roles:
973 try:
Martin Kopeca8578802020-04-07 08:19:14 +0000974 LOG.debug("Deleting role with id %s", role['id'])
Daniel Mellado6b16b922015-12-07 12:43:08 +0000975 self.client.delete_role(role['id'])
David Patersone41ebca2015-04-09 05:40:12 -0400976 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +0000977 LOG.exception("Delete Role %s exception.", role['id'])
David Patersonce781492014-09-18 01:07:01 -0400978
979 def dry_run(self):
980 roles = self.list()
981 self.data['roles'] = roles
982
983 def save_state(self):
984 roles = self.list()
gordon chungc15f1bc2015-02-23 18:00:41 -0500985 self.data['roles'] = {}
David Patersonce781492014-09-18 01:07:01 -0400986 for role in roles:
gordon chungc15f1bc2015-02-23 18:00:41 -0500987 self.data['roles'][role['id']] = role['name']
David Patersonce781492014-09-18 01:07:01 -0400988
989
Arx Cruz05fe4bc2017-10-20 10:48:28 +0200990class ProjectService(BaseService):
David Patersonce781492014-09-18 01:07:01 -0400991
Daniel Melladob04da902015-11-20 17:43:12 +0100992 def __init__(self, manager, **kwargs):
Arx Cruz05fe4bc2017-10-20 10:48:28 +0200993 super(ProjectService, self).__init__(kwargs)
994 self.client = manager.projects_client
Daniel Melladob04da902015-11-20 17:43:12 +0100995
David Patersonce781492014-09-18 01:07:01 -0400996 def list(self):
Arx Cruz05fe4bc2017-10-20 10:48:28 +0200997 projects = self.client.list_projects()['projects']
David Patersonce781492014-09-18 01:07:01 -0400998 if not self.is_save_state:
Federico Ressi2d6bcaa2018-04-11 12:37:36 +0200999 project_ids = self.saved_state_json['projects']
1000 projects = [project
1001 for project in projects
1002 if (project['id'] not in project_ids and
1003 project['name'] != CONF.auth.admin_project_name)]
David Patersonce781492014-09-18 01:07:01 -04001004
1005 if self.is_preserve:
Federico Ressi2d6bcaa2018-04-11 12:37:36 +02001006 projects = [project
1007 for project in projects
1008 if project['name'] not in CONF_PROJECTS]
David Patersonce781492014-09-18 01:07:01 -04001009
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001010 LOG.debug("List count, %s Projects after reconcile", len(projects))
1011 return projects
David Patersonce781492014-09-18 01:07:01 -04001012
1013 def delete(self):
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001014 projects = self.list()
1015 for project in projects:
David Patersonce781492014-09-18 01:07:01 -04001016 try:
Martin Kopeca8578802020-04-07 08:19:14 +00001017 LOG.debug("Deleting project with id %s", project['id'])
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001018 self.client.delete_project(project['id'])
David Patersone41ebca2015-04-09 05:40:12 -04001019 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +00001020 LOG.exception("Delete project %s exception.", project['id'])
David Patersonce781492014-09-18 01:07:01 -04001021
1022 def dry_run(self):
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001023 projects = self.list()
1024 self.data['projects'] = projects
David Patersonce781492014-09-18 01:07:01 -04001025
1026 def save_state(self):
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001027 projects = self.list()
1028 self.data['projects'] = {}
1029 for project in projects:
1030 self.data['projects'][project['id']] = project['name']
David Patersonce781492014-09-18 01:07:01 -04001031
1032
1033class DomainService(BaseService):
1034
1035 def __init__(self, manager, **kwargs):
1036 super(DomainService, self).__init__(kwargs)
Daniel Mellado91a26b62016-02-11 11:13:04 +00001037 self.client = manager.domains_client
David Patersonce781492014-09-18 01:07:01 -04001038
1039 def list(self):
1040 client = self.client
Thomas Bechtold48268a02015-08-30 19:37:46 +02001041 domains = client.list_domains()['domains']
David Patersonce781492014-09-18 01:07:01 -04001042 if not self.is_save_state:
1043 domains = [domain for domain in domains if domain['id']
1044 not in self.saved_state_json['domains'].keys()]
1045
Jordan Pittier525ec712016-12-07 17:51:26 +01001046 LOG.debug("List count, %s Domains after reconcile", len(domains))
David Patersonce781492014-09-18 01:07:01 -04001047 return domains
1048
1049 def delete(self):
1050 client = self.client
1051 domains = self.list()
1052 for domain in domains:
1053 try:
Martin Kopeca8578802020-04-07 08:19:14 +00001054 LOG.debug("Deleting domain with id %s", domain['id'])
David Patersonce781492014-09-18 01:07:01 -04001055 client.update_domain(domain['id'], enabled=False)
1056 client.delete_domain(domain['id'])
David Patersone41ebca2015-04-09 05:40:12 -04001057 except Exception:
Martin Kopecfd01fe92019-02-27 08:46:05 +00001058 LOG.exception("Delete Domain %s exception.", domain['id'])
David Patersonce781492014-09-18 01:07:01 -04001059
1060 def dry_run(self):
1061 domains = self.list()
1062 self.data['domains'] = domains
1063
1064 def save_state(self):
1065 domains = self.list()
gordon chungc15f1bc2015-02-23 18:00:41 -05001066 self.data['domains'] = {}
David Patersonce781492014-09-18 01:07:01 -04001067 for domain in domains:
gordon chungc15f1bc2015-02-23 18:00:41 -05001068 self.data['domains'][domain['id']] = domain['name']
David Patersonce781492014-09-18 01:07:01 -04001069
1070
Martin Kopec56c0b2b2019-11-13 12:50:07 +00001071def get_project_associated_cleanup_services():
1072 """Returns list of project service classes.
1073
1074 The list contains services whose resources need to be deleted prior,
1075 the project they are associated with, deletion. The resources cannot be
1076 most likely deleted after the project is deleted first.
1077 """
1078 project_associated_services = []
ghanshyame4796f82016-04-13 15:49:22 +09001079 # TODO(gmann): Tempest should provide some plugin hook for cleanup
1080 # script extension to plugin tests also.
David Patersonce781492014-09-18 01:07:01 -04001081 if IS_NOVA:
Martin Kopec56c0b2b2019-11-13 12:50:07 +00001082 project_associated_services.append(NovaQuotaService)
David Patersonce781492014-09-18 01:07:01 -04001083 if IS_CINDER:
Martin Kopec56c0b2b2019-11-13 12:50:07 +00001084 project_associated_services.append(VolumeQuotaService)
Lukas Piwowarski97b84112020-03-25 13:57:30 +00001085 if IS_NEUTRON:
1086 project_associated_services.append(NetworkQuotaService)
Martin Kopec56c0b2b2019-11-13 12:50:07 +00001087 return project_associated_services
1088
1089
1090def get_resource_cleanup_services():
1091 """Returns list of project related classes.
1092
1093 The list contains services whose resources are associated with a project,
1094 however, their deletion is possible also after the project is deleted
1095 first.
1096 """
1097 resource_cleanup_services = []
1098 # TODO(gmann): Tempest should provide some plugin hook for cleanup
1099 # script extension to plugin tests also.
1100 if IS_NOVA:
1101 resource_cleanup_services.append(ServerService)
1102 resource_cleanup_services.append(KeyPairService)
1103 resource_cleanup_services.append(ServerGroupService)
1104 if IS_NEUTRON:
1105 resource_cleanup_services.append(NetworkFloatingIpService)
1106 if utils.is_extension_enabled('metering', 'network'):
1107 resource_cleanup_services.append(NetworkMeteringLabelRuleService)
1108 resource_cleanup_services.append(NetworkMeteringLabelService)
1109 resource_cleanup_services.append(NetworkRouterService)
1110 resource_cleanup_services.append(NetworkPortService)
1111 resource_cleanup_services.append(NetworkSubnetService)
1112 resource_cleanup_services.append(NetworkService)
1113 resource_cleanup_services.append(NetworkSecGroupService)
1114 resource_cleanup_services.append(NetworkSubnetPoolsService)
1115 if IS_CINDER:
1116 resource_cleanup_services.append(SnapshotService)
1117 resource_cleanup_services.append(VolumeService)
1118 return resource_cleanup_services
David Patersonce781492014-09-18 01:07:01 -04001119
1120
1121def get_global_cleanup_services():
1122 global_services = []
1123 if IS_NOVA:
1124 global_services.append(FlavorService)
1125 if IS_GLANCE:
1126 global_services.append(ImageService)
1127 global_services.append(UserService)
Arx Cruz05fe4bc2017-10-20 10:48:28 +02001128 global_services.append(ProjectService)
David Patersonce781492014-09-18 01:07:01 -04001129 global_services.append(DomainService)
1130 global_services.append(RoleService)
Lukas Piwowarski3b1311f2019-11-12 10:43:40 +00001131 global_services.append(RegionService)
David Patersonce781492014-09-18 01:07:01 -04001132 return global_services