Exemplo n.º 1
0
    def send_command_to_pilot(self, cmd, arg=None, pilot_manager_id=None, pilot_ids=None):
        """ Send a command to one or more pilots.
        """
        if self._s is None:
            raise Exception("No active session.")

        if pilot_manager_id is None and pilot_ids is None:
            raise Exception("Either Pilot Manager or Pilot needs to be specified.")

        if pilot_manager_id is not None and pilot_ids is not None:
            raise Exception("Pilot Manager and Pilot can not be both specified.")

        command = {COMMAND_FIELD: {COMMAND_TYPE: cmd,
                                   COMMAND_ARG:  arg,
                                   COMMAND_TIME: timestamp()
        }}

        if pilot_ids is None:
            # send command to all pilots that are known to the
            # pilot manager.
            self._p.update(
                {"pilotmanager": pilot_manager_id},
                {"$push": command},
                multi=True
            )
        else:
            if not isinstance(pilot_ids, list):
                pilot_ids = [pilot_ids]
            # send command to selected pilots if pilot_ids are
            # specified convert ids to object ids
            for pid in pilot_ids:
                self._p.update(
                    {"_id": pid},
                    {"$push": command}
                )
Exemplo n.º 2
0
    def update_pilot_state(self, pilot_uid, started=None, finished=None,
                           submitted=None, state=None, sagajobid=None,
                           pilot_sandbox=None, global_sandbox=None, 
                           logs=None):

        """Updates the information of a pilot.
        """
        if self._s is None:
            raise Exception("No active session.")

        # construct the update query
        set_query  = dict()
        push_query = dict()

        if state :
            set_query["state"] = state
            push_query["statehistory"] = [{'state': state, 'timestamp': timestamp()}]

        if logs  : 
            push_query["log"] = logs

        if started        : set_query["started"]        = started 
        if finished       : set_query["finished"]       = finished 
        if submitted      : set_query["submitted"]      = submitted 
        if sagajobid      : set_query["sagajobid"]      = sagajobid 
        if pilot_sandbox  : set_query["sandbox"]        = pilot_sandbox 
        if global_sandbox : set_query["global_sandbox"] = global_sandbox 

        # update pilot entry.
        self._p.update(
            {"_id": pilot_uid},
            {"$set": set_query, "$pushAll": push_query},
            multi=True
        )
Exemplo n.º 3
0
    def close(self):
        """ 
        close the session
        """
        if self._s is None:
            raise RuntimeError("No active session.")

        self._closed = timestamp()
Exemplo n.º 4
0
    def close(self):
        """ 
        close the session
        """
        if self._s is None:
            raise RuntimeError("No active session.")

        self._closed = timestamp()
Exemplo n.º 5
0
    def insert_compute_units(self, umgr_uid, units, unit_log):
        """ Adds one or more compute units to the database and sets their state
            to 'PENDING'.
        """
        if self._s is None:
            raise RuntimeError("No active session.")

        # Make sure we work on a list.
        if not isinstance(units, list):
            units = [units]

        unit_docs = list()
        results = dict()

        for unit in units:

            ts = timestamp()

            unit_json = {
                "_id": unit.uid,
                "description": unit.description.as_dict(),
                "restartable": unit.description.restartable,
                "unitmanager": umgr_uid,
                "pilot": None,
                "pilot_sandbox": None,
                "state": unit._local_state,
                "statehistory": [{
                    "state": unit._local_state,
                    "timestamp": ts
                }],
                "submitted": ts,
                "started": None,
                "finished": None,
                "exec_locs": None,
                "exit_code": None,
                "sandbox": None,
                "stdout": None,
                "stderr": None,
                "log": unit_log,
                "FTW_Input_Status": None,
                "FTW_Input_Directives": None,
                "Agent_Input_Status": None,
                "Agent_Input_Directives": None,
                "FTW_Output_Status": None,
                "FTW_Output_Directives": None,
                "Agent_Output_Status": None,
                "Agent_Output_Directives": None
            }
            unit_docs.append(unit_json)
            results[unit.uid] = unit_json

        unit_uids = self._w.insert(unit_docs)

        assert len(unit_docs) == len(unit_uids)
        assert len(results) == len(unit_uids)

        return results
