# Decorator to invoke class initialization method
@clsinit
class ResourceManager(Logger):
+ """ Base clase for all ResourceManagers.
+
+ A ResourceManger is specific to a resource type (e.g. Node,
+ Switch, Application, etc) on a specific backend (e.g. PlanetLab,
+ OMF, etc).
+
+ The ResourceManager instances are responsible for interacting with
+ and controlling concrete (physical or virtual) resources in the
+ experimental backends.
+
+ """
_rtype = "Resource"
_attributes = None
_traces = None
+ _help = None
+ _backend = None
@classmethod
def _register_attribute(cls, attr):
"""
return copy.deepcopy(cls._traces.values())
+ @classmethod
+ def get_help(cls):
+ """ Returns the description of the type of Resource
+
+ """
+ return cls._help
+
+ @classmethod
+ def get_backend(cls):
+ """ Returns the identified of the backend (i.e. testbed, environment)
+ for the Resource
+
+ """
+ return cls._backend
+
def __init__(self, ec, guid):
super(ResourceManager, self).__init__(self.rtype())
def fail(self):
self.set_failed()
+ self.ec.set_rm_failure()
def set(self, name, value):
""" Set the value of the attribute
:type action: str
:param group: Group of RMs to wait for (list of guids)
:type group: int or list of int
- :param state: State to wait for on all RM in group. (either 'STARTED' or 'STOPPED')
+ :param state: State to wait for on all RM in group. (either 'STARTED', 'STOPPED' or 'READY')
:type state: str
:param time: Time to wait after 'state' is reached on all RMs in group. (e.g. '2s')
:type time: str
def unregister_condition(self, group, action = None):
""" Removed conditions for a certain group of guids
- :param action: Action to restrict to condition (either 'START' or 'STOP')
+ :param action: Action to restrict to condition (either 'START', 'STOP' or 'READY')
:type action: str
:param group: Group of RMs to wait for (list of guids)
:param group: Group of RMs to wait for (list of guids)
:type group: int or list of int
- :param state: State to wait for on all RM in group. (either 'STARTED' or 'STOPPED')
+ :param state: State to wait for on all RM in group. (either 'STARTED', 'STOPPED' or 'READY')
:type state: str
:param time: Time to wait after 'state' is reached on all RMs in group. (e.g. '2s')
:type time: str
elif state == ResourceState.STOPPED:
t = rm.stop_time
else:
- # Only keep time information for START and STOP
break
# time already elapsed since RM changed state
self.debug(" ----- STOPPING ---- ")
self.stop()
+ def deploy_with_conditions(self):
+ """ Deploy RM when all the conditions in self.conditions for
+ action 'READY' are satisfied.
+
+ """
+ reschedule = False
+ delay = reschedule_delay
+
+ ## evaluate if set conditions are met
+
+ # only can deploy when RM is either NEW, DISCOVERED or PROVISIONED
+ if self.state not in [ResourceState.NEW, ResourceState.DISCOVERED,
+ ResourceState.PROVISIONED]:
+ reschedule = True
+ self.debug("---- RESCHEDULING DEPLOY ---- state %s " % self.state )
+ else:
+ deploy_conditions = self.conditions.get(ResourceAction.DEPLOY, [])
+
+ self.debug("---- DEPLOY CONDITIONS ---- %s" % deploy_conditions)
+
+ # Verify all start conditions are met
+ for (group, state, time) in deploy_conditions:
+ # Uncomment for debug
+ #unmet = []
+ #for guid in group:
+ # rm = self.ec.get_resource(guid)
+ # unmet.append((guid, rm._state))
+ #
+ #self.debug("---- WAITED STATES ---- %s" % unmet )
+
+ reschedule, delay = self._needs_reschedule(group, state, time)
+ if reschedule:
+ break
+
+ if reschedule:
+ self.ec.schedule(delay, self.deploy_with_conditions)
+ else:
+ self.debug("----- STARTING ---- ")
+ self.deploy()
+
def connect(self, guid):
""" Performs actions that need to be taken upon associating RMs.
This method should be redefined when necessary in child classes.