What is a ZoneAwarePromise
Promise is a constructor that at run time in the browser resolves to ZoneAwarePromise()
from zone.js
. Please visit the following link to get more insights.
Angular relies heavily on zone.js to persist an execution context across asynchronous tasks. It's wrapped up in an injectable service called NgZone
.
These Zones wrap up common JS objects meant to run async tasks, which include Promises. This is maintained in a Zone
as a Task, MicroTask, etc.
A ZoneAwarePromise
is still functionally identical to a normal Promise, but internally stays aware of a Zone
's execution context, and the Zone
can know when that Promise completes.
In Angular, this execution context almost always means running change detection.
We use Angular because we can only change model and it will update view automatically for us, based on declarative templates that we provide via metadata.
The way Angular handles this is by intercepting three types of events:
- user events (like clicks),
- clocks (
setTimeout
,setInterval
) and - network (
fetch
, XHR,HttpClient
).
Interally, this is done via zones. When you load setTimeout
, it actually swaps the default setTimeout
implementation with its own implementation, but with the same signature. When you call setTimeout
, you're not even aware that you're using zones.
On a very high-level, it pretty much works like this:
const originalSetTimeout = window.setTimeout
window.setTimeout = (fn, time) => {
originalSetTimeout(() => { fn(); updateView() }, time)
}
It pretty much just executes your function as usual and then calls another thing -- which is used by Angular do update the view.
ZoneAwarePromise
is just a way to use Promise
so that zone is aware of it. You can find implementation details in source code of Zone.js, but that's the gist of it.