From 682eb032af3a8c3f6a254183b88e3baf75c1e5f2 Mon Sep 17 00:00:00 2001 From: fsaintma Date: Fri, 22 May 2015 10:57:20 +0200 Subject: [PATCH] add information in Iot-LAB rspec node --- sfa/iotlab/iotlabaggregate.py | 85 ++++++++++++++++++++++------------- sfa/iotlab/iotlabshell.py | 25 +++++------ 2 files changed, 63 insertions(+), 47 deletions(-) diff --git a/sfa/iotlab/iotlabaggregate.py b/sfa/iotlab/iotlabaggregate.py index 9dbeccb3..2b496152 100644 --- a/sfa/iotlab/iotlabaggregate.py +++ b/sfa/iotlab/iotlabaggregate.py @@ -9,6 +9,9 @@ from sfa.rspecs.elements.hardware_type import HardwareType from sfa.rspecs.elements.lease import Lease from sfa.rspecs.elements.granularity import Granularity from sfa.rspecs.version_manager import VersionManager +from sfa.rspecs.elements.services import ServicesElement +from sfa.rspecs.elements.login import Login +from sfa.rspecs.elements.sliver import Sliver from sfa.rspecs.elements.versions.iotlabv1Node import IotlabPosition from sfa.rspecs.elements.versions.iotlabv1Node import IotlabNode from sfa.rspecs.elements.versions.iotlabv1Node import IotlabLocation @@ -16,6 +19,7 @@ from sfa.iotlab.iotlablease import LeaseTable import time import datetime + class IotLABAggregate(object): """ SFA aggregate for Iot-LAB testbed @@ -24,7 +28,6 @@ class IotLABAggregate(object): def __init__(self, driver): self.driver = driver - def leases_to_rspec_leases(self, leases): """ Get leases attributes list""" rspec_leases = [] @@ -33,17 +36,17 @@ class IotLABAggregate(object): rspec_lease = Lease() rspec_lease['lease_id'] = lease['id'] iotlab_xrn = Xrn('.'.join([self.driver.root_auth, - Xrn.escape(node)]), - type='node') + Xrn.escape(node)]), + type='node') rspec_lease['component_id'] = iotlab_xrn.urn rspec_lease['start_time'] = str(lease['date']) - duration = int(lease['duration'])/60 # duration in minutes + # duration in minutes + duration = int(lease['duration'])/60 rspec_lease['duration'] = duration rspec_lease['slice_id'] = lease['slice_id'] rspec_leases.append(rspec_lease) return rspec_leases - def node_to_rspec_node(self, node): """ Get node attributes """ rspec_node = IotlabNode() @@ -51,20 +54,25 @@ class IotLABAggregate(object): rspec_node['archi'] = node['archi'] rspec_node['radio'] = (node['archi'].split(':'))[1] iotlab_xrn = Xrn('.'.join([self.driver.root_auth, - Xrn.escape(node['network_address'])]), - type='node') - rspec_node['boot_state'] = 'true' + Xrn.escape(node['network_address'])]), + type='node') + # rspec_node['boot_state'] = 'true' + if node['state'] == 'Absent' or \ + node['state'] == 'Suspected' or \ + node['state'] == 'Busy': + rspec_node['available'] = 'false' + else: + rspec_node['available'] = 'true' rspec_node['component_id'] = iotlab_xrn.urn rspec_node['component_name'] = node['network_address'] - rspec_node['component_manager_id'] = \ - hrn_to_urn(self.driver.root_auth, - 'authority+sa') + rspec_node['component_manager_id'] = hrn_to_urn(self.driver.root_auth, + 'authority+sa') rspec_node['authority_id'] = rspec_node['component_manager_id'] rspec_node['exclusive'] = 'true' - rspec_node['hardware_types'] = [HardwareType({'name': \ - 'iotlab-node'})] - location = IotlabLocation({'country':'France', 'site': \ - node['site']}) + rspec_node['hardware_types'] = \ + [HardwareType({'name': node['archi']})] + location = IotlabLocation({'country': 'France', + 'site': node['site']}) rspec_node['location'] = location position = IotlabPosition() for field in position: @@ -74,27 +82,38 @@ class IotLABAggregate(object): rspec_node['tags'] = [] return rspec_node - def sliver_to_rspec_node(self, sliver): """ Get node and sliver attributes """ rspec_node = self.node_to_rspec_node(sliver) rspec_node['expires'] = datetime_to_string(utcparse(sliver['expires'])) rspec_node['sliver_id'] = sliver['sliver_id'] + rspec_sliver = Sliver({'sliver_id': sliver['sliver_id'], + 'name': sliver['name'], + 'type': sliver['archi'], + 'tags': []}) + rspec_node['slivers'] = [rspec_sliver] + # slivers always provide the ssh service + login = Login({'authentication': 'ssh-keys', + 'hostname': sliver['hostname'], + 'port': '22', + 'username': sliver['name'], + 'login': sliver['name'] + }) + service = ServicesElement({'login': login}) + rspec_node['services'] = [service] return rspec_node - @classmethod def rspec_node_to_geni_sliver(cls, rspec_node): """ Get sliver status """ geni_sliver = {'geni_sliver_urn': rspec_node['sliver_id'], 'geni_expires': rspec_node['expires'], - 'geni_allocation_status' : 'geni_allocated', + 'geni_allocation_status': 'geni_allocated', 'geni_operational_status': 'geni_pending_allocation', 'geni_error': '', } return geni_sliver - def list_resources(self, version=None, options=None): """ list_resources method sends a RSpec with all Iot-LAB testbed nodes @@ -139,7 +158,7 @@ class IotLABAggregate(object): nodes = self.driver.shell.get_nodes() reserved_nodes = self.driver.shell.get_reserved_nodes() - if not 'error' in nodes and not 'error' in reserved_nodes: + if 'error' not in nodes and 'error' not in reserved_nodes: # convert nodes to rspec nodes rspec_nodes = [] for node in nodes: @@ -162,7 +181,7 @@ class IotLABAggregate(object): # iotlab slice = job submission from Iot-LAB else: reserved_nodes[lease_id]['slice_id'] = \ - hrn_to_urn(self.driver.root_auth+'.'+ + hrn_to_urn(self.driver.root_auth + '.' + reserved_nodes[lease_id]['owner']+"_slice", 'slice') leases.append(reserved_nodes[lease_id]) @@ -173,7 +192,6 @@ class IotLABAggregate(object): rspec.version.add_leases(rspec_leases) return rspec.toxml() - def get_slivers(self, urns, leases, nodes): """ Get slivers attributes list """ logger.warning("iotlabaggregate get_slivers") @@ -181,18 +199,23 @@ class IotLABAggregate(object): slivers = [] for lease in leases: for node in lease['resources']: + network_address = node.split(".") sliver_node = nodes[node] sliver_hrn = '%s.%s-%s' % (self.driver.hrn, - lease['id'], node.split(".")[0]) + lease['id'], + network_address[0]) start_time = datetime.datetime.fromtimestamp(lease['date']) duration = datetime.timedelta(seconds=int(lease['duration'])) sliver_node['expires'] = start_time + duration sliver_node['sliver_id'] = Xrn(sliver_hrn, type='sliver').urn + # frontend SSH hostname + sliver_node['hostname'] = '.'.join(network_address[1:]) + # user login + sliver_node['name'] = lease['owner'] slivers.append(sliver_node) return slivers - def _delete_db_lease(self, job_id): """ Delete lease table row in SFA database """ logger.warning("iotlabdriver _delete_db_lease lease job_id : %s" @@ -201,15 +224,14 @@ class IotLABAggregate(object): LeaseTable.job_id == job_id).delete() self.driver.api.dbsession().commit() - def describe(self, urns, version=None, options=None): """ describe method returns slice slivers (allocated resources) and leases (OAR job submission). We search in lease table of SFA database all OAR - jobs id for this slice and match OAR jobs with state Waiting or Running. - If OAR job id doesn't exist the experiment is terminated and we delete - the database table entry. Otherwise we add slivers and leases in the - response + jobs id for this slice and match OAR jobs with state Waiting or + Running. If OAR job id doesn't exist the experiment is terminated and + we delete the database table entry. Otherwise we add slivers and leases + in the response :returns: geni_slivers : a list of allocated slivers with information about @@ -258,7 +280,7 @@ class IotLABAggregate(object): nodes = self.driver.shell.get_nodes() reserved_nodes = self.driver.shell.get_reserved_nodes() - if not 'error' in nodes and not 'error' in reserved_nodes: + if 'error' not in nodes and 'error' not in reserved_nodes: # find OAR jobs id for one slice in SFA database db_leases = [(lease.job_id, lease.slice_hrn) for lease in self.driver.api.dbsession() @@ -268,7 +290,7 @@ class IotLABAggregate(object): leases = [] for job_id, slice_hrn in db_leases: # OAR job terminated, we delete entry in database - if not job_id in reserved_nodes: + if job_id not in reserved_nodes: self._delete_db_lease(job_id) else: # onelab slice = job submission from OneLAB @@ -304,4 +326,3 @@ class IotLABAggregate(object): return {'geni_urn': urns[0], 'geni_rspec': rspec.toxml(), 'geni_slivers': geni_slivers} - diff --git a/sfa/iotlab/iotlabshell.py b/sfa/iotlab/iotlabshell.py index 558593a4..f1fb1db0 100644 --- a/sfa/iotlab/iotlabshell.py +++ b/sfa/iotlab/iotlabshell.py @@ -18,7 +18,6 @@ class IotLABShell(object): user, passwd = auth.get_user_credentials() self.api = rest.Api(user, passwd) - def get_nodes(self): """ Get all OAR nodes @@ -48,12 +47,11 @@ class IotLABShell(object): nodes = experiment.info_experiment(self.api) except HTTPError as err: logger.warning("iotlashell get_nodes error %s" % err.reason) - return {'error' : err.reason} + return {'error': err.reason} for node in nodes['items']: nodes_dict[node['network_address']] = node return nodes_dict - def get_users(self): """ Get all LDAP users @@ -84,12 +82,11 @@ class IotLABShell(object): users = self.api.method('admin/users') except HTTPError as err: logger.warning("iotlashell get_users error %s" % err.reason) - return {'error' : err.reason} + return {'error': err.reason} for user in users: users_dict[user['email']] = user return users_dict - def reserve_nodes(self, login, exp_name, nodes_list, start_time, duration): """ @@ -108,8 +105,7 @@ class IotLABShell(object): files=exp_file) except HTTPError as err: logger.warning("iotlashell reserve_nodes error %s" % err.reason) - return {'error' : err.reason} - + return {'error': err.reason} def get_reserved_nodes(self): """ @@ -138,7 +134,7 @@ class IotLABShell(object): except HTTPError as err: logger.warning("iotlashell get_reserved_nodes error %s" % err.reason) - return {'error' : err.reason} + return {'error': err.reason} for exp in experiments['items']: # BUG IN OAR REST API : job with reservation didn't return # resources attribute list @@ -148,17 +144,17 @@ class IotLABShell(object): reserved_nodes_dict[exp['id']] = exp return reserved_nodes_dict - def add_user(self, slice_user): """ Add LDAP user """ # pylint:disable=E1123 logger.warning("iotlashell add_user") - user = {"type" : "SA", # single account creation - "city" : "To be defined", - "country" : "To be defined", - "motivations" : "SFA federation"} + # single account creation + user = {"type": "SA", + "city": "To be defined", + "country": "To be defined", + "motivations": "SFA federation"} email = slice_user['email'] user['email'] = email user['sshPublicKey'] = slice_user['keys'][0] @@ -172,7 +168,6 @@ class IotLABShell(object): user['lastName'] = email.split('.')[0] try: self.api.method('admin/users', 'post', - json=user) + json=user) except HTTPError as err: logger.warning("iotlashell add_user error %s" % err.reason) - \ No newline at end of file -- 2.43.0