def listen_messenger(self, timeout=60): """ Wait for msg from slave side and take care about them. """ succ, r_cmd = self.read_msg(timeout) if succ is None: return r_cmd if not succ: raise remote_interface.CommanderError("Remote process died.") self.listen_errors(r_cmd) self.listen_streams(r_cmd) self.listen_cmds(r_cmd) self.listen_queries(r_cmd) return r_cmd
def __init__(self, stdin, stdout, debug=False): """ :type stdin: IOWrapper with implemented write function. :type stout: IOWrapper with implemented read function. """ super(CommanderMaster, self).__init__(stdin, stdout) self.cmds = {} self.debug = debug self.responder = None self.flush_stdin() self.write_msg("start") succ, msg = self.read_msg() if not succ or msg != "Started": raise remote_interface.CommanderError("Remote commander" " not started.")
def cmd_loop(self): """ Wait for commands from master and receive results and outputs from commands. """ try: while (not self._exit): stdios = [self.stdin, self.o_stdout, self.o_stderr] r_pipes = [ cmd.r_pipe for cmd in list(self.cmds.values()) if cmd.r_pipe is not None ] stdouts = [ cmd.stdout_pipe for cmd in list(self.cmds.values()) if cmd.stdout_pipe is not None ] stderrs = [ cmd.stderr_pipe for cmd in list(self.cmds.values()) if cmd.stderr_pipe is not None ] r, _, _ = select.select(stdios + r_pipes + stdouts + stderrs, [], []) if self.stdin in r: # command from controller m = self.read_msg() if m[0] is False: logger.info("Other side is closed.") break if m[0] is None: logger.info("Reading is timeouted.") break cmd = CmdSlave(m[1]) self.cmds[cmd.cmd_id] = cmd try: # There is hidden bug. We can bump into condition when # we running some function-command. That function dump # some data to stdio. But, stdio is out of # consideration at this point. It can stuck. cmd(self) self.write_msg(cmd.basecmd) except Exception: err_msg = traceback.format_exc() self.write_msg( remote_interface.CommanderError(err_msg)) if self.o_stdout in r: # Send message from stdout msg = os.read(self.o_stdout, 16384) self.write_msg(remote_interface.StdOut(msg)) if self.o_stderr in r: # Send message from stdout msg = os.read(self.o_stderr, 16384) self.write_msg(remote_interface.StdErr(msg)) # test all commands for io for cmd in list(self.cmds.values()): if cmd.stdout_pipe in r: # command stdout data = os.read(cmd.stdout_pipe, 16384) if data != "": # pipe is not closed on another side. self.write_msg( remote_interface.StdOut(data, cmd.cmd_id)) else: os.close(cmd.stdout_pipe) cmd.stdout_pipe = None if cmd.stderr_pipe in r: # command stderr data = os.read(cmd.stderr_pipe, 16384) if data != "": # pipe is not closed on another side. self.write_msg( remote_interface.StdErr(data, cmd.cmd_id)) else: os.close(cmd.stderr_pipe) cmd.stderr_pipe = None if cmd.r_pipe in r: # command results if cmd.work(): cmd.finish(self) self.write_msg(cmd.basecmd) except Exception: err_msg = traceback.format_exc() self.write_msg(remote_interface.CommanderError(err_msg))