Skip to content

Commit b8daf47

Browse files
fix(core): execute timer trigger outside zone (#60392)
This should prevent defer timers from impacting app stability by executing them outside of the zone, similar to other defer triggers. fixes: #60373 PR Close #60392
1 parent c147a0d commit b8daf47

File tree

1 file changed

+10
-6
lines changed

1 file changed

+10
-6
lines changed

packages/core/src/defer/timer_scheduler.ts

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88

99
import {Injector, ɵɵdefineInjectable} from '../di';
1010
import {arrayInsert2, arraySplice} from '../util/array_utils';
11+
import {NgZone} from '../zone';
1112

1213
/**
1314
* Returns a function that captures a provided delay.
@@ -27,8 +28,9 @@ export function onTimer(delay: number) {
2728
*/
2829
export function scheduleTimerTrigger(delay: number, callback: VoidFunction, injector: Injector) {
2930
const scheduler = injector.get(TimerScheduler);
31+
const ngZone = injector.get(NgZone);
3032
const cleanupFn = () => scheduler.remove(callback);
31-
scheduler.add(delay, callback);
33+
scheduler.add(delay, callback, ngZone);
3234
return cleanupFn;
3335
}
3436

@@ -60,10 +62,10 @@ export class TimerScheduler {
6062
// as the shape of the `current` list.
6163
deferred: Array<number | VoidFunction> = [];
6264

63-
add(delay: number, callback: VoidFunction) {
65+
add(delay: number, callback: VoidFunction, ngZone: NgZone) {
6466
const target = this.executingCallbacks ? this.deferred : this.current;
6567
this.addToQueue(target, Date.now() + delay, callback);
66-
this.scheduleTimer();
68+
this.scheduleTimer(ngZone);
6769
}
6870

6971
remove(callback: VoidFunction) {
@@ -117,7 +119,7 @@ export class TimerScheduler {
117119
return index;
118120
}
119121

120-
private scheduleTimer() {
122+
private scheduleTimer(ngZone: NgZone) {
121123
const callback = () => {
122124
this.clearTimeout();
123125

@@ -170,7 +172,7 @@ export class TimerScheduler {
170172
}
171173
this.deferred.length = 0;
172174
}
173-
this.scheduleTimer();
175+
this.scheduleTimer(ngZone);
174176
};
175177

176178
// Avoid running timer callbacks more than once per
@@ -198,7 +200,9 @@ export class TimerScheduler {
198200

199201
const timeout = Math.max(invokeAt - now, FRAME_DURATION_MS);
200202
this.invokeTimerAt = invokeAt;
201-
this.timeoutId = setTimeout(callback, timeout) as unknown as number;
203+
this.timeoutId = ngZone.runOutsideAngular(() => {
204+
return setTimeout(() => ngZone.run(callback), timeout) as unknown as number;
205+
});
202206
}
203207
}
204208
}

0 commit comments

Comments
 (0)