Add the RestAPI suppor to upload config

1. Add the RestAPI suppor to upload config;
2. Support multiple routers per tenant;
3. Enhance the cleanup logic;

Change-Id: Id209765a138686db7a767b4ab65c833ab6f78522
This commit is contained in:
Yichen Wang 2015-07-13 16:46:39 -07:00
parent af1e5ca210
commit d2891a0209
6 changed files with 139 additions and 69 deletions

View File

@ -234,7 +234,7 @@ class Router(object):
network_instance = BaseNetwork(self)
self.network_list.append(network_instance)
# Create the network and subnet
network_name = self.user.user_name + "-N" + str(network_count)
network_name = self.router['router']['name'] + "-N" + str(network_count)
network_instance.create_network_and_subnet(network_name)
# Attach the created network to router interface
self.attach_router_interface(network_instance)

View File

@ -45,7 +45,6 @@ server:
users_per_tenant: 1
# Number of routers to be created within the context of each User
# For now support only 1 router per user
routers_per_user: 1
# Number of networks to be created within the context of each Router

View File

@ -46,46 +46,53 @@ class Credentials(object):
dct['version'] = 2
return dct
#
def _init_with_openrc_(self, openrc_contents):
export_re = re.compile('export OS_([A-Z_]*)="?(.*)')
for line in openrc_contents:
line = line.strip()
mstr = export_re.match(line)
if mstr:
# get rif of posible trailing double quote
# the first one was removed by the re
name = mstr.group(1)
value = mstr.group(2)
if value.endswith('"'):
value = value[:-1]
# get rid of password assignment
# echo "Please enter your OpenStack Password: "
# read -sr OS_PASSWORD_INPUT
# export OS_PASSWORD=$OS_PASSWORD_INPUT
if value.startswith('$'):
continue
# now match against wanted variable names
if name == 'USERNAME':
self.rc_username = value
elif name == 'AUTH_URL':
self.rc_auth_url = value
elif name == 'TENANT_NAME':
self.rc_tenant_name = value
# Read a openrc file and take care of the password
# The 2 args are passed from the command line and can be None
#
def __init__(self, openrc_file, pwd, no_env):
def __init__(self, openrc_file=None, openrc_contents=None, pwd=None, no_env=False):
self.rc_password = None
self.rc_username = None
self.rc_tenant_name = None
self.rc_auth_url = None
self.openrc_contents = openrc_contents
success = True
if openrc_file:
if os.path.exists(openrc_file):
export_re = re.compile('export OS_([A-Z_]*)="?(.*)')
for line in open(openrc_file):
line = line.strip()
mstr = export_re.match(line)
if mstr:
# get rif of posible trailing double quote
# the first one was removed by the re
name = mstr.group(1)
value = mstr.group(2)
if value.endswith('"'):
value = value[:-1]
# get rid of password assignment
# echo "Please enter your OpenStack Password: "
# read -sr OS_PASSWORD_INPUT
# export OS_PASSWORD=$OS_PASSWORD_INPUT
if value.startswith('$'):
continue
# now match against wanted variable names
if name == 'USERNAME':
self.rc_username = value
elif name == 'AUTH_URL':
self.rc_auth_url = value
elif name == 'TENANT_NAME':
self.rc_tenant_name = value
self.openrc_contents = open(openrc_file).read()
self._init_with_openrc_(self.openrc_contents)
else:
LOG.error("rc file does not exist %s" % openrc_file)
success = False
return
if self.openrc_contents:
self._init_with_openrc_(self.openrc_contents)
elif not no_env:
# no openrc file passed - we assume the variables have been
# sourced by the calling shell

View File

@ -75,39 +75,7 @@ class KBConfig(object):
self.client_cfg = None
self.topo_cfg = None
def init_with_cli(self):
self.get_credentials()
self.get_configs()
self.get_topo_cfg()
def init_with_rest_api(self, **kwargs):
self.cred_tested = kwargs['cred_tested']
self.cred_testing = kwargs['cred_testing']
self.server_cfg = kwargs['server_cfg']
self.client_cfg = kwargs['client_cfg']
self.topo_cfg = kwargs['topo_cfg']
def get_total_vm_count(self, config):
return (config['number_tenants'] * config['users_per_tenant'] *
config['routers_per_user'] * config['networks_per_router'] *
config['vms_per_network'])
def get_credentials(self):
# Retrieve the credentials
self.cred_tested = credentials.Credentials(CONF.tested_rc, CONF.passwd_tested, CONF.no_env)
if CONF.testing_rc and CONF.testing_rc != CONF.tested_rc:
self.cred_testing = credentials.Credentials(CONF.testing_rc,
CONF.passwd_testing,
CONF.no_env)
else:
# Use the same openrc file for both cases
self.cred_testing = self.cred_tested
def get_configs(self):
if CONF.config:
alt_config = configure.Configuration.from_file(CONF.config).configure()
self.config_scale = self.config_scale.merge(alt_config)
def update_configs(self):
# Initialize the key pair name
if self.config_scale['public_key_file']:
# verify the public key file exists
@ -137,6 +105,41 @@ class KBConfig(object):
self.client_cfg['vms_per_network'] =\
self.get_total_vm_count(self.server_cfg) + 1
def init_with_cli(self):
self.get_credentials()
self.get_configs()
self.get_topo_cfg()
self.update_configs()
def init_with_rest_api(self, **kwargs):
self.cred_tested = kwargs['cred_tested']
self.cred_testing = kwargs['cred_testing']
self.topo_cfg = kwargs['topo_cfg']
self.update_configs()
def get_total_vm_count(self, config):
return (config['number_tenants'] * config['users_per_tenant'] *
config['routers_per_user'] * config['networks_per_router'] *
config['vms_per_network'])
def get_credentials(self):
# Retrieve the credentials
self.cred_tested = credentials.Credentials(openrc_file=CONF.tested_rc,
pwd=CONF.passwd_tested,
no_env=CONF.no_env)
if CONF.testing_rc and CONF.testing_rc != CONF.tested_rc:
self.cred_testing = credentials.Credentials(openrc_file=CONF.testing_rc,
pwd=CONF.passwd_testing,
no_env=CONF.no_env)
else:
# Use the same openrc file for both cases
self.cred_testing = self.cred_tested
def get_configs(self):
if CONF.config:
alt_config = configure.Configuration.from_file(CONF.config).configure()
self.config_scale = self.config_scale.merge(alt_config)
def get_topo_cfg(self):
if CONF.topology:
self.topo_cfg = configure.Configuration.from_file(CONF.topology).configure()

