Skip to content

Commit a71f114

Browse files
JiaLiPassionmhevery
authored andcommittedJul 24, 2020
fix(zone.js): clearTimeout/clearInterval should call on object global (#37858)
Close #37333 `clearTimeout` is patched by `zone.js`, and it finally calls the native delegate of `clearTimeout`, the current implemention only call `clearNative(id)`, but it should call on object `global` like `clearNative.call(global, id)`. Otherwise in some env, it will throw error `clearTimeout called on an object that does not implement interface Window` PR Close #37858
1 parent 253337d commit a71f114

File tree

2 files changed

+22
-1
lines changed

2 files changed

+22
-1
lines changed
 

‎packages/zone.js/lib/common/timers.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ export function patchTimer(window: any, setName: string, cancelName: string, nam
5555
}
5656

5757
function clearTask(task: Task) {
58-
return clearNative!((<TimerOptions>task.data).handleId);
58+
return clearNative!.call(window, (<TimerOptions>task.data).handleId);
5959
}
6060

6161
setNative =

‎packages/zone.js/test/common/setTimeout.spec.ts

+21
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66
* found in the LICENSE file at https://angular.io/license
77
*/
88

9+
import {patchTimer} from '../../lib/common/timers';
910
import {isNode, zoneSymbol} from '../../lib/common/utils';
11+
1012
declare const global: any;
1113
const wtfMock = global.wtfMock;
1214

@@ -56,6 +58,25 @@ describe('setTimeout', function() {
5658
});
5759
});
5860

61+
it('should call native clearTimeout with the correct context', function() {
62+
// since clearTimeout has been patched already, we can not test `clearTimeout` directly
63+
// we will fake another API patch to test
64+
let context: any = null;
65+
const fakeGlobal = {
66+
setTimeout: function() {
67+
return 1;
68+
},
69+
clearTimeout: function(id: number) {
70+
context = this;
71+
}
72+
};
73+
patchTimer(fakeGlobal, 'set', 'clear', 'Timeout')
74+
const cancelId = fakeGlobal.setTimeout();
75+
const m = fakeGlobal.clearTimeout;
76+
m.call({}, cancelId);
77+
expect(context).toBe(fakeGlobal);
78+
});
79+
5980
it('should allow cancelation of fns registered with setTimeout after invocation', function(done) {
6081
const testZone = Zone.current.fork((Zone as any)['wtfZoneSpec']).fork({name: 'TestZone'});
6182
testZone.run(() => {

0 commit comments

Comments
 (0)
Please sign in to comment.