Exemplo n.º 6
0
    def insert_compute_units(self, umgr_uid, units, unit_log):
        """ Adds one or more compute units to the database and sets their state
            to 'PENDING'.
        """
        if self._s is None:
            raise RuntimeError("No active session.")

        # Make sure we work on a list.
        if not isinstance(units, list):
            units = [units]

        unit_docs = list()
        results = dict()

        for unit in units:

            ts = timestamp()

            unit_json = {
                "_id":           unit.uid,
                "description":   unit.description.as_dict(),
                "restartable":   unit.description.restartable,
                "unitmanager":   umgr_uid,
                "pilot":         None,
                "pilot_sandbox": None,
                "state":         unit._local_state,
                "statehistory":  [{"state": unit._local_state, "timestamp": ts}],
                "submitted":     ts,
                "started":       None,
                "finished":      None,
                "exec_locs":     None,
                "exit_code":     None,
                "sandbox":       None,
                "stdout":        None,
                "stderr":        None,
                "log":           unit_log,
                "FTW_Input_Status":        None,
                "FTW_Input_Directives":    None,
                "Agent_Input_Status":      None,
                "Agent_Input_Directives":  None,
                "FTW_Output_Status":       None,
                "FTW_Output_Directives":   None,
                "Agent_Output_Status":     None,
                "Agent_Output_Directives": None
            }
            unit_docs.append(unit_json)
            results[unit.uid] = unit_json

        unit_uids = self._w.insert(unit_docs)

        assert len(unit_docs) == len(unit_uids)
        assert len(results) == len(unit_uids)

        return results
Exemplo n.º 7
0
    def __init__(self, sid, name, dburl):
        """ Creates a new session
            A session is a distinct collection with three sub-collections
            in MongoDB:

            radical.pilot.<sid>    | Base collection. Holds some metadata.   | self._s
            radical.pilot.<sid>.cu | Collection holding all compute units.   | self._w
            radical.pilot.<sid>.um | Collection holding all unit managers.   | self._um
            radical.pilot.<sid>.p  | Collection holding all pilots.          | self._p
            radical.pilot.<sid>.pm | Collection holding all pilot managers.  | self._pm

            All collections are created with a new session. Since MongoDB
            uses lazy-create, they only appear in the database after the
            first insert. That's ok.
        """

        # mpongodb_connect wants a string at the moment
        mongo, db, _, _, _ = ru.mongodb_connect(str(dburl))

        if not mongo or not db:
            raise RuntimeError("Could not connect to database at %s" % dburl)

        self._client = mongo
        self._db = db
        self._dburl = ru.Url(dburl)
        self._session_id = sid
        self._created = timestamp()
        self._connected = self._created
        self._closed = None

        # make sure session doesn't exist already
        if self._db[sid].count() != 0:
            raise RuntimeError("Session '%s' already exists." % sid)

        # create the db entry
        self._s = self._db["%s" % sid]
        self._s.insert({
            "_id": sid,
            "name": name,
            "created": self._created,
            "connected": self._created
        })

        # Create the collection shortcut:
        self._w = self._db["%s.cu" % sid]
        self._um = self._db["%s.um" % sid]

        self._p = self._db["%s.p" % sid]
        self._pm = self._db["%s.pm" % sid]
Exemplo n.º 8
0
    def __init__(self, sid, name, dburl):
        """ Creates a new session
            A session is a distinct collection with three sub-collections
            in MongoDB:

            radical.pilot.<sid>    | Base collection. Holds some metadata.   | self._s
            radical.pilot.<sid>.cu | Collection holding all compute units.   | self._w
            radical.pilot.<sid>.um | Collection holding all unit managers.   | self._um
            radical.pilot.<sid>.p  | Collection holding all pilots.          | self._p
            radical.pilot.<sid>.pm | Collection holding all pilot managers.  | self._pm

            All collections are created with a new session. Since MongoDB
            uses lazy-create, they only appear in the database after the
            first insert. That's ok.
        """

        # mpongodb_connect wants a string at the moment
        mongo, db, _, _, _ = ru.mongodb_connect(str(dburl))

        if not mongo or not db:
            raise RuntimeError("Could not connect to database at %s" % dburl)

        self._client     = mongo
        self._db         = db
        self._dburl      = ru.Url(dburl)
        self._session_id = sid
        self._created    = timestamp()
        self._connected  = self._created
        self._closed     = None

        # make sure session doesn't exist already
        if self._db[sid].count() != 0:
            raise RuntimeError("Session '%s' already exists." % sid)

        # create the db entry
        self._s = self._db["%s" % sid]
        self._s.insert({"_id"       : sid,
                        "name"      : name,
                        "created"   : self._created,
                        "connected" : self._created})

        # Create the collection shortcut:
        self._w  = self._db["%s.cu" % sid]
        self._um = self._db["%s.um" % sid] 

        self._p  = self._db["%s.p"  % sid]
        self._pm = self._db["%s.pm" % sid] 
