From 0a15b899eeb9c74b434c1348cb6b5381d0dcb8ba Mon Sep 17 00:00:00 2001 From: Pierre Colle Date: Sat, 8 Dec 2018 14:25:30 +0100 Subject: [PATCH 1/2] fix: sync functions and sync errors --- lib/worker.js | 8 ++- package-lock.json | 111 ++++++++++++++-------------------- test/scenarios/sync-fn.js | 123 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 175 insertions(+), 67 deletions(-) create mode 100644 test/scenarios/sync-fn.js diff --git a/lib/worker.js b/lib/worker.js index aaeb9cf..d326a5c 100644 --- a/lib/worker.js +++ b/lib/worker.js @@ -131,7 +131,13 @@ Worker.prototype.close = function (cb) { }; Worker.prototype.execute = function (input, cb, heartbeat) { - this.fn(input, cb, heartbeat); + setImmediate(() => { + try { + this.fn(input, cb, heartbeat); + } catch (err) { + cb(err); + } + }); }; Worker.prototype.succeed = function (res) { diff --git a/package-lock.json b/package-lock.json index 0651f24..0e3a3bb 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1153,6 +1153,11 @@ } } }, + "aws-arn-parser": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/aws-arn-parser/-/aws-arn-parser-1.0.0.tgz", + "integrity": "sha1-ZHvgMMhPH43/nJbZ2PpgNIaehKI=" + }, "aws-sdk": { "version": "2.82.0", "resolved": "https://registry.npmjs.org/aws-sdk/-/aws-sdk-2.82.0.tgz", @@ -2859,6 +2864,12 @@ "array-find-index": "1.0.2" } }, + "cycle": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/cycle/-/cycle-1.0.3.tgz", + "integrity": "sha1-IegLK+hYD5i0aPN5QwZisEbDStI=", + "dev": true + }, "d": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz", @@ -3060,12 +3071,6 @@ "integrity": "sha1-OHHMCmoALow+Wzz38zYmRnXwa50=", "dev": true }, - "diff": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.0.8.tgz", - "integrity": "sha1-NDJ2MI7Jkbe8giZ+1VvBQR+XFmY=", - "dev": true - }, "dir-glob": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz", @@ -5213,18 +5218,6 @@ "parse-domain": "2.0.0" } }, - "glob": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-4.0.6.tgz", - "integrity": "sha1-aVxQvdTi+1xdNwsJHziNNwfikac=", - "dev": true, - "requires": { - "graceful-fs": "3.0.11", - "inherits": "2.0.3", - "minimatch": "1.0.0", - "once": "1.4.0" - } - }, "glob-base": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", @@ -5322,15 +5315,6 @@ "url-parse-lax": "1.0.0" } }, - "graceful-fs": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-3.0.11.tgz", - "integrity": "sha1-dhPHeKGv6mLyXGMKCG1/Osu92Bg=", - "dev": true, - "requires": { - "natives": "1.1.0" - } - }, "handlebars": { "version": "4.0.11", "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz", @@ -6158,6 +6142,12 @@ "isarray": "1.0.0" } }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true + }, "issue-parser": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/issue-parser/-/issue-parser-1.0.3.tgz", @@ -6493,12 +6483,6 @@ "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=", "dev": true }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, "make-dir": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.0.0.tgz", @@ -6725,16 +6709,6 @@ "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==", "dev": true }, - "minimatch": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-1.0.0.tgz", - "integrity": "sha1-4N0hILSeG3JM6NcUxSCCKpQ4V20=", - "dev": true, - "requires": { - "lru-cache": "2.7.3", - "sigmund": "1.0.1" - } - }, "minimist": { "version": "0.0.8", "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", @@ -6869,12 +6843,6 @@ } } }, - "natives": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/natives/-/natives-1.1.0.tgz", - "integrity": "sha1-6f+EFBimsux6SV6TmYT3jxY+bjE=", - "dev": true - }, "natural-compare": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", @@ -8362,12 +8330,6 @@ } } }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", @@ -8611,6 +8573,12 @@ "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, + "stack-trace": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/stack-trace/-/stack-trace-0.0.10.tgz", + "integrity": "sha1-VHxws0fo0ytOEI6hoqFZ5f3eGcA=", + "dev": true + }, "stack-utils": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-1.0.1.tgz", @@ -9245,17 +9213,6 @@ "spdx-expression-parse": "1.0.4" } }, - "vows": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/vows/-/vows-0.8.1.tgz", - "integrity": "sha1-4J6YjOWUygWgjXKrzKNOiNtVkTE=", - "dev": true, - "requires": { - "diff": "1.0.8", - "eyes": "0.1.8", - "glob": "4.0.6" - } - }, "well-known-symbols": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/well-known-symbols/-/well-known-symbols-1.0.0.tgz", @@ -9293,6 +9250,28 @@ "dev": true, "optional": true }, + "winston": { + "version": "2.4.4", + "resolved": "https://registry.npmjs.org/winston/-/winston-2.4.4.tgz", + "integrity": "sha512-NBo2Pepn4hK4V01UfcWcDlmiVTs7VTB1h7bgnB0rgP146bYhMxX0ypCz3lBOfNxCO4Zuek7yeT+y/zM1OfMw4Q==", + "dev": true, + "requires": { + "async": "1.0.0", + "colors": "1.0.3", + "cycle": "1.0.3", + "eyes": "0.1.8", + "isstream": "0.1.2", + "stack-trace": "0.0.10" + }, + "dependencies": { + "async": { + "version": "1.0.0", + "resolved": "http://registry.npmjs.org/async/-/async-1.0.0.tgz", + "integrity": "sha1-+PwEyjoTeErenhZBr5hXjPvWR6k=", + "dev": true + } + } + }, "wordwrap": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", diff --git a/test/scenarios/sync-fn.js b/test/scenarios/sync-fn.js new file mode 100644 index 0000000..83952bf --- /dev/null +++ b/test/scenarios/sync-fn.js @@ -0,0 +1,123 @@ +const test = require('ava').test; +const AWS = require('aws-sdk'); +const StepFunctionWorker = require('../../index.js'); +const createActivity = require('../utils/create-activity'); +const cleanUp = require('../utils/clean-up'); + +const stepFunction = new AWS.StepFunctions(); +const workerName = 'test worker name'; +const stateMachineName = 'test-state-machine-' + Math.floor(Math.random() * 1000); +const activityName = 'test-step-function-worker-' + Math.floor(Math.random() * 1000); + +process.on('uncaughtException', err => { + console.log('uncaughtException', err); +}); +/* +{ + definition: '{"Comment":"An Example State machine using Activity.","StartAt":"FirstState","States":{"FirstState":{"Type":"Task","Resource":"arn:aws:states:eu-central-1:170670752151:activity:test-step-function-worker","TimeoutSeconds":300,"HeartbeatSeconds":60,"Next":"End"}}}', + name: 'test-state-machine', + roleArn: 'arn:aws:iam::170670752151:role/service-role/StatesExecutionRole-eu-central-1' +} +*/ + +const context = {}; + +const before = createActivity.bind(null, {context, activityName, stateMachineName, workerName}); +const after = cleanUp.bind(null, context); + +const sentInput = {foo: 'bar'}; +const sentOutput = {foo2: 'bar2'}; + +const fn = function (event, callback) { + callback(null, sentOutput); +}; + +const fnError = function () { + throw (new Error('custom error')); +}; + +test.before(before); + +test.serial('Step function Activity Worker with 2 consecutive synchronous tasks', t => { + const activityArn = context.activityArn; + const stateMachineArn = context.stateMachineArn; + + const worker = new StepFunctionWorker({ + activityArn, + workerName: workerName + '-fn', + fn + }); + + return new Promise((resolve, reject) => { + let expectedTaskToken; + const params = { + stateMachineArn, + input: JSON.stringify(sentInput) + }; + worker.once('task', task => { + // Task.taskToken + // task.input + t.deepEqual(task.input, sentInput); + t.is(typeof (task.taskToken), 'string'); + expectedTaskToken = task.taskToken; + }); + worker.on('error', reject); + worker.once('success', out => { + t.is(out.taskToken, expectedTaskToken); + + let expectedTaskToken2; + worker.once('task', task => { + // Task.taskToken + // task.input + expectedTaskToken2 = task.taskToken; + }); + + worker.once('success', out => { + t.is(out.taskToken, expectedTaskToken2); + worker.close(() => { + resolve(); + }); + }); + + stepFunction.startExecution(params).promise(); + }); + + stepFunction.startExecution(params).promise(); + }); +}); + +test.serial('Step function Activity Worker with synchronous failing task', t => { + const activityArn = context.activityArn; + const stateMachineArn = context.stateMachineArn; + + const worker = new StepFunctionWorker({ + activityArn, + workerName: workerName + '-fn', + fn: fnError + }); + + return new Promise((resolve, reject) => { + let expectedTaskToken; + const params = { + stateMachineArn, + input: JSON.stringify(sentInput) + }; + worker.once('task', task => { + // Task.taskToken + // task.input + t.deepEqual(task.input, sentInput); + t.is(typeof (task.taskToken), 'string'); + expectedTaskToken = task.taskToken; + }); + worker.once('failure', out => { + t.is(out.taskToken, expectedTaskToken); + t.is(out.error.message, 'custom error'); + worker.close(() => { + resolve(); + }); + }); + worker.once('success', reject); + stepFunction.startExecution(params).promise(); + }); +}); +test.after(after); From 38c75ef4c9b6e47c46fbb318f5cbd245b33c3a3b Mon Sep 17 00:00:00 2001 From: Pierre Colle Date: Sat, 8 Dec 2018 14:29:00 +0100 Subject: [PATCH 2/2] fix: sync functions and sync errors for #10 --- lib/worker.js | 8 ++- package-lock.json | 111 ++++++++++++++-------------------- test/scenarios/sync-fn.js | 123 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 175 insertions(+), 67 deletions(-) create mode 100644 test/scenarios/sync-fn.js diff --git a/lib/worker.js b/lib/worker.js index aaeb9cf..d326a5c 100644 --- a/lib/worker.js +++ b/lib/worker.js @@ -131,7 +131,13 @@ Worker.prototype.close = function (cb) { }; Worker.prototype.execute = function (input, cb, heartbeat) { - this.fn(input, cb, heartbeat); + setImmediate(() => { + try { + this.fn(input, cb, heartbeat); + } catch (err) { + cb(err); + } + }); }; Worker.prototype.succeed = function (res) { diff --git a/package-lock.json b/package-lock.json index 0651f24..0e3a3bb 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1153,6 +1153,11 @@ } } }, + "aws-arn-parser": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/aws-arn-parser/-/aws-arn-parser-1.0.0.tgz", + "integrity": "sha1-ZHvgMMhPH43/nJbZ2PpgNIaehKI=" + }, "aws-sdk": { "version": "2.82.0", "resolved": "https://registry.npmjs.org/aws-sdk/-/aws-sdk-2.82.0.tgz", @@ -2859,6 +2864,12 @@ "array-find-index": "1.0.2" } }, + "cycle": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/cycle/-/cycle-1.0.3.tgz", + "integrity": "sha1-IegLK+hYD5i0aPN5QwZisEbDStI=", + "dev": true + }, "d": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz", @@ -3060,12 +3071,6 @@ "integrity": "sha1-OHHMCmoALow+Wzz38zYmRnXwa50=", "dev": true }, - "diff": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.0.8.tgz", - "integrity": "sha1-NDJ2MI7Jkbe8giZ+1VvBQR+XFmY=", - "dev": true - }, "dir-glob": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz", @@ -5213,18 +5218,6 @@ "parse-domain": "2.0.0" } }, - "glob": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-4.0.6.tgz", - "integrity": "sha1-aVxQvdTi+1xdNwsJHziNNwfikac=", - "dev": true, - "requires": { - "graceful-fs": "3.0.11", - "inherits": "2.0.3", - "minimatch": "1.0.0", - "once": "1.4.0" - } - }, "glob-base": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", @@ -5322,15 +5315,6 @@ "url-parse-lax": "1.0.0" } }, - "graceful-fs": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-3.0.11.tgz", - "integrity": "sha1-dhPHeKGv6mLyXGMKCG1/Osu92Bg=", - "dev": true, - "requires": { - "natives": "1.1.0" - } - }, "handlebars": { "version": "4.0.11", "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz", @@ -6158,6 +6142,12 @@ "isarray": "1.0.0" } }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true + }, "issue-parser": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/issue-parser/-/issue-parser-1.0.3.tgz", @@ -6493,12 +6483,6 @@ "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=", "dev": true }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, "make-dir": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.0.0.tgz", @@ -6725,16 +6709,6 @@ "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==", "dev": true }, - "minimatch": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-1.0.0.tgz", - "integrity": "sha1-4N0hILSeG3JM6NcUxSCCKpQ4V20=", - "dev": true, - "requires": { - "lru-cache": "2.7.3", - "sigmund": "1.0.1" - } - }, "minimist": { "version": "0.0.8", "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", @@ -6869,12 +6843,6 @@ } } }, - "natives": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/natives/-/natives-1.1.0.tgz", - "integrity": "sha1-6f+EFBimsux6SV6TmYT3jxY+bjE=", - "dev": true - }, "natural-compare": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", @@ -8362,12 +8330,6 @@ } } }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", @@ -8611,6 +8573,12 @@ "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, + "stack-trace": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/stack-trace/-/stack-trace-0.0.10.tgz", + "integrity": "sha1-VHxws0fo0ytOEI6hoqFZ5f3eGcA=", + "dev": true + }, "stack-utils": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-1.0.1.tgz", @@ -9245,17 +9213,6 @@ "spdx-expression-parse": "1.0.4" } }, - "vows": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/vows/-/vows-0.8.1.tgz", - "integrity": "sha1-4J6YjOWUygWgjXKrzKNOiNtVkTE=", - "dev": true, - "requires": { - "diff": "1.0.8", - "eyes": "0.1.8", - "glob": "4.0.6" - } - }, "well-known-symbols": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/well-known-symbols/-/well-known-symbols-1.0.0.tgz", @@ -9293,6 +9250,28 @@ "dev": true, "optional": true }, + "winston": { + "version": "2.4.4", + "resolved": "https://registry.npmjs.org/winston/-/winston-2.4.4.tgz", + "integrity": "sha512-NBo2Pepn4hK4V01UfcWcDlmiVTs7VTB1h7bgnB0rgP146bYhMxX0ypCz3lBOfNxCO4Zuek7yeT+y/zM1OfMw4Q==", + "dev": true, + "requires": { + "async": "1.0.0", + "colors": "1.0.3", + "cycle": "1.0.3", + "eyes": "0.1.8", + "isstream": "0.1.2", + "stack-trace": "0.0.10" + }, + "dependencies": { + "async": { + "version": "1.0.0", + "resolved": "http://registry.npmjs.org/async/-/async-1.0.0.tgz", + "integrity": "sha1-+PwEyjoTeErenhZBr5hXjPvWR6k=", + "dev": true + } + } + }, "wordwrap": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", diff --git a/test/scenarios/sync-fn.js b/test/scenarios/sync-fn.js new file mode 100644 index 0000000..83952bf --- /dev/null +++ b/test/scenarios/sync-fn.js @@ -0,0 +1,123 @@ +const test = require('ava').test; +const AWS = require('aws-sdk'); +const StepFunctionWorker = require('../../index.js'); +const createActivity = require('../utils/create-activity'); +const cleanUp = require('../utils/clean-up'); + +const stepFunction = new AWS.StepFunctions(); +const workerName = 'test worker name'; +const stateMachineName = 'test-state-machine-' + Math.floor(Math.random() * 1000); +const activityName = 'test-step-function-worker-' + Math.floor(Math.random() * 1000); + +process.on('uncaughtException', err => { + console.log('uncaughtException', err); +}); +/* +{ + definition: '{"Comment":"An Example State machine using Activity.","StartAt":"FirstState","States":{"FirstState":{"Type":"Task","Resource":"arn:aws:states:eu-central-1:170670752151:activity:test-step-function-worker","TimeoutSeconds":300,"HeartbeatSeconds":60,"Next":"End"}}}', + name: 'test-state-machine', + roleArn: 'arn:aws:iam::170670752151:role/service-role/StatesExecutionRole-eu-central-1' +} +*/ + +const context = {}; + +const before = createActivity.bind(null, {context, activityName, stateMachineName, workerName}); +const after = cleanUp.bind(null, context); + +const sentInput = {foo: 'bar'}; +const sentOutput = {foo2: 'bar2'}; + +const fn = function (event, callback) { + callback(null, sentOutput); +}; + +const fnError = function () { + throw (new Error('custom error')); +}; + +test.before(before); + +test.serial('Step function Activity Worker with 2 consecutive synchronous tasks', t => { + const activityArn = context.activityArn; + const stateMachineArn = context.stateMachineArn; + + const worker = new StepFunctionWorker({ + activityArn, + workerName: workerName + '-fn', + fn + }); + + return new Promise((resolve, reject) => { + let expectedTaskToken; + const params = { + stateMachineArn, + input: JSON.stringify(sentInput) + }; + worker.once('task', task => { + // Task.taskToken + // task.input + t.deepEqual(task.input, sentInput); + t.is(typeof (task.taskToken), 'string'); + expectedTaskToken = task.taskToken; + }); + worker.on('error', reject); + worker.once('success', out => { + t.is(out.taskToken, expectedTaskToken); + + let expectedTaskToken2; + worker.once('task', task => { + // Task.taskToken + // task.input + expectedTaskToken2 = task.taskToken; + }); + + worker.once('success', out => { + t.is(out.taskToken, expectedTaskToken2); + worker.close(() => { + resolve(); + }); + }); + + stepFunction.startExecution(params).promise(); + }); + + stepFunction.startExecution(params).promise(); + }); +}); + +test.serial('Step function Activity Worker with synchronous failing task', t => { + const activityArn = context.activityArn; + const stateMachineArn = context.stateMachineArn; + + const worker = new StepFunctionWorker({ + activityArn, + workerName: workerName + '-fn', + fn: fnError + }); + + return new Promise((resolve, reject) => { + let expectedTaskToken; + const params = { + stateMachineArn, + input: JSON.stringify(sentInput) + }; + worker.once('task', task => { + // Task.taskToken + // task.input + t.deepEqual(task.input, sentInput); + t.is(typeof (task.taskToken), 'string'); + expectedTaskToken = task.taskToken; + }); + worker.once('failure', out => { + t.is(out.taskToken, expectedTaskToken); + t.is(out.error.message, 'custom error'); + worker.close(() => { + resolve(); + }); + }); + worker.once('success', reject); + stepFunction.startExecution(params).promise(); + }); +}); +test.after(after);