X-Git-Url: https://osm.etsi.org/gitweb/?a=blobdiff_plain;ds=sidebyside;f=rwlaunchpad%2Fplugins%2Frwnsm%2Frift%2Ftasklets%2Frwnsmtasklet%2Frwnsmtasklet.py;h=718d2b191b1f952aecc5edb6ef81b3a1646b880d;hb=2d3f1023ac94d9c19115c0b63ce85ae7a8598517;hp=bb217672f3e706e0233be1dffe77a5e0ae7940c0;hpb=6b732c720ec31351624871f83ab156e50d93c940;p=osm%2FSO.git diff --git a/rwlaunchpad/plugins/rwnsm/rift/tasklets/rwnsmtasklet/rwnsmtasklet.py b/rwlaunchpad/plugins/rwnsm/rift/tasklets/rwnsmtasklet/rwnsmtasklet.py index bb217672..718d2b19 100755 --- a/rwlaunchpad/plugins/rwnsm/rift/tasklets/rwnsmtasklet/rwnsmtasklet.py +++ b/rwlaunchpad/plugins/rwnsm/rift/tasklets/rwnsmtasklet/rwnsmtasklet.py @@ -1,4 +1,4 @@ -# +# # Copyright 2016 RIFT.IO Inc # # Licensed under the Apache License, Version 2.0 (the "License"); @@ -25,6 +25,8 @@ import tempfile import time import uuid import yaml +import requests +import json from collections import deque @@ -458,6 +460,7 @@ class VnffgRecord(object): class VirtualLinkRecord(object): """ Virtual Link Records class""" + XPATH = "D,/vlr:vlr-catalog/vlr:vlr" @staticmethod @asyncio.coroutine def create_record(dts, log, loop, nsr_name, vld_msg, cloud_account_name, om_datacenter, ip_profile, nsr_id, restart_mode=False): @@ -513,7 +516,8 @@ class VirtualLinkRecord(object): self._vlr_id = str(uuid.uuid4()) self._state = VlRecordState.INIT self._prev_state = None - + self._create_time = int(time.time()) + @property def xpath(self): """ path for this object """ @@ -606,6 +610,7 @@ class VirtualLinkRecord(object): "nsr_id_ref": self._nsr_id, "vld_ref": self.vld_msg.id, "name": self.name, + "create_time": self._create_time, "cloud_account": self.cloud_account_name, "om_datacenter": self.om_datacenter_name, } @@ -643,7 +648,6 @@ class VirtualLinkRecord(object): @asyncio.coroutine def instantiate(self): """ Instantiate this VL """ - self._log.debug("Instaniating VLR key %s, vld %s", self.xpath, self._vld_msg) vlr = None @@ -948,7 +952,6 @@ class VirtualNetworkFunctionRecord(object): vnfr_dict = { "id": self.id, "nsr_id_ref": self._nsr_id, - "vnfd_ref": self.vnfd.id, "name": self.name, "cloud_account": self._cloud_account_name, "om_datacenter": self._om_datacenter_name, @@ -957,6 +960,8 @@ class VirtualNetworkFunctionRecord(object): vnfr_dict.update(vnfd_copy_dict) vnfr = RwVnfrYang.YangData_Vnfr_VnfrCatalog_Vnfr.from_dict(vnfr_dict) + + vnfr.vnfd = VnfrYang.YangData_Vnfr_VnfrCatalog_Vnfr_Vnfd.from_dict(self.vnfd.as_dict()) vnfr.member_vnf_index_ref = self.member_vnf_index vnfr.vnf_configuration.from_dict(self._vnfd.vnf_configuration.as_dict()) @@ -1080,7 +1085,7 @@ class VirtualNetworkFunctionRecord(object): cpr.vlr_ref = vlr_ref.id self.vnfr_msg.connection_point.append(cpr) self._log.debug("Connection point [%s] added, vnf id=%s vnfd id=%s", - cpr, self.vnfr_msg.id, self.vnfr_msg.vnfd_ref) + cpr, self.vnfr_msg.id, self.vnfr_msg.vnfd.id) if not self.restart_mode: yield from self._dts.query_create(self.xpath, @@ -1229,7 +1234,8 @@ class NetworkServiceRecord(object): """ Network service record """ XPATH = "D,/nsr:ns-instance-opdata/nsr:nsr" - def __init__(self, dts, log, loop, nsm, nsm_plugin, nsr_cfg_msg, sdn_account_name, restart_mode=False): + def __init__(self, dts, log, loop, nsm, nsm_plugin, nsr_cfg_msg, sdn_account_name, key_pairs, restart_mode=False, + vlr_handler=None): self._dts = dts self._log = log self._loop = loop @@ -1237,10 +1243,12 @@ class NetworkServiceRecord(object): self._nsr_cfg_msg = nsr_cfg_msg self._nsm_plugin = nsm_plugin self._sdn_account_name = sdn_account_name + self._vlr_handler = vlr_handler self._nsd = None self._nsr_msg = None self._nsr_regh = None + self._key_pairs = key_pairs self._vlrs = [] self._vnfrs = {} self._vnfds = {} @@ -1449,6 +1457,18 @@ class NetworkServiceRecord(object): for vlr in self._vlrs: yield from self.nsm_plugin.instantiate_vl(self, vlr) vlr.state = VlRecordState.ACTIVE + self._loop.create_task(self.vlr_uptime_update(vlr)) + + + def vlr_uptime_update(self, vlr): + vlr_ = RwVlrYang.YangData_Vlr_VlrCatalog_Vlr.from_dict({'id': vlr.id}) + while True: + if vlr.state not in [VlRecordState.INIT, VlRecordState.INSTANTIATION_PENDING, VlRecordState.ACTIVE]: + return + vlr_.uptime = int(time.time()) - vlr._create_time + yield from self._vlr_handler.update(None, VirtualLinkRecord.vlr_xpath(vlr), vlr_) + yield from asyncio.sleep(2, loop=self._loop) + @asyncio.coroutine def create(self, config_xact): @@ -1804,19 +1824,20 @@ class NetworkServiceRecord(object): self._vnffgrs[vnffgr.id] = vnffgr def resolve_vld_ip_profile(self, nsd_msg, vld): + self._log.debug("Receieved ip profile ref is %s",vld.ip_profile_ref) if not vld.has_field('ip_profile_ref'): return None - profile = [ profile for profile in nsd_msg.ip_profiles if profile.name == vld.ip_profile_ref ] + profile = [profile for profile in nsd_msg.ip_profiles if profile.name == vld.ip_profile_ref] return profile[0] if profile else None @asyncio.coroutine def _create_vls(self, vld, cloud_account,om_datacenter): """Create a VLR in the cloud account specified using the given VLD - + Args: vld : VLD yang obj cloud_account : Cloud account name - + Returns: VirtualLinkRecord """ @@ -1884,6 +1905,7 @@ class NetworkServiceRecord(object): """ This function creates VLs for every VLD in the NSD associated with this NSR""" for vld in self.nsd_msg.vld: + self._log.debug("Found vld %s in nsr id %s", vld, self.id) cloud_account_list = self._extract_cloud_accounts_for_vl(vld) for cloud_account,om_datacenter in cloud_account_list: @@ -1910,8 +1932,8 @@ class NetworkServiceRecord(object): if vlr is None: cloud_account_list = self._extract_cloud_accounts_for_vl(vld) - for account in cloud_account_list: - vlr = yield from self._create_vls(vld, account) + for account,om_datacenter in cloud_account_list: + vlr = yield from self._create_vls(vld, account,om_datacenter) self._vlrs.append(vlr) vlr.state = VlRecordState.INSTANTIATION_PENDING @@ -2468,6 +2490,7 @@ class NetworkServiceRecord(object): nsr.config_status = self.map_config_status() nsr.config_status_details = self._config_status_details nsr.create_time = self._create_time + nsr.uptime = int(time.time()) - self._create_time for cfg_prim in self.nsd_msg.service_primitive: cfg_prim = NsrYang.YangData_Nsr_NsInstanceOpdata_Nsr_ServicePrimitive.from_dict( @@ -2900,8 +2923,10 @@ class NsrRpcDtsHandler(object): EXEC_NSR_CONF_O_XPATH = "O,/nsr:start-network-service" NETCONF_IP_ADDRESS = "127.0.0.1" NETCONF_PORT = 2022 + RESTCONF_PORT = 8888 NETCONF_USER = "admin" NETCONF_PW = "admin" + REST_BASE_V2_URL = 'https://{}:{}/v2/api/'.format("127.0.0.1",8888) def __init__(self, dts, log, loop, nsm): self._dts = dts @@ -2913,6 +2938,7 @@ class NsrRpcDtsHandler(object): self._ns_regh = None self._manager = None + self._nsr_config_url = NsrRpcDtsHandler.REST_BASE_V2_URL + 'config/ns-instance-config' self._model = RwYang.Model.create_libncx() self._model.load_schema_ypbc(RwNsrYang.get_schema()) @@ -2958,6 +2984,12 @@ class NsrRpcDtsHandler(object): raise NsrInstantiationFailed("Failed to connect to Launchpad within %s seconds" % timeout_secs) + def _apply_ns_instance_config(self,payload_dict): + #self._log.debug("At apply NS instance config with payload %s",payload_dict) + req_hdr= {'accept':'application/vnd.yang.data+json','content-type':'application/vnd.yang.data+json'} + response=requests.post(self._nsr_config_url, headers=req_hdr, auth=('admin', 'admin'),data=payload_dict,verify=False) + return response + @asyncio.coroutine def register(self): """ Register for NS monitoring read from dts """ @@ -2969,21 +3001,22 @@ class NsrRpcDtsHandler(object): rpc_op = NsrYang.YangOutput_Nsr_StartNetworkService.from_dict({ "nsr_id":str(uuid.uuid4()) }) - - if not ('name' in rpc_ip and 'nsd_ref' in rpc_ip and 'cloud_account' in rpc_ip): + + if not ('name' in rpc_ip and 'nsd_ref' in rpc_ip and ('cloud_account' in rpc_ip or 'om_datacenter' in rpc_ip)): self._log.error("Mandatory parameters name or nsd_ref or cloud account not found in start-network-service {}".format(rpc_ip)) - + self._log.debug("start-network-service RPC input: {}".format(rpc_ip)) try: # Add used value to the pool self._log.debug("RPC output: {}".format(rpc_op)) + nsd_copy = self.nsm.get_nsd(rpc_ip.nsd_ref) - if not self._manager: - self._manager = yield from self._connect() - + #if not self._manager: + # self._manager = yield from self._connect() + self._log.debug("Configuring ns-instance-config with name %s nsd-ref: %s", rpc_ip.name, rpc_ip.nsd_ref) @@ -2996,17 +3029,26 @@ class NsrRpcDtsHandler(object): ns_instance_config.nsd = NsrYang.YangData_Nsr_NsInstanceConfig_Nsr_Nsd() ns_instance_config.nsd.from_dict(nsd_copy.msg.as_dict()) - xml = ns_instance_config.to_xml_v2(self._model) - netconf_xml = self.wrap_netconf_config_xml(xml) - - self._log.debug("Sending configure ns-instance-config xml to %s: %s", - netconf_xml, NsrRpcDtsHandler.NETCONF_IP_ADDRESS) - - response = yield from self._manager.edit_config( - target="running", - config=netconf_xml, - ) - self._log.debug("Received edit config response: %s", str(response)) + payload_dict = ns_instance_config.to_json(self._model) + #xml = ns_instance_config.to_xml_v2(self._model) + #netconf_xml = self.wrap_netconf_config_xml(xml) + + #self._log.debug("Sending configure ns-instance-config xml to %s: %s", + # netconf_xml, NsrRpcDtsHandler.NETCONF_IP_ADDRESS) + self._log.debug("Sending configure ns-instance-config json to %s: %s", + self._nsr_config_url,ns_instance_config) + + #response = yield from self._manager.edit_config( + # target="running", + # config=netconf_xml, + # ) + response = yield from self._loop.run_in_executor( + None, + self._apply_ns_instance_config, + payload_dict + ) + response.raise_for_status() + self._log.debug("Received edit config response: %s", response.json()) xact_info.respond_xpath(rwdts.XactRspCode.ACK, NsrRpcDtsHandler.EXEC_NSR_CONF_O_XPATH, @@ -3032,6 +3074,7 @@ class NsrDtsHandler(object): """ The network service DTS handler """ NSR_XPATH = "C,/nsr:ns-instance-config/nsr:nsr" SCALE_INSTANCE_XPATH = "C,/nsr:ns-instance-config/nsr:nsr/nsr:scaling-group/nsr:instance" + KEY_PAIR_XPATH = "C,/nsr:key-pair" def __init__(self, dts, log, loop, nsm): self._dts = dts @@ -3041,6 +3084,7 @@ class NsrDtsHandler(object): self._nsr_regh = None self._scale_regh = None + self._key_pair_regh = None @property def nsm(self): @@ -3174,12 +3218,20 @@ class NsrDtsHandler(object): return added_cfgs, deleted_cfgs, updated_cfgs + def get_nsr_key_pairs(dts_member_reg, xact): + key_pairs = {} + for instance_cfg, keyspec in dts_member_reg.get_xact_elements(xact, include_keyspec=True): + self._log.debug("Key pair received is {} KS: {}".format(instance_cfg, keyspec)) + xpath = keyspec.to_xpath(RwNsrYang.get_schema()) + key_pairs[instance_cfg.name] = instance_cfg + return key_pairs + def on_apply(dts, acg, xact, action, scratch): """Apply the configuration""" self._log.debug("Got nsr apply (xact: %s) (action: %s)(scr: %s)", xact, action, scratch) - def handle_create_nsr(msg, restart_mode=False): + def handle_create_nsr(msg, key_pairs=None, restart_mode=False): # Handle create nsr requests """ # Do some validations if not msg.has_field("nsd"): @@ -3189,7 +3241,7 @@ class NsrDtsHandler(object): self._log.debug("Creating NetworkServiceRecord %s from nsr config %s", msg.id, msg.as_dict()) - nsr = self.nsm.create_nsr(msg, restart_mode=restart_mode) + nsr = self.nsm.create_nsr(msg, key_pairs=key_pairs, restart_mode=restart_mode) return nsr def handle_delete_nsr(msg): @@ -3220,8 +3272,11 @@ class NsrDtsHandler(object): xact, action, scratch) if action == rwdts.AppconfAction.INSTALL and xact.id is None: + key_pairs = [] + for element in self._key_pair_regh.elements: + key_pairs.append(element) for element in self._nsr_regh.elements: - nsr = handle_create_nsr(element, restart_mode=True) + nsr = handle_create_nsr(element, key_pairs, restart_mode=True) self._loop.create_task(begin_instantiation(nsr)) @@ -3235,7 +3290,8 @@ class NsrDtsHandler(object): for msg in added_msgs: if msg.id not in self._nsm.nsrs: self._log.info("Create NSR received in on_apply to instantiate NS:%s", msg.id) - nsr = handle_create_nsr(msg) + key_pairs = get_nsr_key_pairs(self._key_pair_regh, xact) + nsr = handle_create_nsr(msg,key_pairs) self._loop.create_task(begin_instantiation(nsr)) for msg in deleted_msgs: @@ -3352,6 +3408,11 @@ class NsrDtsHandler(object): flags=rwdts.Flag.SUBSCRIBER | rwdts.Flag.DELTA_READY| rwdts.Flag.CACHE, ) + self._key_pair_regh = acg.register( + xpath=NsrDtsHandler.KEY_PAIR_XPATH, + flags=rwdts.Flag.SUBSCRIBER | rwdts.Flag.DELTA_READY | rwdts.Flag.CACHE, + ) + class NsrOpDataDtsHandler(object): """ The network service op data DTS handler """ @@ -3748,7 +3809,7 @@ class NsManager(object): # msg.nsr_id_ref, # msg.scaling_group_name_ref, # msg.instance_id) - + def nsr_update_cfg(self, nsr_id, msg): nsr = self._nsrs[nsr_id] nsr.nsr_cfg_msg= msg @@ -3771,7 +3832,7 @@ class NsManager(object): # Not calling in a separate task as this is called from a separate task yield from nsr.delete_vl_instance(vld) - def create_nsr(self, nsr_msg, restart_mode=False): + def create_nsr(self, nsr_msg, key_pairs=None,restart_mode=False): """ Create an NSR instance """ if nsr_msg.id in self._nsrs: msg = "NSR id %s already exists" % nsr_msg.id @@ -3792,10 +3853,12 @@ class NsManager(object): nsm_plugin, nsr_msg, sdn_account_name, - restart_mode=restart_mode + key_pairs, + restart_mode=restart_mode, + vlr_handler=self._ro_plugin_selector._records_publisher._vlr_pub_hdlr ) self._nsrs[nsr_msg.id] = nsr - nsm_plugin.create_nsr(nsr_msg, nsr_msg.nsd) + nsm_plugin.create_nsr(nsr_msg, nsr_msg.nsd, key_pairs) return nsr @@ -3923,7 +3986,7 @@ class NsManager(object): self.create_nsd(nsd) else: self._log.debug("Updating NSD id = %s, nsd = %s", nsd.id, nsd) - self._nsds[nsd.id].update(nsd) + self._nsds[nsd.id].update(nsd) def delete_nsd(self, nsd_id): """ Delete the Network service descriptor with the passed id """ @@ -3975,9 +4038,6 @@ class NsManager(object): """ Update the virtual network function descriptor """ self._log.debug("Update virtual network function descriptor- %s", vnfd) - # Hack to remove duplicates from leaf-lists - to be fixed by RIFT-6511 - for ivld in vnfd.internal_vld: - ivld.internal_connection_point_ref = list(set(ivld.internal_connection_point_ref)) if vnfd.id not in self._vnfds: self._log.debug("No VNFD found - creating VNFD id = %s", vnfd.id)