node: fix removing AsyncListener in callback
context._asyncQueue shouldn't be exposed as asyncQueue, as it allows modification of queues already attached to an event. Which is not supposed to happend. Instead context._asyncQueue should be copied.
This commit is contained in:
parent
5757642e91
commit
16a402c0b5
@ -341,7 +341,7 @@
|
|||||||
var item, before, i;
|
var item, before, i;
|
||||||
|
|
||||||
asyncStack.push(asyncQueue);
|
asyncStack.push(asyncQueue);
|
||||||
asyncQueue = queue;
|
asyncQueue = queue.slice();
|
||||||
// Since the async listener callback is required, the number of
|
// Since the async listener callback is required, the number of
|
||||||
// objects in the asyncQueue implies the number of async listeners
|
// objects in the asyncQueue implies the number of async listeners
|
||||||
// there are to be processed.
|
// there are to be processed.
|
||||||
@ -363,12 +363,13 @@
|
|||||||
// Unload one level of the async stack. Returns true if there are
|
// Unload one level of the async stack. Returns true if there are
|
||||||
// still listeners somewhere in the stack.
|
// still listeners somewhere in the stack.
|
||||||
function unloadAsyncQueue(context) {
|
function unloadAsyncQueue(context) {
|
||||||
|
var queue = context._asyncQueue;
|
||||||
var item, after, i;
|
var item, after, i;
|
||||||
|
|
||||||
// Run "after" callbacks.
|
// Run "after" callbacks.
|
||||||
inAsyncTick = true;
|
inAsyncTick = true;
|
||||||
for (i = 0; i < asyncQueue.length; i++) {
|
for (i = 0; i < queue.length; i++) {
|
||||||
item = asyncQueue[i];
|
item = queue[i];
|
||||||
if (!item.callbacks)
|
if (!item.callbacks)
|
||||||
continue;
|
continue;
|
||||||
after = item.callbacks.after;
|
after = item.callbacks.after;
|
||||||
|
45
test/simple/test-asynclistener-remove-add-in-before.js
Normal file
45
test/simple/test-asynclistener-remove-add-in-before.js
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
// Copyright Joyent, Inc. and other Node contributors.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the
|
||||||
|
// "Software"), to deal in the Software without restriction, including
|
||||||
|
// without limitation the rights to use, copy, modify, merge, publish,
|
||||||
|
// distribute, sublicense, and/or sell copies of the Software, and to permit
|
||||||
|
// persons to whom the Software is furnished to do so, subject to the
|
||||||
|
// following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
|
||||||
|
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
|
||||||
|
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||||
|
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
||||||
|
// USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
|
||||||
|
var common = require('../common');
|
||||||
|
var assert = require('assert');
|
||||||
|
var val;
|
||||||
|
var callbacks = {
|
||||||
|
before: function() {
|
||||||
|
process.removeAsyncListener(listener);
|
||||||
|
process.addAsyncListener(listener);
|
||||||
|
},
|
||||||
|
after: function(context, storage) {
|
||||||
|
val = storage;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
var listener = process.addAsyncListener(function() {
|
||||||
|
return 66;
|
||||||
|
}, callbacks);
|
||||||
|
|
||||||
|
process.nextTick(function() {});
|
||||||
|
|
||||||
|
process.on('exit', function(status) {
|
||||||
|
process.removeAsyncListener(listener);
|
||||||
|
assert.equal(status, 0);
|
||||||
|
assert.equal(val, 66);
|
||||||
|
});
|
42
test/simple/test-asynclistener-remove-in-before.js
Normal file
42
test/simple/test-asynclistener-remove-in-before.js
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
// Copyright Joyent, Inc. and other Node contributors.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the
|
||||||
|
// "Software"), to deal in the Software without restriction, including
|
||||||
|
// without limitation the rights to use, copy, modify, merge, publish,
|
||||||
|
// distribute, sublicense, and/or sell copies of the Software, and to permit
|
||||||
|
// persons to whom the Software is furnished to do so, subject to the
|
||||||
|
// following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
|
||||||
|
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
|
||||||
|
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||||
|
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
||||||
|
// USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
|
||||||
|
var common = require('../common');
|
||||||
|
var assert = require('assert');
|
||||||
|
var done = false;
|
||||||
|
var callbacks = {
|
||||||
|
before: function() {
|
||||||
|
process.removeAsyncListener(listener);
|
||||||
|
},
|
||||||
|
after: function() {
|
||||||
|
done = true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
var listener = process.addAsyncListener(function() {}, callbacks);
|
||||||
|
|
||||||
|
process.nextTick(function() {});
|
||||||
|
|
||||||
|
process.on('exit', function(status) {
|
||||||
|
process.removeAsyncListener(listener);
|
||||||
|
assert.equal(status, 0);
|
||||||
|
assert.ok(done);
|
||||||
|
});
|
Loading…
x
Reference in New Issue
Block a user