diff options
author | Steven Knight <knight@baldmt.com> | 2001-10-02 03:15:32 (GMT) |
---|---|---|
committer | Steven Knight <knight@baldmt.com> | 2001-10-02 03:15:32 (GMT) |
commit | 321aa365f5770b70be13631f717be8ecfeaf70f2 (patch) | |
tree | 683c28579fef2fe9a942693357dd5ca9a46e2514 /src/engine | |
parent | 97446895b5e0d92057123a962f45856009ff6bb9 (diff) | |
download | SCons-321aa365f5770b70be13631f717be8ecfeaf70f2.zip SCons-321aa365f5770b70be13631f717be8ecfeaf70f2.tar.gz SCons-321aa365f5770b70be13631f717be8ecfeaf70f2.tar.bz2 |
Handle build errors.
Diffstat (limited to 'src/engine')
-rw-r--r-- | src/engine/SCons/Builder.py | 15 | ||||
-rw-r--r-- | src/engine/SCons/BuilderTests.py | 35 | ||||
-rw-r--r-- | src/engine/SCons/Errors.py | 6 | ||||
-rw-r--r-- | src/engine/SCons/ErrorsTests.py | 8 | ||||
-rw-r--r-- | src/engine/SCons/Node/FSTests.py | 5 | ||||
-rw-r--r-- | src/engine/SCons/Node/NodeTests.py | 19 | ||||
-rw-r--r-- | src/engine/SCons/Node/__init__.py | 8 |
7 files changed, 78 insertions, 18 deletions
diff --git a/src/engine/SCons/Builder.py b/src/engine/SCons/Builder.py index d354c57..c90bc40 100644 --- a/src/engine/SCons/Builder.py +++ b/src/engine/SCons/Builder.py @@ -55,7 +55,7 @@ class Builder: def execute(self, **kw): """Execute a builder's action to create an output object. """ - apply(self.action.execute, (), kw) + return apply(self.action.execute, (), kw) @@ -99,6 +99,7 @@ class CommandAction(ActionBase): cmd = self.command % kw if print_actions: self.show(cmd) + ret = 0 if execute_actions: pid = os.fork() if not pid: @@ -112,7 +113,10 @@ class CommandAction(ActionBase): os.execvpe(args[0], args, ENV) else: # Parent process. - os.waitpid(pid, 0) + pid, stat = os.waitpid(pid, 0) + ret = stat >> 8 + return ret + class FunctionAction(ActionBase): @@ -124,7 +128,7 @@ class FunctionAction(ActionBase): # if print_actions: # XXX: WHAT SHOULD WE PRINT HERE? if execute_actions: - self.function(kw) + return self.function(kw) class ListAction(ActionBase): """Class for lists of other actions.""" @@ -133,4 +137,7 @@ class ListAction(ActionBase): def execute(self, **kw): for l in self.list: - apply(l.execute, (), kw) + r = apply(l.execute, (), kw) + if r != 0: + return r + return 0 diff --git a/src/engine/SCons/BuilderTests.py b/src/engine/SCons/BuilderTests.py index 0ea81f0..965df6e 100644 --- a/src/engine/SCons/BuilderTests.py +++ b/src/engine/SCons/BuilderTests.py @@ -77,23 +77,34 @@ class BuilderTestCase(unittest.TestCase): """Test execution of simple Builder objects One Builder is a string that executes an external command, - and one is an internal Python function. + one is an internal Python function, one is a list + containing one of each. """ - cmd = "python %s %s xyzzy" % (act_py, outfile) - builder = SCons.Builder.Builder(action = cmd) - builder.execute() + cmd1 = "python %s %s xyzzy" % (act_py, outfile) + builder = SCons.Builder.Builder(action = cmd1) + r = builder.execute() + assert r == 0 assert test.read(outfile, 'r') == "act.py: xyzzy\n" - def function(kw): - import os, string, sys + def function1(kw): f = open(kw['out'], 'w') - f.write("function\n") + f.write("function1\n") f.close() - return not None - - builder = SCons.Builder.Builder(action = function) - builder.execute(out = outfile) - assert test.read(outfile, 'r') == "function\n" + return 1 + + builder = SCons.Builder.Builder(action = function1) + r = builder.execute(out = outfile) + assert r == 1 + assert test.read(outfile, 'r') == "function1\n" + + cmd2 = "python %s %s syzygy" % (act_py, outfile) + def function2(kw): + open(kw['out'], 'a').write("function2\n") + return 2 + builder = SCons.Builder.Builder(action = [cmd2, function2]) + r = builder.execute(out = outfile) + assert r == 2 + assert test.read(outfile, 'r') == "act.py: syzygy\nfunction2\n" def test_insuffix(self): """Test Builder creation with a specified input suffix diff --git a/src/engine/SCons/Errors.py b/src/engine/SCons/Errors.py index ac43837..8599aee 100644 --- a/src/engine/SCons/Errors.py +++ b/src/engine/SCons/Errors.py @@ -9,6 +9,12 @@ __revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__" +class BuildError(Exception): + def __init__(self, node=None, stat=0, *args): + self.node = node + self.stat = stat + self.args = args + class InternalError(Exception): def __init__(self, args=None): self.args = args diff --git a/src/engine/SCons/ErrorsTests.py b/src/engine/SCons/ErrorsTests.py index d39a287..4747a43 100644 --- a/src/engine/SCons/ErrorsTests.py +++ b/src/engine/SCons/ErrorsTests.py @@ -6,6 +6,14 @@ import SCons.Errors class ErrorsTestCase(unittest.TestCase): + def test_BuildError(self): + """Test the BuildError exception.""" + try: + raise SCons.Errors.BuildError(node = "n", stat = 7) + except SCons.Errors.BuildError, e: + assert e.node == "n" + assert e.stat == 7 + def test_InternalError(self): """Test the InternalError exception.""" try: diff --git a/src/engine/SCons/Node/FSTests.py b/src/engine/SCons/Node/FSTests.py index 8e7e2a6..1cffd8c 100644 --- a/src/engine/SCons/Node/FSTests.py +++ b/src/engine/SCons/Node/FSTests.py @@ -6,17 +6,22 @@ import unittest import SCons.Node.FS + + built_it = None class Builder: def execute(self, **kw): global built_it built_it = 1 + return 0 class Environment: def Dictionary(self, *args): pass + + class FSTestCase(unittest.TestCase): def runTest(self): """Test FS (file system) Node operations diff --git a/src/engine/SCons/Node/NodeTests.py b/src/engine/SCons/Node/NodeTests.py index 738c7cc..26cf6bd 100644 --- a/src/engine/SCons/Node/NodeTests.py +++ b/src/engine/SCons/Node/NodeTests.py @@ -4,6 +4,7 @@ import os import sys import unittest +import SCons.Errors import SCons.Node @@ -14,6 +15,11 @@ class Builder: def execute(self, **kw): global built_it built_it = 1 + return 0 + +class FailBuilder: + def execute(self, **kw): + return 1 class Environment: def Dictionary(self, *args): @@ -23,6 +29,19 @@ class Environment: class NodeTestCase(unittest.TestCase): + def test_BuildException(self): + """Test throwing an exception on build failure. + """ + node = SCons.Node.Node() + node.builder_set(FailBuilder()) + node.env_set(Environment()) + try: + node.build() + except SCons.Errors.BuildError: + pass + else: + raise TestFailed, "did not catch expected BuildError" + def test_build(self): """Test building a node """ diff --git a/src/engine/SCons/Node/__init__.py b/src/engine/SCons/Node/__init__.py index 4f414ec..de15712 100644 --- a/src/engine/SCons/Node/__init__.py +++ b/src/engine/SCons/Node/__init__.py @@ -8,6 +8,7 @@ __revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__" +from SCons.Errors import BuildError import string @@ -25,8 +26,11 @@ class Node: def build(self): sources_str = string.join(map(lambda x: str(x), self.sources)) - self.builder.execute(ENV = self.env.Dictionary('ENV'), - target = str(self), source = sources_str) + stat = self.builder.execute(ENV = self.env.Dictionary('ENV'), + target = str(self), source = sources_str) + if stat != 0: + raise BuildError(node = self, stat = stat) + return stat def builder_set(self, builder): self.builder = builder |