Example #1
0
    def cluster_exec(self, cmd, single=False, parallel=False,
                all_nodes=False, check=False, timeout=None, **kwargs):
        """Runs cmd on cluster.

        If single is True, commands will run parallel, but only one
        command on server.

        If parallel is True, commands will run parallel and wouldn't
        see how many ones on one server.

        If both is false, one command per time.

        If all_nodes is true, runs command on all child of the node,
        else only on cluster (e.g. nodes with numeric name).

        If check is true, runs command only if all servers in node is alive.
        Optional argument is 'timeout', it's a timeout to determine if server
        is alive. See get_dead_nodes for detail.
        """
        if single and parallel:
            raise TypeError("single OR parallel, not both")
        if (timeout is not None) and not check:
            raise TypeError("timeout hasn't got any sense without check=True")
        if check:
            if not alive.is_alive(self, all_nodes=all_nodes, **kwargs):
                raise RadistError('some nodes is dead')
        devnull = file(os.devnull, 'r')
        result = []
        pids = {}
        queue = {}
        to_run = self.__get_exec_list(cmd, all_nodes)
        for node, command in to_run.items():
            server = node.primary.server
            if parallel:
                pid = helpers.r_exec(server, command,
                    flags=os.P_NOWAIT, stdin=devnull, **kwargs)
                pids[pid] = node
            elif single:
                if server not in queue:
                    queue[server] = []
                queue[server].append((node, command))
            else:
                result.append((node, helpers.r_exec(server, command, **kwargs)))
        if parallel:
            return self.__wait_parallels(pids)
        elif single:
            return self.__run_single(queue, **kwargs)
        else:
            return result
Example #2
0
    def __run_single(self, queue, **kwargs):
        result = []
        pids = {}
        for server in queue.keys():
            node, command = queue[server].pop()
            pid = helpers.r_exec(server, command, flags=os.P_NOWAIT, **kwargs)
            pids[pid] = node

        while len(pids) > 0:
            pid, status = os.wait()
            if pid in pids:
                node = pids[pid]
                del pids[pid]
                result.append((node, status))
                if len(queue[node.primary.server]) > 0:
                    node, command = queue[node.primary.server].pop()
                    server = node.primary.server
                    pid = helpers.r_exec(server, command, flags=os.P_NOWAIT, **kwargs)
                    pids[pid] = node
            else:
                # XXX shit happens
                pass
        return result
Example #3
0
 def r_exec(self, command, **kwargs):
     """Run command on node."""
     return helpers.r_exec(self._get_server(),
                 command % self.get_attrs(), **kwargs)