diff options
author | Lars Wirzenius <lars.wirzenius@codethink.co.uk> | 2011-10-19 15:01:00 +0100 |
---|---|---|
committer | Lars Wirzenius <lars.wirzenius@codethink.co.uk> | 2011-10-19 15:01:00 +0100 |
commit | 04b37aca13ac899bede40bfef19e5c2e1230a75f (patch) | |
tree | 467a2ac6a059a23d9dd5c163bd900675f6068601 /morphlib | |
parent | fd4d285ed978c662607463ae4aa8abdccfab708a (diff) | |
download | morph-04b37aca13ac899bede40bfef19e5c2e1230a75f.tar.gz |
Include stdout output in CommandFailed errors.
This is necessary because compilers tend to write error messages to
stdout, not stderr, and it is silly to make morph users go read the
log files to see what the error actually is.
Diffstat (limited to 'morphlib')
-rw-r--r-- | morphlib/execute.py | 18 | ||||
-rw-r--r-- | morphlib/execute_tests.py | 23 |
2 files changed, 36 insertions, 5 deletions
diff --git a/morphlib/execute.py b/morphlib/execute.py index fe1921fe..02e7e196 100644 --- a/morphlib/execute.py +++ b/morphlib/execute.py @@ -23,7 +23,17 @@ import morphlib class CommandFailure(Exception): - pass + def __init__(self, command, stdout, stderr, exit): + Exception.__init__(self, + 'Command failed: %s\n' + 'Standard output:\n%s\n' + 'Standard error:\n%s\n' + 'Exit code: %s' % + (command, + morphlib.util.indent(stdout), + morphlib.util.indent(stderr), + exit)) + class Execute(object): @@ -64,8 +74,7 @@ class Execute(object): logging.debug('Standard output:\n%s' % morphlib.util.indent(out)) logging.debug('Standard error:\n%s' % morphlib.util.indent(err)) if p.returncode != 0: - raise CommandFailure('Command failed: %s\n%s' % - (command, morphlib.util.indent(err))) + raise CommandFailure(command, out, err, p.returncode) stdouts.append(out) return stdouts @@ -90,7 +99,6 @@ class Execute(object): logging.debug('Standard output:\n%s' % morphlib.util.indent(out)) logging.debug('Standard error:\n%s' % morphlib.util.indent(err)) if p.returncode != 0: - raise CommandFailure('Command failed: %s\n%s' % - (argv, morphlib.util.indent(err))) + raise CommandFailure(' '.join(argv), out, err, p.returncode) return out diff --git a/morphlib/execute_tests.py b/morphlib/execute_tests.py index 043b9e2c..0d785809 100644 --- a/morphlib/execute_tests.py +++ b/morphlib/execute_tests.py @@ -35,6 +35,17 @@ class ExecuteTests(unittest.TestCase): self.assertRaises(morphlib.execute.CommandFailure, self.e.run, ['false']) + def test_run_commandfailure_contains_both_stdout_and_stderr_output(self): + try: + self.e.run(['printf "%s%s\n" foo msg; ' + 'printf "%s%s" bar msg 1>&2; ' + 'exit 1']) + except morphlib.execute.CommandFailure, e: + self.assert_('foomsg' in str(e)) + self.assert_('barmsg' in str(e)) + else: + self.assertTrue(False) + def test_returns_stdout_from_all_commands(self): self.assertEqual(self.e.run(['echo foo', 'echo bar']), ['foo\n', 'bar\n']) @@ -49,6 +60,18 @@ class ExecuteTests(unittest.TestCase): self.assertRaises(morphlib.execute.CommandFailure, self.e.runv, ['false']) + def test_runv_commandfailure_contains_both_stdout_and_stderr_output(self): + try: + self.e.runv(['sh', '-c', + 'printf "%s%s\n" foo msg; ' + 'printf "%s%s" bar msg 1>&2; ' + 'exit 1']) + except morphlib.execute.CommandFailure, e: + self.assert_('foomsg' in str(e)) + self.assert_('barmsg' in str(e)) + else: + self.assertTrue(False) + def test_runv_sets_working_directory(self): self.assertEqual(self.e.runv(['pwd']), '/\n') |