1'use strict'; 2 3const common = require('../common'); 4const assert = require('assert'); 5const domain = require('domain'); 6 7// setImmediate should run clear its queued cbs once per event loop turn 8// but immediates queued while processing the current queue should happen 9// on the next turn of the event loop. 10 11// In addition, if any setImmediate throws, the rest of the queue should 12// be processed after all error handling is resolved, but that queue 13// should not include any setImmediate calls scheduled after the 14// processing of the queue started. 15 16let threw = false; 17let stage = -1; 18 19const QUEUE = 10; 20 21const errObj = { 22 name: 'Error', 23 message: 'setImmediate Err' 24}; 25 26process.once('uncaughtException', common.mustCall((err, errorOrigin) => { 27 assert.strictEqual(errorOrigin, 'uncaughtException'); 28 assert.strictEqual(stage, 0); 29 common.expectsError(errObj)(err); 30})); 31 32const d1 = domain.create(); 33d1.once('error', common.expectsError(errObj)); 34d1.once('error', () => assert.strictEqual(stage, 0)); 35 36const run = common.mustCall((callStage) => { 37 assert(callStage >= stage); 38 stage = callStage; 39 if (threw) 40 return; 41 42 setImmediate(run, 2); 43}, QUEUE * 3); 44 45for (let i = 0; i < QUEUE; i++) 46 setImmediate(run, 0); 47setImmediate(() => { 48 threw = true; 49 process.nextTick(() => assert.strictEqual(stage, 1)); 50 throw new Error('setImmediate Err'); 51}); 52d1.run(() => setImmediate(() => { 53 throw new Error('setImmediate Err'); 54})); 55for (let i = 0; i < QUEUE; i++) 56 setImmediate(run, 1); 57