Exemplo n.º 9
0
    def insert_pilot(self, pilot_uid, pilot_manager_uid, pilot_description,
                     pilot_sandbox, global_sandbox):
        """Adds a new pilot document to the database.
        """
        if self._s is None:
            raise Exception("No active session.")

        ts = timestamp()

        # the SAGA attribute interface does not expose private attribs in
        # as_dict().  That semantics may change in the future, for now we copy
        # private elems directly.
        pd_dict = dict()
        for k in pilot_description._attributes_i_list(priv=True):
            pd_dict[k] = pilot_description[k]

        pilot_doc = {
            "_id": pilot_uid,
            "description": pd_dict,
            "submitted": ts,
            "input_transfer_started": None,
            "input_transfer_finished": None,
            "started": None,
            "finished": None,
            "heartbeat": None,
            "output_transfer_started": None,
            "output_transfer_finished": None,
            "nodes": None,
            "cores_per_node": None,
            "sagajobid": None,
            "sandbox": pilot_sandbox,
            "global_sandbox": global_sandbox,
            "state": PENDING_LAUNCH,
            "statehistory": [{
                "state": PENDING_LAUNCH,
                "timestamp": ts
            }],
            "log": [],
            "pilotmanager": pilot_manager_uid,
            "unitmanager": None,
            "commands": []
        }

        self._p.insert(pilot_doc)

        return str(pilot_uid), pilot_doc
Exemplo n.º 10
0
    def insert_pilot(self, pilot_uid, pilot_manager_uid, pilot_description,
        pilot_sandbox, global_sandbox):
        """Adds a new pilot document to the database.
        """
        if self._s is None:
            raise Exception("No active session.")

        ts = timestamp()

        # the SAGA attribute interface does not expose private attribs in
        # as_dict().  That semantics may change in the future, for now we copy
        # private elems directly.
        pd_dict = dict()
        for k in pilot_description._attributes_i_list (priv=True):
            pd_dict[k] = pilot_description[k]

        pilot_doc = {
            "_id":            pilot_uid,
            "description":    pd_dict,
            "submitted":      ts,
            "input_transfer_started": None,
            "input_transfer_finished": None,
            "started":        None,
            "finished":       None,
            "heartbeat":      None,
            "output_transfer_started": None,
            "output_transfer_finished": None,
            "nodes":          None,
            "cores_per_node": None,
            "sagajobid":      None,
            "sandbox":        pilot_sandbox,
            "global_sandbox": global_sandbox,
            "state":          PENDING_LAUNCH,
            "statehistory":   [{"state": PENDING_LAUNCH, "timestamp": ts}],
            "log":            [],
            "pilotmanager":   pilot_manager_uid,
            "unitmanager":    None,
            "commands":       []
        }

        self._p.insert(pilot_doc)

        return str(pilot_uid), pilot_doc
Exemplo n.º 11
0
    def update_pilot_state(self,
                           pilot_uid,
                           started=None,
                           finished=None,
                           submitted=None,
                           state=None,
                           sagajobid=None,
                           pilot_sandbox=None,
                           global_sandbox=None,
                           logs=None):
        """Updates the information of a pilot.
        """
        if self._s is None:
            raise Exception("No active session.")

        # construct the update query
        set_query = dict()
        push_query = dict()

        if state:
            set_query["state"] = state
            push_query["statehistory"] = [{
                'state': state,
                'timestamp': timestamp()
            }]

        if logs:
            push_query["log"] = logs

        if started: set_query["started"] = started
        if finished: set_query["finished"] = finished
        if submitted: set_query["submitted"] = submitted
        if sagajobid: set_query["sagajobid"] = sagajobid
        if pilot_sandbox: set_query["sandbox"] = pilot_sandbox
        if global_sandbox: set_query["global_sandbox"] = global_sandbox

        # update pilot entry.
        self._p.update({"_id": pilot_uid}, {
            "$set": set_query,
            "$pushAll": push_query
        },
                       multi=True)
