angular/packages/zone.js/lib/common/to-string.ts
Doug Parker 7c1991048b refactor(zone.js): wrap Zone.__load_patch calls in exported functions (#53443)
This removes top-level side effects from each of these files and drops the dependency on global `Zone`, instead allowing it to be provided to each patch as a parameter.

Most of these are pure mechanical transformations. A couple notable files which were somewhat unique:

* `async-test.ts`, `fake-async-test.ts`, and `wtf.ts` had unique IIFE usage and patch `Zone` itself. This removes the IIFE and exports the function instead.
* `jest.ts` and `jasmine.ts` have a unique `jest` global usage which needs to be declared.

PR Close #53443
2024-03-15 18:11:33 -07:00

62 lines
2.2 KiB
TypeScript

/**
* @license
* Copyright Google LLC All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import {ZoneType} from '../zone-impl';
import {zoneSymbol} from './utils';
export function patchToString(Zone: ZoneType): void {
// override Function.prototype.toString to make zone.js patched function
// look like native function
Zone.__load_patch('toString', (global: any) => {
// patch Func.prototype.toString to let them look like native
const originalFunctionToString = Function.prototype.toString;
const ORIGINAL_DELEGATE_SYMBOL = zoneSymbol('OriginalDelegate');
const PROMISE_SYMBOL = zoneSymbol('Promise');
const ERROR_SYMBOL = zoneSymbol('Error');
const newFunctionToString = function toString(this: unknown) {
if (typeof this === 'function') {
const originalDelegate = (this as any)[ORIGINAL_DELEGATE_SYMBOL];
if (originalDelegate) {
if (typeof originalDelegate === 'function') {
return originalFunctionToString.call(originalDelegate);
} else {
return Object.prototype.toString.call(originalDelegate);
}
}
if (this === Promise) {
const nativePromise = global[PROMISE_SYMBOL];
if (nativePromise) {
return originalFunctionToString.call(nativePromise);
}
}
if (this === Error) {
const nativeError = global[ERROR_SYMBOL];
if (nativeError) {
return originalFunctionToString.call(nativeError);
}
}
}
return originalFunctionToString.call(this);
};
(newFunctionToString as any)[ORIGINAL_DELEGATE_SYMBOL] = originalFunctionToString;
Function.prototype.toString = newFunctionToString;
// patch Object.prototype.toString to let them look like native
const originalObjectToString = Object.prototype.toString;
const PROMISE_OBJECT_TO_STRING = '[object Promise]';
Object.prototype.toString = function() {
if (typeof Promise === 'function' && this instanceof Promise) {
return PROMISE_OBJECT_TO_STRING;
}
return originalObjectToString.call(this);
};
});
}