-
Notifications
You must be signed in to change notification settings - Fork 408
Patch captureStackTrace/prepareStackTrace to ZoneAwareError, patch process.nextTick, fix removeAllListeners bug #516
Conversation
# Conflicts: # dist/long-stack-trace-zone.js # dist/long-stack-trace-zone.min.js # lib/zone-spec/long-stack-trace.ts # test/zone-spec/long-stack-trace-zone.spec.ts
…moveAllListeners
…array. add test cases for prepend listener and once.
@@ -30,6 +30,13 @@ if (shouldPatchGlobalTimers) { | |||
patchTimer(_global, set, clear, 'Immediate'); | |||
} | |||
|
|||
// patch process.nextTick | |||
var nativeNextTick = process.nextTick; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
maybe use const
better
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yes, you are right, thank you.
… should remove all listeners
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've looked through the changes, keep in mind that I'm not directly attached to the project so take the feedback for what it is, I do however believe that a few changes are needed before a merge.
// remove all listeners without eventName | ||
target[EVENT_TASKS] = []; | ||
target[symbol](); | ||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The real removeAllListeners(...)
return this
This wrapper should do the same
https://github.com/nodejs/node/blob/master/lib/events.js#L404
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In typescript I believe you probably want to use either let
or const
as far as I can tell all except the logic in the loop can use const
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
thanks, I will change the var to const.
and about the return this part, it has been handled by https://github.com/angular/zone.js/blob/master/lib/node/events.ts#L14
var eventName = args[0]; | ||
var useCapturing = args[1] || defaultUseCapturing; | ||
var target = self || _global; | ||
var eventTasks = findAllExistingRegisteredTasks(target, eventName, useCapturing, true); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When all all listeners are removed shouldn't all the eventTasks also be chanceled?
I believe we need to look into how to use findAllExistingRegisteredTasks
to get and cancel all eventTasks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the cancelTask will just call the original EventEmitter.removeListener, I think we don't need to cancel it, because when we call targetsymbol https://github.com/angular/zone.js/pull/516/files#diff-f5e084bcb7c43d977d56c3b791bbca2dR287, the EventEmitter.removeAllListeners will do it for us.
and the cancelTask call here is also not necessary either I think, https://github.com/angular/zone.js/blob/master/lib/common/utils.ts#L290
Tested it, seems to fix the issue. When are you planning to merge this? |
…meter cause it is not needed
args[0] = function() { | ||
task.invoke.apply(this, arguments); | ||
}; | ||
setNative.apply(process, args); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't this be setNative.apply(self, args)
using the self
variable coming from patchMethod
? Not actually a problem since nextTick
appears to bind callbacks to global
, but still
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah, we can pass the self form patchMethod to scheduleTask, but here we know it is process , so we can just use process directly, just like patch timer.https://github.com/angular/zone.js/blob/master/lib/common/timers.ts#L30
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we know it's process
?
var nextTick = process.nextTick;
nextTick.call(myObject, function() {
console.log(this); // If `nextTick` passed its context object directly to
// its callback, this would be `myObject`. However,
// with the zone.js patch, this would be `process`
});
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
(I edited my code in the above comment, since it used to make no sense)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, but I can't imagine when we need to call like nextTick.call(myObject, ...), in my understanding we should always call nextTick.call(process, ...)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I also don't think there's ever a good reason to call nextTick
with a different context, especially since with the current implementation (and probably all past/future implementations) it would be useless anyway. But it is allowable to use a different context, and so this could be a problem in the future. With setTimeout
the DOM spec requires you to call it on an object of type Window
or WorkerGlobalScope
(i.e. the global scope)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Anyway, I'd prefer to see it the other way, but it honestly doesn't matter
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But it is allowable to use a different context, and so this could be a problem in the future. With setTimeout the DOM spec requires you to call it on an object of type Window or WorkerGlobalScope (i.e. the global scope)
I didn't know such kind of usage, thank you for the information. in this PR, I'll just keep it this way just to make the coding style be the same with patchTimer. Thanks again.
@@ -83,3 +85,28 @@ if (httpClient && httpClient.ClientRequest) { | |||
} | |||
}; | |||
} | |||
|
|||
function patchNextTick() { | |||
let setNative = null; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It seems weird to use this local variable instead of moving scheduleTask
inside of patchMethod
, but I guess you're trying to limit nested closures?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah, I agree, I just keep the coding style to be the same with timer patch, https://github.com/angular/zone.js/blob/master/lib/common/timers.ts#L17
ZoneAwareError didn't add captureStackTrace method, so it will failed when user call Error.captureStackTrace. for example issue 0.7.1 Breaking Error #515
ZoneAwareError didn't add Error.prepareStackTrace callback, so if user add prepareStackTrace callback to Error, the callback will not be executed. for example issue 0.7.1 Breaking Error #515
https://github.com/v8/v8/wiki/Stack-Trace-API
patch process.nextTick with zone.scheduleMicroTask, so process.nextTick can be in zone, and can be handled by ZoneDelegate task related callback(onScheduleTask/onInvokeTask) Patch process.nextTick() #505
modify a typo, FrameType.trasition->FrameType.transition
fix EventEmitter.removeAllListeners bug Incompatabile with nodejs 6.9.1: makeZoneAwareRemoveAllListeners addes 'undefined' arguments to real removeAllListeners calls #518, when call EventEmitter.removeAllListeners without eventName, should remove all eventListener, and add some test cases for EventEmitter.removeListener/newListener.
update fetch to 2.0.1 in package.json