def test_with_stdout(self):
     stdout = """
     Lo, praise of the prowess of people-kings
     of spear-armed Danes, in days long sped,
     we have heard, and what honot the athelings won!
     Oft Scyld the Scefing from squadroned foes,
     from many a tribe, the mead-bench tore,
     awing the earls. Since erse he lay
     friendless, a foundling, fate repaid him:
     for he waxed under welkin, in wealth he trove,
     till before him the folk, both far and near,
     who house by the whale-path, heard his mandate,
     gabe him gits: a good king he!
     To him an heir was afterward born,
     a son in his halls, whom heaven sent
     to favor the fol, feeling their woe
     that erst they had lacked an earl for leader
     so long a while; the Lord endowed him,
     the Wielder of Wonder, with world's renown.
     """.strip()
     err = exception.ProcessExecutionError(stdout=stdout)
     print err.message
     self.assertTrue('people-kings' in err.message)
Esempio n. 2
0
def execute(*cmd, **kwargs):
    """
    Helper method to execute command with optional retry.

    :cmd                Passed to subprocess.Popen.
    :process_input      Send to opened process.
    :check_exit_code    Defaults to 0. Raise exception.ProcessExecutionError
                        unless program exits with this code.
    :delay_on_retry     True | False. Defaults to True. If set to True, wait a
                        short amount of time before retrying.
    :attempts           How many times to retry cmd.
    :run_as_root        True | False. Defaults to False. If set to True,
                        the command is prefixed by the command specified
                        in the root_helper kwarg.
    :root_helper        command to prefix all cmd's with

    :raises exception.Error on receiving unknown arguments
    :raises exception.ProcessExecutionError
    """

    process_input = kwargs.pop('process_input', None)
    check_exit_code = kwargs.pop('check_exit_code', 0)
    delay_on_retry = kwargs.pop('delay_on_retry', True)
    attempts = kwargs.pop('attempts', 1)
    run_as_root = kwargs.pop('run_as_root', False)
    root_helper = kwargs.pop('root_helper', '')
    if len(kwargs):
        raise exception.Error(
            _('Got unknown keyword args '
              'to utils.execute: %r') % kwargs)
    if run_as_root:
        cmd = shlex.split(root_helper) + list(cmd)
    cmd = map(str, cmd)

    while attempts > 0:
        attempts -= 1
        try:
            LOG.debug(_('Running cmd (subprocess): %s'), ' '.join(cmd))
            _PIPE = subprocess.PIPE  # pylint: disable=E1101
            obj = subprocess.Popen(cmd,
                                   stdin=_PIPE,
                                   stdout=_PIPE,
                                   stderr=_PIPE,
                                   close_fds=True)
            result = None
            if process_input is not None:
                result = obj.communicate(process_input)
            else:
                result = obj.communicate()
            obj.stdin.close()  # pylint: disable=E1101
            _returncode = obj.returncode  # pylint: disable=E1101
            if _returncode:
                LOG.debug(_('Result was %s') % _returncode)
                if (isinstance(check_exit_code, int)
                        and not isinstance(check_exit_code, bool)
                        and _returncode != check_exit_code):
                    (stdout, stderr) = result
                    raise exception.ProcessExecutionError(
                        exit_code=_returncode,
                        stdout=stdout,
                        stderr=stderr,
                        cmd=' '.join(cmd))
            return result
        except exception.ProcessExecutionError:
            if not attempts:
                raise
            else:
                LOG.debug(_('%r failed. Retrying.'), cmd)
                if delay_on_retry:
                    greenthread.sleep(random.randint(20, 200) / 100.0)
        finally:
            # NOTE(termie): this appears to be necessary to let the subprocess
            #               call clean something up in between calls, without
            #               it two execute calls in a row hangs the second one
            greenthread.sleep(0)
 def test_with_cmd(self):
     cmd = 'telinit'
     err = exception.ProcessExecutionError(cmd=cmd)
     self.assertTrue(cmd in err.message)
 def test_with_exit_code(self):
     exit_code = 0
     err = exception.ProcessExecutionError(exit_code=exit_code)
     self.assertTrue(str(exit_code) in err.message)
 def test_with_description(self):
     description = 'The Narwhal Bacons at Midnight'
     err = exception.ProcessExecutionError(description=description)
     self.assertTrue(description in err.message)
 def test_defaults(self):
     err = exception.ProcessExecutionError()
     self.assertTrue('None\n' in err.message)
     self.assertTrue('code: -\n' in err.message)
 def test_with_stderr(self):
     stderr = 'Cottonian library'
     err = exception.ProcessExecutionError(stderr=stderr)
     self.assertTrue(stderr in str(err.message))