0

我正在学习ngZone如何在Angular中工作。我知道它正在对标准异步操作(例如 setTimeout)进行猴子修补。

但谁在打猴子补丁?zone.js 库或 ngZone 中的 Angular 本身?如果您可以在源代码中显示它发生的特定位置,那就太好了。

4

3 回答 3

2

Angular 在 zone.js 中运行区域,zone.js 提供了一个带有修补 API 的范围。

您可以自己使用zone.run(...)Angular 并获得修补 API 的所有效果。

另请参阅https://github.com/angular/zone.js/

修补计时器的代码 https://github.com/angular/zone.js/blob/master/lib/common/timers.ts#L22

于 2017-11-05T15:41:53.170 回答
1

区域库必须在浏览器和服务器端项目中工作。所以它比仅仅修补全局函数要复杂一些。

Zone 不仅修补全局 API,还修补广播的事件对象。修补是通过完成的Zone.__load_patch,您可以看到这些模块中正在修补的内容。

https://github.com/angular/zone.js/blob/master/lib/browser/browser.ts

https://github.com/angular/zone.js/blob/master/lib/node/node.ts

https://github.com/angular/zone.js/blob/master/lib/rxjs/rxjs.ts

这显然不是一个简单的过程。我确信仍有一些区域尚未修补的边缘情况。

于 2017-11-05T15:50:42.117 回答
0

猴子补丁由 Zone.js 完成。在 ng_zone.ts 中,加载了 zone.ts,它创建了根区域以及猴子补丁 API。

NGZone 只是分叉了一个名为“ angular ”的子区域,并在区域规范中提供回调。在这些回调中,它发出在 application_ref.ts 中进一步订阅的事件,并启动更改检测。

Monkey Patching:这是通过使用 2 个参数调用Zone.__load_patch()函数来完成的。第一个参数是猴子补丁 API 的标识符,第二个是补丁函数,它在执行时会用重新定义的版本替换实际的浏览器 API。

现在,这只是冰山一角。实际的魔法是通过调用utils.ts 的patchMethod()来完成的。对于 set/clearTimeOut 情况,这是在此处完成的。

在patchMethod() 中,原始api 保存在局部变量即委托中,并返回保存在timers.ts内的setNative 变量中的相同api。

有关完整的工作流程,您可以参考以下文章。

https://medium.com/reverse-engineering-angular/angular-deep-dive-zone-js-how-does-it-monkey-patches-various-apis-9cc1c7fcc321

于 2018-05-14T17:56:30.530 回答