View File

@ -17,23 +17,78 @@ import sys
kb_main_path = os.path.split(os.path.abspath(__file__))[0] + "/../../.."
sys.path.append(kb_main_path)
from credentials import Credentials
from configure import Configuration
from kb_config import KBConfig
from pecan import expose
from pecan import response
class ConfigController(object):
def __init__(self):
self.kb_config = KBConfig()
self.cur_config = None
self.status = 'READY'
self.def_config = self.kb_config.config_scale
@expose(generic=True)
def default_config(self):
def_config = self.kb_config.config_scale
return str(def_config)
return str(self.def_config)
@expose(generic=True)
def current_config(self):
return str(self.cur_config)
def running_config(self):
return str(self.kb_config.config_scale)
@running_config.when(method='POST')
def running_config_POST(self, args):
try:
user_config = eval(args)
except Exception:
response.status = 403
response.text = "Error while parsing configurations!"
return response.text
# Expectation:
# {
# 'credentials': {'tested_rc': '<STRING>', 'passwd_tested': '<STRING>',
# 'testing_rc': '<STRING>', 'passwd_testing': '<STRING>'},
# 'kb_cfg': {<USER_OVERRIDED_CONFIGS>},
# 'topo_cfg': {<TOPOLOGY_CONFIGS>}
# }
# Parsing credentials from application input
cred_config = user_config['credentials']
cred_tested = Credentials(openrc_contents=cred_config['tested_rc'],
pwd=cred_config['passwd_tested'])
if ('testing_rc' in cred_config and cred_config['testing_rc'] != cred_config['tested_rc']):
cred_testing = Credentials(openrc_contents=cred_config['testing_rc'],
pwd=cred_config['passwd_testing'])
else:
# Use the same openrc file for both cases
cred_testing = cred_tested
# Parsing server and client configs from application input
# Save the public key into a temporary file
if 'public_key' in user_config['kb_cfg']:
pubkey_filename = '/tmp/kb_public_key.pub'
f = open(pubkey_filename, 'w')
f.write(user_config['kb_cfg']['public_key_file'])
f.close()
self.kb_config.config_scale['public_key_file'] = pubkey_filename
alt_config = Configuration.from_string(user_config['kb_cfg']).configure()
self.kb_config.config_scale = self.kb_config.config_scale.merge(alt_config)
# Parsing topology configs from application input
if 'topo_cfg' in user_config:
topo_cfg = Configuration.from_string(user_config['topo_cfg']).configure()
else:
topo_cfg = None
self.kb_config.init_with_rest_api(cred_tested=cred_tested,
cred_testing=cred_testing,
topo_cfg=topo_cfg)
return str(self.kb_config.config_scale)
@expose(generic=True)
def status(self):

View File

@ -120,7 +120,12 @@ class Kloud(object):
def delete_resources(self):
# Deleting flavors created by KloudBuster
nova_client = self.tenant_list[0].user_list[0].nova_client
try:
nova_client = self.tenant_list[0].user_list[0].nova_client
except Exception:
# NOVA Client is not yet initialized, so skip cleaning up...
return
flavor_manager = base_compute.Flavor(nova_client)
if self.testing_side:
flavor_manager.delete_flavor('kb.client')
@ -370,7 +375,8 @@ class KloudBuster(object):
total_vm = self.get_tenant_vm_count(self.server_cfg)
server_quota = {}
server_quota['network'] = self.server_cfg['networks_per_router']
server_quota['network'] = self.server_cfg['routers_per_user'] *\
self.server_cfg['networks_per_router']
server_quota['subnet'] = server_quota['network']
server_quota['router'] = self.server_cfg['routers_per_user']
if (self.server_cfg['use_floatingip']):