#!/usr/bin/env python from pyeole import ihm from pyeole import process from creole.client import CreoleClient from tempfile import mkstemp import sys import os import csv import logging LOG_FILE = '/var/log/one/eole-one-node.log' #= Configure Logger === logger = logging.getLogger(__name__) #std_handler = logging.StreamHandler(sys.stdout) file_handler = logging.FileHandler(LOG_FILE) logger.setLevel(logging.INFO) #std_handler.setLevel(logging.INFO) file_handler.setLevel(logging.DEBUG) formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') #std_handler.setFormatter(formatter) file_handler.setFormatter(formatter) #logger.addHandler(std_handler) logger.addHandler(file_handler) #= End Logger === class RunCmdError(Exception): pass class OneClient(): def __init__(self, user): self.user = None self.auth = None self.root = '/var/lib/one' if user: self.user = user else: self.user = 'oneadmin' user_info = process.system_out(['getent', 'passwd', user])[1] if user_info: self.root = user_info.split(':')[5] command = ['cat', u'{0}/.one/one_auth'.format(self.root)] res = process.system_out(command) if res[0] == 0: self.auth = res[1].split(':') def __run_cmd__(self, cmd): cmd.extend(['--user', self.auth[0]]) cmd.extend(['--password', self.auth[1]]) res = process.system_out(cmd) if res[0] == 0: if 'list' in cmd: out_lines = [] if res: for line in res[1].split('\n'): if len(line) == 0: next elif 'ID' in line: next else: out_lines.append(line.split()) return out_lines else: return res else: return False def get_hosts(self): """ get the list of hosts """ cmd = ['onehost', 'list'] cmd.extend(['-l', 'ID,NAME']) res = self.__run_cmd__(cmd) return(res) def get_clusters(self): """ get the cluster list """ cmd = ['onecluster', 'list'] cmd.extend(['-l', 'ID,NAME']) return self.__run_cmd__(cmd) def get_networks(self): """ get the virtual network list """ cmd = ['onevnet', 'list'] cmd.extend(['-l', 'ID,NAME']) return self.__run_cmd__(cmd) def get_cluster_id_by_name(self, name): cmd = ['onecluster', 'list'] cmd.extend(['-f', 'NAME={0}'.format(name)]) res = self.__run_cmd__(cmd) ID = res[0][0] return ID def get_vnet_id_by_name(self, name): cmd = ['onevnet', 'list'] cmd.extend(['-f', 'NAME={0}'.format(name)]) res = self.__run_cmd__(cmd) ID = res[0][0] return ID def create_network(self, templatefile, cluster, vnet_name): """ Create a network """ cmd = ['onevnet', 'create'] cmd.extend(['--user', self.auth[0]]) cmd.extend(['--password', self.auth[1][:-1]]) #cmd.extend(['-c', cluster]) cmd.append(templatefile) res = process.system_out(cmd) if res[0] == 0: clt_id = self.get_cluster_id_by_name(cluster) vnet_id = self.get_vnet_id_by_name(vnet_name) res = self.__run_cmd__(['onecluster', 'addvnet', clt_id, vnet_id]) os.remove(templatefile) if not res: print("Error attaching {0} vnet to {1} cluster".format(vnet_name, cluster)) return False else: return True else: logger.error("Creation of virtual network with template {0} failed".format(templatefile)) return False def update_network(self, templatefile, cluster, vnet_name): """ Update a network """ vnet_id = self.get_vnet_id_by_name(vnet_name) cmd = ['onevnet', 'update'] cmd.extend(['--user', self.auth[0]]) cmd.extend(['--password', self.auth[1][:-1]]) cmd.extend([vnet_id, templatefile]) res = process.system_out(cmd) if res[0] == 0: os.remove(templatefile) return True else: logger.error("Update of virtual network with template {0} failed".format(templatefile)) return False def delete_network(self, vnet_id): cmd = ['onevnet', 'delete'] cmd.extend(['--user', self.auth[0]]) cmd.extend(['--password', self.auth[1][:-1]]) cmd.append(vnet_id) res = process.system_out(cmd) if res[0] == 0: ihm.print_line("Network {0} deleted".format(vnet_id)) return True else: logger.error("Error deleting network {0}".format(vnet_id)) ihm.print_line("Error deleting network {0}".format(vnet_id)) return False class OneNetwork(): def create(self, one_client): tmpl_file = self.create_template() if one_client.create_network(tmpl_file, self.cluster, self.zone): ihm.print_line("Virtual network {0} created".format(self.zone)) return True else: ihm.print_line("Error Creating virtual network {0}".format(self.zone)) return False def update(self, one_client): tmpl_file = self.create_template(True) if one_client.update_network(tmpl_file, self.cluster, self.zone): ihm.print_line("Virtual network {0} updated".format(self.zone)) return True else: ihm.print_line("Error Updating virtual network {0}".format(self.zone)) return False def manage(self, one_client): found = False vnet = one_client.get_networks() network_name = self.zone for net in vnet: if network_name in net: found = True break if not found: return self.create(one_client) else: return self.update(one_client) class OneNetworkL3(OneNetwork): def __init__(self, net_info, cluster): self.swname = net_info[0] self.zone = u'{0}{1}'.format(net_info[10], net_info[1]) self.vlan = net_info[2] self.vnet_addr = net_info[3] self.vnet_mask = net_info[4] self.vnet_gw = net_info[5] self.vnet_rg_start = net_info[6] self.vnet_rg_size = net_info[7] self.vnet_dns = net_info[8] self.vnet_trunk = net_info[9] self.cluster = cluster def create_template(self, update=False): fd, tmp_path = mkstemp(prefix='oneVnet-') template = open(tmp_path, 'w') template.write('NAME = "{0}"\n'.format(self.zone)) if (update is False): if self.vnet_rg_start and self.vnet_rg_size: template.write('AR=[\n') template.write('TYPE = "IP4",\n') template.write('IP = "{0}",\n'.format(self.vnet_rg_start)) template.write('SIZE = "{0}"\n'.format(self.vnet_rg_size)) template.write(']\n') else: template.write('TYPE = FIXED\n') if self.vlan: template.write('VLAN = yes\n') template.write('VLAN_ID = {0}\n'.format(self.vlan)) if self.vnet_trunk: template.write('VLAN_TAGGED_ID = {0}\n'.format(self.vnet_trunk)) template.write('BRIDGE = {0}\n'.format(self.swname)) template.write('NETWORK_ADDRESS = {0}\n'.format(self.vnet_addr)) template.write('NETWORK_MASK = {0}\n'.format(self.vnet_mask)) template.write('GATEWAY = {0}\n'.format(self.vnet_gw)) template.write('DNS = {0}\n'.format(self.vnet_dns)) template.close() return tmp_path class OneNetworkL2(OneNetwork): def __init__(self, net_info, cluster): self.swname = net_info[0] self.zone = u'{0}{1}'.format(net_info[6], net_info[1]) self.net_size = net_info[2] self.first_mac = net_info[3] self.tag = net_info[4] self.trunk = net_info[5] self.cluster = cluster def create_template(self,update=False): fd, tmp_path = mkstemp(prefix='oneVnet-') template = open(tmp_path, 'w') template.write('NAME = "{0}"\n'.format(self.zone)) if self.tag: template.write('VLAN = yes\n') template.write('VLAN_ID = "{0}"\n'.format(self.tag)) if self.trunk: template.write('VLAN_TAGGED_ID = "{0}""\n'.format(self.trunk)) template.write('BRIDGE = {0}\n'.format(self.swname)) if self.net_size: template.write("AR=[\n") template.write(' TYPE = "ETHER",\n') if self.first_mac: template.write(' MAC = "{0}",\n'.format(self.first_mac)) template.write(' SIZE = "{0}"\n'.format(self.net_size)) template.write("]\n") template.close() return tmp_path def main(): client = CreoleClient() one_client = OneClient('oneadmin') networks = [] cluster = client.get_creole('one_cluster_name') swname = client.get_creole('ovs_sw_name') zones = client.get_creole('vnets') vlans = client.get_creole('vnet_vlan_tag') vnet_addr = client.get_creole('vnet_network_addr') vnet_mask = client.get_creole('vnet_network_mask') vnet_dns = client.get_creole('vnet_network_dns') vnet_gw = client.get_creole('vnet_network_gw') vnet_rg_start = client.get_creole('vnet_range_start') vnet_rg_size = client.get_creole('vnet_range_size') vnet_trunk = client.get_creole('vnet_vlan_trunk') l2_vnet = client.get_creole('l2_vnets') l2_vnet_size = client.get_creole('l2_vnet_size') l2_vnet_vlan_tag = client.get_creole('l2_vnet_vlan_tag') l2_vnet_vlan_trunk = client.get_creole('l2_vnet_vlan_trunk') l2_vnet_first_mac = client.get_creole('l2_vnet_first_mac') net_prefix = "CR_" processed = [] for cpt in range(len(zones)): if zones[cpt] not in processed: info = [] info.append(swname) info.append(zones[cpt]) info.append(vlans[cpt]) info.append(vnet_addr[cpt]) info.append(vnet_mask[cpt]) info.append(vnet_gw[cpt]) info.append(vnet_rg_start[cpt]) info.append(vnet_rg_size[cpt]) info.append(vnet_dns[cpt]) info.append(vnet_trunk[cpt]) info.append(net_prefix) networks.append(OneNetworkL3(info, cluster)) processed.append(zones[cpt]) for i in range(len(l2_vnet)): if l2_vnet[i] not in processed: net_info = [] net_info.append(swname) net_info.append(l2_vnet[i]) net_info.append(l2_vnet_size[i]) net_info.append(l2_vnet_first_mac[i]) net_info.append(l2_vnet_vlan_tag[i]) net_info.append(l2_vnet_vlan_trunk[i]) net_info.append(net_prefix) networks.append(OneNetworkL2(net_info, cluster)) processed.append(l2_vnet[i]) if client.get_creole('activer_openvswitch'): for network in networks: if not network.manage(one_client): exit(1) else: ihm.print_line(u'Open vSwitch disabled no need to configure virtual networks') networks = one_client.get_networks() for net in networks: name = net[1] if name.startswith(net_prefix): if not name[3:] in zones and not name[3:] in l2_vnet: one_client.delete_network(net[0]) exit(0) main()