Exemplo n.º 12
0
    def send_command_to_pilot(self,
                              cmd,
                              arg=None,
                              pilot_manager_id=None,
                              pilot_ids=None):
        """ Send a command to one or more pilots.
        """
        if self._s is None:
            raise Exception("No active session.")

        if pilot_manager_id is None and pilot_ids is None:
            raise Exception(
                "Either Pilot Manager or Pilot needs to be specified.")

        if pilot_manager_id is not None and pilot_ids is not None:
            raise Exception(
                "Pilot Manager and Pilot can not be both specified.")

        command = {
            COMMAND_FIELD: {
                COMMAND_TYPE: cmd,
                COMMAND_ARG: arg,
                COMMAND_TIME: timestamp()
            }
        }

        if pilot_ids is None:
            # send command to all pilots that are known to the
            # pilot manager.
            self._p.update({"pilotmanager": pilot_manager_id},
                           {"$push": command},
                           multi=True)
        else:
            if not isinstance(pilot_ids, list):
                pilot_ids = [pilot_ids]
            # send command to selected pilots if pilot_ids are
            # specified convert ids to object ids
            for pid in pilot_ids:
                self._p.update({"_id": pid}, {"$push": command})
Exemplo n.º 13
0
    def set_compute_unit_state(self, unit_ids, state, log, src_states=None):
        """
        Update the state and the log of one or more ComputeUnit(s).
        If src_states is given, this will only update units which are currently
        in those src states.
        """
        ts = timestamp()

        if not unit_ids:
            return

        if self._s is None:
            raise Exception("No active session.")

        # Make sure we work on a list.
        if not isinstance(unit_ids, list):
            unit_ids = [unit_ids]

        if src_states and not isinstance(src_states, list):
            src_states = [src_states]

        bulk = self._w.initialize_ordered_bulk_op()

        for uid in unit_ids:

            if src_states:
                bulk.find   ({"_id"     : uid,
                              "state"   : {"$in"  : src_states} }) \
                    .update ({"$set"    : {"state": state},
                              "$push"   : {"statehistory": {"state": state, "timestamp": ts}},
                              "$push"   : {"log"  : {"message": log, "timestamp": ts}}})
            else:
                bulk.find   ({"_id"     : uid}) \
                    .update ({"$set"    : {"state": state},
                              "$push"   : {"statehistory": {"state": state, "timestamp": ts}},
                              "$push"   : {"log"  : {"message": log, "timestamp": ts}}})

        result = bulk.execute()
Exemplo n.º 14
0
    def set_compute_unit_state(self, unit_ids, state, log, src_states=None):
        """
        Update the state and the log of one or more ComputeUnit(s).
        If src_states is given, this will only update units which are currently
        in those src states.
        """
        ts = timestamp()

        if  not unit_ids :
            return

        if  self._s is None:
            raise Exception("No active session.")

        # Make sure we work on a list.
        if not isinstance(unit_ids, list):
            unit_ids = [unit_ids]

        if src_states and not isinstance (src_states, list) :
            src_states = [src_states]

        bulk = self._w.initialize_ordered_bulk_op ()

        for uid in unit_ids :

            if src_states :
                bulk.find   ({"_id"     : uid, 
                              "state"   : {"$in"  : src_states} }) \
                    .update ({"$set"    : {"state": state},
                              "$push"   : {"statehistory": {"state": state, "timestamp": ts}},
                              "$push"   : {"log"  : {"message": log, "timestamp": ts}}})
            else :
                bulk.find   ({"_id"     : uid}) \
                    .update ({"$set"    : {"state": state},
                              "$push"   : {"statehistory": {"state": state, "timestamp": ts}},
                              "$push"   : {"log"  : {"message": log, "timestamp": ts}}})

        result = bulk.execute()