diff --git a/lib/models/builder.js b/lib/models/builder.js index d0332a8117..641ec70402 100644 --- a/lib/models/builder.js +++ b/lib/models/builder.js @@ -117,7 +117,11 @@ module.exports = Task.extend({ return self.builder.build.apply(self.builder, args); }) .then(this.processBuildResult.bind(this)) - .then(this.processAddonBuildSteps.bind(this, 'postBuild')); + .then(this.processAddonBuildSteps.bind(this, 'postBuild')) + .catch(function(error) { + this.processAddonBuildSteps('buildError', error); + throw error; + }.bind(this)); }, cleanup: function() { diff --git a/tests/unit/models/builder-test.js b/tests/unit/models/builder-test.js index ce24690613..307e95fed4 100644 --- a/tests/unit/models/builder-test.js +++ b/tests/unit/models/builder-test.js @@ -138,6 +138,10 @@ describe('models/builder.js', function() { return Promise.resolve(); }, + + buildError: function() { + hooksCalled.push('buildError'); + }, }; builder = new Builder({ @@ -182,5 +186,68 @@ describe('models/builder.js', function() { assert.deepEqual(hooksCalled, ['preBuild', 'build', 'postBuild']); }); }); + + it('buildError receives the error object from the errored step', function() { + var thrownBuildError = new Error('buildError'); + var receivedBuildError; + + addon.buildError = function(errorThrown) { + receivedBuildError = errorThrown; + }; + + builder.builder.build = function() { + hooksCalled.push('build'); + + return Promise.reject(thrownBuildError); + }; + + return builder.build().then(function() { + assert(false, 'should not succeed'); + }).catch(function() { + assert.equal(receivedBuildError, thrownBuildError); + }); + }); + + it('calls buildError and does not call build or postBuild when preBuild fails', function() { + addon.preBuild = function() { + hooksCalled.push('preBuild'); + + return Promise.reject(new Error('preBuild Error')); + }; + + return builder.build().then(function() { + assert(false, 'should not succeed'); + }).catch(function() { + assert.deepEqual(hooksCalled, ['preBuild', 'buildError']); + }); + }); + + it('calls buildError and does not call postBuild when build fails', function() { + builder.builder.build = function() { + hooksCalled.push('build'); + + return Promise.reject(new Error('build Error')); + }; + + return builder.build().then(function() { + assert(false, 'should not succeed'); + }).catch(function() { + assert.deepEqual(hooksCalled, ['preBuild', 'build', 'buildError']); + }); + }); + + it('calls buildError when postBuild fails', function() { + addon.postBuild = function() { + hooksCalled.push('postBuild'); + + return Promise.reject(new Error('preBuild Error')); + }; + + return builder.build().then(function() { + assert(false, 'should not succeed'); + }).catch(function() { + assert.deepEqual(hooksCalled, ['preBuild', 'build', 'postBuild', 'buildError']); + }); + }); }); });