bug fix: use PASS/FAIL in Onos instead of passed/failed
[functest.git] / utils / openstack_utils.py
1 #!/usr/bin/env python
2 #
3 # jose.lausuch@ericsson.com
4 # valentin.boucher@orange.com
5 # All rights reserved. This program and the accompanying materials
6 # are made available under the terms of the Apache License, Version 2.0
7 # which accompanies this distribution, and is available at
8 # http://www.apache.org/licenses/LICENSE-2.0
9 #
10
11 import os
12 import os.path
13 import subprocess
14 import sys
15 import time
16
17 from glanceclient import client as glanceclient
18 from keystoneclient.v2_0 import client as keystoneclient
19 from neutronclient.v2_0 import client as neutronclient
20 from novaclient import client as novaclient
21
22
23 # *********************************************
24 #   CREDENTIALS
25 # *********************************************
26 def check_credentials():
27     """
28     Check if the OpenStack credentials (openrc) are sourced
29     """
30     env_vars = ['OS_AUTH_URL', 'OS_USERNAME', 'OS_PASSWORD', 'OS_TENANT_NAME']
31     return all(map(lambda v: v in os.environ and os.environ[v], env_vars))
32
33
34 def get_credentials(service):
35     """Returns a creds dictionary filled with the following keys:
36     * username
37     * password/api_key (depending on the service)
38     * tenant_name/project_id (depending on the service)
39     * auth_url
40     :param service: a string indicating the name of the service
41                     requesting the credentials.
42     """
43     creds = {}
44
45     # Check that the env vars exists:
46     envvars = ('OS_USERNAME', 'OS_PASSWORD', 'OS_AUTH_URL', 'OS_TENANT_NAME')
47     for envvar in envvars:
48         if os.getenv(envvar) is None:
49             print("'%s' is not exported as an env variable." % envvar)
50             exit(-1)
51
52     # Unfortunately, each of the OpenStack client will request slightly
53     # different entries in their credentials dict.
54     if service.lower() in ("nova", "cinder"):
55         password = "api_key"
56         tenant = "project_id"
57     else:
58         password = "password"
59         tenant = "tenant_name"
60
61     # The most common way to pass these info to the script is to do it through
62     # environment variables.
63     creds.update({
64         "username": os.environ.get("OS_USERNAME"),
65         password: os.environ.get("OS_PASSWORD"),
66         "auth_url": os.environ.get("OS_AUTH_URL"),
67         tenant: os.environ.get("OS_TENANT_NAME")
68     })
69     cacert = os.environ.get("OS_CACERT")
70     if cacert is not None:
71         # each openstack client uses differnt kwargs for this
72         creds.update({"cacert": cacert,
73                       "ca_cert": cacert,
74                       "https_ca_cert": cacert,
75                       "https_cacert": cacert,
76                       "ca_file": cacert})
77         creds.update({"insecure": "True", "https_insecure": "True"})
78         if not os.path.isfile(cacert):
79             print ("WARNING: The 'OS_CACERT' environment variable is " +
80                    "set to %s but the file does not exist." % cacert)
81     return creds
82
83
84 def source_credentials(rc_file):
85     pipe = subprocess.Popen(". %s; env" % rc_file, stdout=subprocess.PIPE,
86                             shell=True)
87     output = pipe.communicate()[0]
88     env = dict((line.split("=", 1) for line in output.splitlines()))
89     os.environ.update(env)
90     return env
91
92
93 # *********************************************
94 #   CLIENTS
95 # *********************************************
96 def get_keystone_client():
97     creds_keystone = get_credentials("keystone")
98     return keystoneclient.Client(**creds_keystone)
99
100
101 def get_nova_client():
102     creds_nova = get_credentials("nova")
103     return novaclient.Client('2', **creds_nova)
104
105
106 def get_neutron_client():
107     creds_neutron = get_credentials("neutron")
108     return neutronclient.Client(**creds_neutron)
109
110
111 def get_glance_client():
112     keystone_client = get_keystone_client()
113     glance_endpoint = keystone_client.service_catalog.url_for(
114         service_type='image', endpoint_type='publicURL')
115     return glanceclient.Client(1, glance_endpoint,
116                                token=keystone_client.auth_token)
117
118 # *********************************************
119 #   NOVA
120 # *********************************************
121
122
123 def get_instances(nova_client):
124     try:
125         instances = nova_client.servers.list(search_opts={'all_tenants': 1})
126         return instances
127     except Exception, e:
128         print "Error [get_instances(nova_client)]:", e
129         return None
130
131
132 def get_instance_status(nova_client, instance):
133     try:
134         instance = nova_client.servers.get(instance.id)
135         return instance.status
136     except:
137         # print ("Error [get_instance_status(nova_client, '%s')]:" %
138         #        str(instance)), e
139         return None
140
141
142 def get_instance_by_name(nova_client, instance_name):
143     try:
144         instance = nova_client.servers.find(name=instance_name)
145         return instance
146     except Exception, e:
147         print ("Error [get_instance_by_name(nova_client, '%s')]:" %
148                instance_name), e
149         return None
150
151
152 def get_flavor_id(nova_client, flavor_name):
153     flavors = nova_client.flavors.list(detailed=True)
154     id = ''
155     for f in flavors:
156         if f.name == flavor_name:
157             id = f.id
158             break
159     return id
160
161
162 def get_flavor_id_by_ram_range(nova_client, min_ram, max_ram):
163     flavors = nova_client.flavors.list(detailed=True)
164     id = ''
165     for f in flavors:
166         if min_ram <= f.ram and f.ram <= max_ram:
167             id = f.id
168             break
169     return id
170
171
172 def get_floating_ips(nova_client):
173     try:
174         floating_ips = nova_client.floating_ips.list()
175         return floating_ips
176     except Exception, e:
177         print "Error [get_floating_ips(nova_client)]:", e
178         return None
179
180
181 def get_hypervisors(nova_client):
182     try:
183         nodes = []
184         hypervisors = nova_client.hypervisors.list()
185         for hypervisor in hypervisors:
186             if hypervisor.state == "up":
187                 nodes.append(hypervisor.hypervisor_hostname)
188         return nodes
189     except Exception, e:
190         print "Error [get_hypervisors(nova_client)]:", e
191         return None
192
193
194 def create_flavor(nova_client, flavor_name, ram, disk, vcpus):
195     try:
196         flavor = nova_client.flavors.create(flavor_name, ram, vcpus, disk)
197     except Exception, e:
198         print ("Error [create_flavor(nova_client, '%s', '%s', '%s', "
199                "'%s')]:" % (flavor_name, ram, disk, vcpus)), e
200         return None
201     return flavor.id
202
203
204 def create_instance(flavor_name,
205                     image_id,
206                     network_id,
207                     instance_name="functest-vm",
208                     confdrive=True,
209                     userdata=None,
210                     av_zone=''):
211     nova_client = get_nova_client()
212     try:
213         flavor = nova_client.flavors.find(name=flavor_name)
214     except:
215         print("Error: Flavor '%s' not found. Available flavors are:" %
216               flavor_name)
217         print(nova_client.flavor.list())
218         return -1
219     if userdata is None:
220         instance = nova_client.servers.create(
221             name=instance_name,
222             flavor=flavor,
223             image=image_id,
224             nics=[{"net-id": network_id}],
225             availability_zone=av_zone
226         )
227     else:
228         instance = nova_client.servers.create(
229             name=instance_name,
230             flavor=flavor,
231             image=image_id,
232             nics=[{"net-id": network_id}],
233             config_drive=confdrive,
234             userdata=userdata,
235             availability_zone=av_zone
236         )
237     return instance
238
239
240 def create_instance_and_wait_for_active(flavor_name,
241                                         image_id,
242                                         network_id,
243                                         instance_name="",
244                                         config_drive=False,
245                                         userdata="",
246                                         av_zone=''):
247     SLEEP = 3
248     VM_BOOT_TIMEOUT = 180
249     nova_client = get_nova_client()
250     instance = create_instance(flavor_name,
251                                image_id,
252                                network_id,
253                                instance_name,
254                                config_drive,
255                                userdata,
256                                av_zone)
257
258     count = VM_BOOT_TIMEOUT / SLEEP
259     for n in range(count, -1, -1):
260         status = get_instance_status(nova_client, instance)
261         if status.lower() == "active":
262             return instance
263         elif status.lower() == "error":
264             print("The instance %s went to ERROR status." % instance_name)
265             return None
266         time.sleep(SLEEP)
267     print("Timeout booting the instance %s." % instance_name)
268     return None
269
270
271 def create_floating_ip(neutron_client):
272     extnet_id = get_external_net_id(neutron_client)
273     props = {'floating_network_id': extnet_id}
274     try:
275         ip_json = neutron_client.create_floatingip({'floatingip': props})
276         fip_addr = ip_json['floatingip']['floating_ip_address']
277         fip_id = ip_json['floatingip']['id']
278     except Exception, e:
279         print "Error [create_floating_ip(neutron_client)]:", e
280         return None
281     return {'fip_addr': fip_addr, 'fip_id': fip_id}
282
283
284 def add_floating_ip(nova_client, server_id, floatingip_id):
285     try:
286         nova_client.servers.add_floating_ip(server_id, floatingip_id)
287         return True
288     except Exception, e:
289         print ("Error [add_floating_ip(nova_client, '%s', '%s')]:" %
290                (server_id, floatingip_id)), e
291         return False
292
293
294 def delete_instance(nova_client, instance_id):
295     try:
296         nova_client.servers.force_delete(instance_id)
297         return True
298     except Exception, e:
299         print "Error [delete_instance(nova_client, '%s')]:" % instance_id, e
300         return False
301
302
303 def delete_floating_ip(nova_client, floatingip_id):
304     try:
305         nova_client.floating_ips.delete(floatingip_id)
306         return True
307     except Exception, e:
308         print ("Error [delete_floating_ip(nova_client, '%s')]:" %
309                floatingip_id), e
310         return False
311
312
313 # *********************************************
314 #   NEUTRON
315 # *********************************************
316 def get_network_list(neutron_client):
317     network_list = neutron_client.list_networks()['networks']
318     if len(network_list) == 0:
319         return None
320     else:
321         return network_list
322
323
324 def get_router_list(neutron_client):
325     router_list = neutron_client.list_routers()['routers']
326     if len(router_list) == 0:
327         return None
328     else:
329         return router_list
330
331
332 def get_port_list(neutron_client):
333     port_list = neutron_client.list_ports()['ports']
334     if len(port_list) == 0:
335         return None
336     else:
337         return port_list
338
339
340 def get_network_id(neutron_client, network_name):
341     networks = neutron_client.list_networks()['networks']
342     id = ''
343     for n in networks:
344         if n['name'] == network_name:
345             id = n['id']
346             break
347     return id
348
349
350 def get_subnet_id(neutron_client, subnet_name):
351     subnets = neutron_client.list_subnets()['subnets']
352     id = ''
353     for s in subnets:
354         if s['name'] == subnet_name:
355             id = s['id']
356             break
357     return id
358
359
360 def get_router_id(neutron_client, router_name):
361     routers = neutron_client.list_routers()['routers']
362     id = ''
363     for r in routers:
364         if r['name'] == router_name:
365             id = r['id']
366             break
367     return id
368
369
370 def get_private_net(neutron_client):
371     # Checks if there is an existing shared private network
372     networks = neutron_client.list_networks()['networks']
373     if len(networks) == 0:
374         return None
375     for net in networks:
376         if (net['router:external'] is False) and (net['shared'] is True):
377             return net
378     return None
379
380
381 def get_external_net(neutron_client):
382     for network in neutron_client.list_networks()['networks']:
383         if network['router:external']:
384             return network['name']
385     return False
386
387
388 def get_external_net_id(neutron_client):
389     for network in neutron_client.list_networks()['networks']:
390         if network['router:external']:
391             return network['id']
392     return False
393
394
395 def check_neutron_net(neutron_client, net_name):
396     for network in neutron_client.list_networks()['networks']:
397         if network['name'] == net_name:
398             for subnet in network['subnets']:
399                 return True
400     return False
401
402
403 def create_neutron_net(neutron_client, name):
404     json_body = {'network': {'name': name,
405                              'admin_state_up': True}}
406     try:
407         network = neutron_client.create_network(body=json_body)
408         network_dict = network['network']
409         return network_dict['id']
410     except Exception, e:
411         print "Error [create_neutron_net(neutron_client, '%s')]:" % name, e
412         return False
413
414
415 def create_neutron_subnet(neutron_client, name, cidr, net_id):
416     json_body = {'subnets': [{'name': name, 'cidr': cidr,
417                               'ip_version': 4, 'network_id': net_id}]}
418     try:
419         subnet = neutron_client.create_subnet(body=json_body)
420         return subnet['subnets'][0]['id']
421     except Exception, e:
422         print ("Error [create_neutron_subnet(neutron_client, '%s', '%s', "
423                "'%s')]:" % (name, cidr, net_id)), e
424         return False
425
426
427 def create_neutron_router(neutron_client, name):
428     json_body = {'router': {'name': name, 'admin_state_up': True}}
429     try:
430         router = neutron_client.create_router(json_body)
431         return router['router']['id']
432     except Exception, e:
433         print "Error [create_neutron_router(neutron_client, '%s')]:" % name, e
434         return False
435
436
437 def create_neutron_port(neutron_client, name, network_id, ip):
438     json_body = {'port': {
439                  'admin_state_up': True,
440                  'name': name,
441                  'network_id': network_id,
442                  'fixed_ips': [{"ip_address": ip}]
443                  }}
444     try:
445         port = neutron_client.create_port(body=json_body)
446         return port['port']['id']
447     except Exception, e:
448         print ("Error [create_neutron_port(neutron_client, '%s', '%s', "
449                "'%s')]:" % (name, network_id, ip)), e
450         return False
451
452
453 def update_neutron_net(neutron_client, network_id, shared=False):
454     json_body = {'network': {'shared': shared}}
455     try:
456         neutron_client.update_network(network_id, body=json_body)
457         return True
458     except Exception, e:
459         print ("Error [update_neutron_net(neutron_client, '%s', '%s')]:" %
460                (network_id, str(shared))), e
461         return False
462
463
464 def update_neutron_port(neutron_client, port_id, device_owner):
465     json_body = {'port': {
466                  'device_owner': device_owner,
467                  }}
468     try:
469         port = neutron_client.update_port(port=port_id,
470                                           body=json_body)
471         return port['port']['id']
472     except Exception, e:
473         print ("Error [update_neutron_port(neutron_client, '%s', '%s')]:" %
474                (port_id, device_owner)), e
475         return False
476
477
478 def add_interface_router(neutron_client, router_id, subnet_id):
479     json_body = {"subnet_id": subnet_id}
480     try:
481         neutron_client.add_interface_router(router=router_id, body=json_body)
482         return True
483     except Exception, e:
484         print ("Error [add_interface_router(neutron_client, '%s', '%s')]:" %
485                (router_id, subnet_id)), e
486         return False
487
488
489 def add_gateway_router(neutron_client, router_id):
490     ext_net_id = get_external_net_id(neutron_client)
491     router_dict = {'network_id': ext_net_id}
492     try:
493         neutron_client.add_gateway_router(router_id, router_dict)
494         return True
495     except Exception, e:
496         print ("Error [add_gateway_router(neutron_client, '%s')]:" %
497                router_id), e
498         return False
499
500
501 def delete_neutron_net(neutron_client, network_id):
502     try:
503         neutron_client.delete_network(network_id)
504         return True
505     except Exception, e:
506         print ("Error [delete_neutron_net(neutron_client, '%s')]:" %
507                network_id), e
508         return False
509
510
511 def delete_neutron_subnet(neutron_client, subnet_id):
512     try:
513         neutron_client.delete_subnet(subnet_id)
514         return True
515     except Exception, e:
516         print ("Error [delete_neutron_subnet(neutron_client, '%s')]:" %
517                subnet_id), e
518         return False
519
520
521 def delete_neutron_router(neutron_client, router_id):
522     try:
523         neutron_client.delete_router(router=router_id)
524         return True
525     except Exception, e:
526         print ("Error [delete_neutron_router(neutron_client, '%s')]:" %
527                router_id), e
528         return False
529
530
531 def delete_neutron_port(neutron_client, port_id):
532     try:
533         neutron_client.delete_port(port_id)
534         return True
535     except Exception, e:
536         print "Error [delete_neutron_port(neutron_client, '%s')]:" % port_id, e
537         return False
538
539
540 def remove_interface_router(neutron_client, router_id, subnet_id):
541     json_body = {"subnet_id": subnet_id}
542     try:
543         neutron_client.remove_interface_router(router=router_id,
544                                                body=json_body)
545         return True
546     except Exception, e:
547         print ("Error [remove_interface_router(neutron_client, '%s', '%s')]:" %
548                (router_id, subnet_id)), e
549         return False
550
551
552 def remove_gateway_router(neutron_client, router_id):
553     try:
554         neutron_client.remove_gateway_router(router_id)
555         return True
556     except Exception, e:
557         print ("Error [remove_gateway_router(neutron_client, '%s')]:" %
558                router_id), e
559         return False
560
561
562 def create_network_full(logger,
563                         neutron_client,
564                         net_name,
565                         subnet_name,
566                         router_name,
567                         cidr):
568
569     # Check if the network already exists
570     network_id = get_network_id(neutron_client, net_name)
571     subnet_id = get_subnet_id(neutron_client, subnet_name)
572     router_id = get_router_id(neutron_client, router_name)
573
574     if network_id != '' and subnet_id != '' and router_id != '':
575         logger.info("A network with name '%s' already exists..." % net_name)
576     else:
577         neutron_client.format = 'json'
578         logger.info('Creating neutron network %s...' % net_name)
579         network_id = create_neutron_net(neutron_client, net_name)
580
581         if not network_id:
582             return False
583
584         logger.debug("Network '%s' created successfully" % network_id)
585         logger.debug('Creating Subnet....')
586         subnet_id = create_neutron_subnet(neutron_client, subnet_name,
587                                           cidr, network_id)
588         if not subnet_id:
589             return False
590
591         logger.debug("Subnet '%s' created successfully" % subnet_id)
592         logger.debug('Creating Router...')
593         router_id = create_neutron_router(neutron_client, router_name)
594
595         if not router_id:
596             return False
597
598         logger.debug("Router '%s' created successfully" % router_id)
599         logger.debug('Adding router to subnet...')
600
601         if not add_interface_router(neutron_client, router_id, subnet_id):
602             return False
603
604         logger.debug("Interface added successfully.")
605
606         logger.debug('Adding gateway to router...')
607         if not add_gateway_router(neutron_client, router_id):
608             return False
609
610         logger.debug("Gateway added successfully.")
611
612     network_dic = {'net_id': network_id,
613                    'subnet_id': subnet_id,
614                    'router_id': router_id}
615     return network_dic
616
617
618 def create_bgpvpn(neutron_client, **kwargs):
619     # route_distinguishers
620     # route_targets
621     json_body = {"bgpvpn": kwargs}
622     return neutron_client.create_bgpvpn(json_body)
623
624
625 def create_network_association(neutron_client, bgpvpn_id, neutron_network_id):
626     json_body = {"network_association": {"network_id": neutron_network_id}}
627     return neutron_client.create_network_association(bgpvpn_id, json_body)
628
629
630 def update_bgpvpn(neutron_client, bgpvpn_id, **kwargs):
631     json_body = {"bgpvpn": kwargs}
632     return neutron_client.update_bgpvpn(bgpvpn_id, json_body)
633
634
635 def delete_bgpvpn(neutron_client, bgpvpn_id):
636     return neutron_client.delete_bgpvpn(bgpvpn_id)
637
638
639 # *********************************************
640 #   SEC GROUPS
641 # *********************************************
642
643
644 def get_security_groups(neutron_client):
645     try:
646         security_groups = neutron_client.list_security_groups()[
647             'security_groups']
648         return security_groups
649     except Exception, e:
650         print "Error [get_security_groups(neutron_client)]:", e
651         return None
652
653
654 def get_security_group_id(neutron_client, sg_name):
655     security_groups = get_security_groups(neutron_client)
656     id = ''
657     for sg in security_groups:
658         if sg['name'] == sg_name:
659             id = sg['id']
660             break
661     return id
662
663
664 def create_security_group(neutron_client, sg_name, sg_description):
665     json_body = {'security_group': {'name': sg_name,
666                                     'description': sg_description}}
667     try:
668         secgroup = neutron_client.create_security_group(json_body)
669         return secgroup['security_group']
670     except Exception, e:
671         print ("Error [create_security_group(neutron_client, '%s', '%s')]:" %
672                (sg_name, sg_description)), e
673         return False
674
675
676 def create_secgroup_rule(neutron_client, sg_id, direction, protocol,
677                          port_range_min=None, port_range_max=None):
678     if port_range_min is None and port_range_max is None:
679         json_body = {'security_group_rule': {'direction': direction,
680                                              'security_group_id': sg_id,
681                                              'protocol': protocol}}
682     elif port_range_min is not None and port_range_max is not None:
683         json_body = {'security_group_rule': {'direction': direction,
684                                              'security_group_id': sg_id,
685                                              'port_range_min': port_range_min,
686                                              'port_range_max': port_range_max,
687                                              'protocol': protocol}}
688     else:
689         print ("Error [create_secgroup_rule(neutron_client, '%s', '%s', "
690                "'%s', '%s', '%s', '%s')]:" % (neutron_client, sg_id, direction,
691                                               port_range_min, port_range_max,
692                                               protocol),
693                " Invalid values for port_range_min, port_range_max")
694         return False
695     try:
696         neutron_client.create_security_group_rule(json_body)
697         return True
698     except Exception, e:
699         print ("Error [create_secgroup_rule(neutron_client, '%s', '%s', "
700                "'%s', '%s', '%s', '%s')]:" % (neutron_client, sg_id, direction,
701                                               port_range_min, port_range_max,
702                                               protocol)), e
703         return False
704
705
706 def create_security_group_full(logger, neutron_client,
707                                sg_name, sg_description):
708     sg_id = get_security_group_id(neutron_client, sg_name)
709     if sg_id != '':
710         logger.info("Using existing security group '%s'..." % sg_name)
711     else:
712         logger.info("Creating security group  '%s'..." % sg_name)
713         SECGROUP = create_security_group(neutron_client,
714                                          sg_name,
715                                          sg_description)
716         if not SECGROUP:
717             logger.error("Failed to create the security group...")
718             return False
719
720         sg_id = SECGROUP['id']
721
722         logger.debug("Security group '%s' with ID=%s created successfully."
723                      % (SECGROUP['name'], sg_id))
724
725         logger.debug("Adding ICMP rules in security group '%s'..."
726                      % sg_name)
727         if not create_secgroup_rule(neutron_client, sg_id,
728                                     'ingress', 'icmp'):
729             logger.error("Failed to create the security group rule...")
730             return False
731
732         logger.debug("Adding SSH rules in security group '%s'..."
733                      % sg_name)
734         if not create_secgroup_rule(
735                 neutron_client, sg_id, 'ingress', 'tcp', '22', '22'):
736             logger.error("Failed to create the security group rule...")
737             return False
738
739         if not create_secgroup_rule(
740                 neutron_client, sg_id, 'egress', 'tcp', '22', '22'):
741             logger.error("Failed to create the security group rule...")
742             return False
743     return sg_id
744
745
746 def add_secgroup_to_instance(nova_client, instance_id, secgroup_id):
747     try:
748         nova_client.servers.add_security_group(instance_id, secgroup_id)
749         return True
750     except Exception, e:
751         print ("Error [add_secgroup_to_instance(nova_client, '%s', '%s')]: " %
752                (instance_id, secgroup_id)), e
753         return False
754
755
756 def update_sg_quota(neutron_client, tenant_id, sg_quota, sg_rule_quota):
757     json_body = {"quota": {
758         "security_group": sg_quota,
759         "security_group_rule": sg_rule_quota
760     }}
761
762     try:
763         neutron_client.update_quota(tenant_id=tenant_id,
764                                     body=json_body)
765         return True
766     except Exception, e:
767         print ("Error [update_sg_quota(neutron_client, '%s', '%s', "
768                "'%s')]:" % (tenant_id, sg_quota, sg_rule_quota)), e
769         return False
770
771
772 def delete_security_group(neutron_client, secgroup_id):
773     try:
774         neutron_client.delete_security_group(secgroup_id)
775         return True
776     except Exception, e:
777         print ("Error [delete_security_group(neutron_client, '%s')]:" %
778                secgroup_id), e
779         return False
780
781
782 # *********************************************
783 #   GLANCE
784 # *********************************************
785 def get_images(nova_client):
786     try:
787         images = nova_client.images.list()
788         return images
789     except Exception, e:
790         print "Error [get_images]:", e
791         return None
792
793
794 def get_image_id(glance_client, image_name):
795     images = glance_client.images.list()
796     id = ''
797     for i in images:
798         if i.name == image_name:
799             id = i.id
800             break
801     return id
802
803
804 def create_glance_image(glance_client, image_name, file_path, disk="qcow2",
805                         container="bare", public=True, logger=None):
806     if not os.path.isfile(file_path):
807         print "Error: file " + file_path + " does not exist."
808         return False
809     try:
810         image_id = get_image_id(glance_client, image_name)
811         if image_id != '':
812             if logger:
813                 logger.info("Image %s already exists." % image_name)
814         else:
815             if logger:
816                 logger.info("Creating image '%s' from '%s'..." % (image_name,
817                                                                   file_path))
818             with open(file_path) as fimage:
819                 image = glance_client.images.create(name=image_name,
820                                                     is_public=public,
821                                                     disk_format=disk,
822                                                     container_format=container,
823                                                     data=fimage)
824             image_id = image.id
825         return image_id
826     except Exception, e:
827         print ("Error [create_glance_image(glance_client, '%s', '%s', "
828                "'%s')]:" % (image_name, file_path, str(public))), e
829         return False
830
831
832 def delete_glance_image(nova_client, image_id):
833     try:
834         nova_client.images.delete(image_id)
835         return True
836     except Exception, e:
837         print ("Error [delete_glance_image(nova_client, '%s')]:" % image_id), e
838         return False
839
840
841 # *********************************************
842 #   CINDER
843 # *********************************************
844 def get_volumes(cinder_client):
845     try:
846         volumes = cinder_client.volumes.list(search_opts={'all_tenants': 1})
847         return volumes
848     except Exception, e:
849         print "Error [get_volumes(cinder_client)]:", e
850         return None
851
852
853 def list_volume_types(cinder_client, public=True, private=True):
854     try:
855         volume_types = cinder_client.volume_types.list()
856         if not public:
857             volume_types = [vt for vt in volume_types if not vt.is_public]
858         if not private:
859             volume_types = [vt for vt in volume_types if vt.is_public]
860         return volume_types
861     except Exception, e:
862         print "Error [list_volume_types(cinder_client)]:", e
863         return None
864
865
866 def create_volume_type(cinder_client, name):
867     try:
868         volume_type = cinder_client.volume_types.create(name)
869         return volume_type
870     except Exception, e:
871         print "Error [create_volume_type(cinder_client, '%s')]:" % name, e
872         return None
873
874
875 def update_cinder_quota(cinder_client, tenant_id, vols_quota,
876                         snapshots_quota, gigabytes_quota):
877     quotas_values = {"volumes": vols_quota,
878                      "snapshots": snapshots_quota,
879                      "gigabytes": gigabytes_quota}
880
881     try:
882         cinder_client.quotas.update(tenant_id, **quotas_values)
883         return True
884     except Exception, e:
885         print ("Error [update_cinder_quota(cinder_client, '%s', '%s', '%s'"
886                "'%s')]:" % (tenant_id, vols_quota,
887                             snapshots_quota, gigabytes_quota)), e
888         return False
889
890
891 def delete_volume(cinder_client, volume_id, forced=False):
892     try:
893         if forced:
894             try:
895                 cinder_client.volumes.detach(volume_id)
896             except:
897                 print "Error:", sys.exc_info()[0]
898             cinder_client.volumes.force_delete(volume_id)
899         else:
900             cinder_client.volumes.delete(volume_id)
901         return True
902     except Exception, e:
903         print ("Error [delete_volume(cinder_client, '%s', '%s')]:" %
904                (volume_id, str(forced))), e
905         return False
906
907
908 def delete_volume_type(cinder_client, volume_type):
909     try:
910         cinder_client.volume_types.delete(volume_type)
911         return True
912     except Exception, e:
913         print ("Error [delete_volume_type(cinder_client, '%s')]:" %
914                volume_type), e
915         return False
916
917
918 # *********************************************
919 #   KEYSTONE
920 # *********************************************
921 def get_tenants(keystone_client):
922     try:
923         tenants = keystone_client.tenants.list()
924         return tenants
925     except Exception, e:
926         print "Error [get_tenants(keystone_client)]:", e
927         return None
928
929
930 def get_users(keystone_client):
931     try:
932         users = keystone_client.users.list()
933         return users
934     except Exception, e:
935         print "Error [get_users(keystone_client)]:", e
936         return None
937
938
939 def get_tenant_id(keystone_client, tenant_name):
940     tenants = keystone_client.tenants.list()
941     id = ''
942     for t in tenants:
943         if t.name == tenant_name:
944             id = t.id
945             break
946     return id
947
948
949 def get_user_id(keystone_client, user_name):
950     users = keystone_client.users.list()
951     id = ''
952     for u in users:
953         if u.name == user_name:
954             id = u.id
955             break
956     return id
957
958
959 def get_role_id(keystone_client, role_name):
960     roles = keystone_client.roles.list()
961     id = ''
962     for r in roles:
963         if r.name == role_name:
964             id = r.id
965             break
966     return id
967
968
969 def create_tenant(keystone_client, tenant_name, tenant_description):
970     try:
971         tenant = keystone_client.tenants.create(tenant_name,
972                                                 tenant_description,
973                                                 enabled=True)
974         return tenant.id
975     except Exception, e:
976         print ("Error [create_tenant(cinder_client, '%s', '%s')]:" %
977                (tenant_name, tenant_description)), e
978         return False
979
980
981 def create_user(keystone_client, user_name, user_password,
982                 user_email, tenant_id):
983     try:
984         user = keystone_client.users.create(user_name, user_password,
985                                             user_email, tenant_id,
986                                             enabled=True)
987         return user.id
988     except Exception, e:
989         print ("Error [create_user(keystone_client, '%s', '%s', '%s'"
990                "'%s')]:" % (user_name, user_password, user_email, tenant_id),
991                e)
992         return False
993
994
995 def add_role_user(keystone_client, user_id, role_id, tenant_id):
996     try:
997         keystone_client.roles.add_user_role(user_id, role_id, tenant_id)
998         return True
999     except Exception, e:
1000         print ("Error [add_role_user(keystone_client, '%s', '%s'"
1001                "'%s')]:" % (user_id, role_id, tenant_id)), e
1002         return False
1003
1004
1005 def delete_tenant(keystone_client, tenant_id):
1006     try:
1007         keystone_client.tenants.delete(tenant_id)
1008         return True
1009     except Exception, e:
1010         print "Error [delete_tenant(keystone_client, '%s')]:" % tenant_id, e
1011         return False
1012
1013
1014 def delete_user(keystone_client, user_id):
1015     try:
1016         keystone_client.users.delete(user_id)
1017         return True
1018     except Exception, e:
1019         print "Error [delete_user(keystone_client, '%s')]:" % user_id, e
1020         return False