refactor: ensure zone.js can be built with typescript strict flag (#30993)

As part of FW-1265, the `zone.js` package is made compatible
with the TypeScript `--strict` flag. Read more about the strict flag [here](https://www.typescriptlang.org/docs/handbook/compiler-options.html)

PR Close #30993
This commit is contained in:
Paul Gschwendtner 2019-06-26 10:33:02 +02:00 committed by Miško Hevery
parent 10a1e1974b
commit 60f58bf051
20 changed files with 77 additions and 66 deletions

View File

@ -7,7 +7,7 @@
*/ */
Zone.__load_patch('getUserMedia', (global: any, Zone: any, api: _ZonePrivate) => { Zone.__load_patch('getUserMedia', (global: any, Zone: any, api: _ZonePrivate) => {
function wrapFunctionArgs(func: Function, source?: string): Function { function wrapFunctionArgs(func: Function, source?: string): Function {
return function() { return function(this: unknown) {
const args = Array.prototype.slice.call(arguments); const args = Array.prototype.slice.call(arguments);
const wrappedArgs = api.bindArguments(args, source ? source : (func as any).name); const wrappedArgs = api.bindArguments(args, source ? source : (func as any).name);
return func.apply(this, wrappedArgs); return func.apply(this, wrappedArgs);

View File

@ -115,7 +115,7 @@ Zone.__load_patch('Error', (global: any, Zone: ZoneType, api: _ZonePrivate) => {
* This is ZoneAwareError which processes the stack frame and cleans up extra frames as well as * This is ZoneAwareError which processes the stack frame and cleans up extra frames as well as
* adds zone information to it. * adds zone information to it.
*/ */
function ZoneAwareError(): Error { function ZoneAwareError(this: unknown | typeof NativeError): Error {
// We always have to return native error otherwise the browser console will not work. // We always have to return native error otherwise the browser console will not work.
let error: Error = NativeError.apply(this, arguments); let error: Error = NativeError.apply(this, arguments);
// Save original stack trace // Save original stack trace

View File

@ -112,7 +112,7 @@ export function patchEventTarget(
}; };
// global shared zoneAwareCallback to handle all event callback with capture = false // global shared zoneAwareCallback to handle all event callback with capture = false
const globalZoneAwareCallback = function(event: Event) { const globalZoneAwareCallback = function(this: unknown, event: Event) {
// https://github.com/angular/zone.js/issues/911, in IE, sometimes // https://github.com/angular/zone.js/issues/911, in IE, sometimes
// event will be undefined, so we need to use window.event // event will be undefined, so we need to use window.event
event = event || _global.event; event = event || _global.event;
@ -144,7 +144,7 @@ export function patchEventTarget(
}; };
// global shared zoneAwareCallback to handle all event callback with capture = true // global shared zoneAwareCallback to handle all event callback with capture = true
const globalZoneAwareCaptureCallback = function(event: Event) { const globalZoneAwareCaptureCallback = function(this: unknown, event: Event) {
// https://github.com/angular/zone.js/issues/911, in IE, sometimes // https://github.com/angular/zone.js/issues/911, in IE, sometimes
// event will be undefined, so we need to use window.event // event will be undefined, so we need to use window.event
event = event || _global.event; event = event || _global.event;
@ -330,7 +330,7 @@ export function patchEventTarget(
const makeAddListener = function( const makeAddListener = function(
nativeListener: any, addSource: string, customScheduleFn: any, customCancelFn: any, nativeListener: any, addSource: string, customScheduleFn: any, customCancelFn: any,
returnTarget = false, prepend = false) { returnTarget = false, prepend = false) {
return function() { return function(this: unknown) {
const target = this || _global; const target = this || _global;
const eventName = arguments[0]; const eventName = arguments[0];
let delegate = arguments[1]; let delegate = arguments[1];

View File

@ -54,7 +54,7 @@ Zone.__load_patch('ZoneAwarePromise', (global: any, Zone: ZoneType, api: _ZonePr
const UNHANDLED_PROMISE_REJECTION_HANDLER_SYMBOL = __symbol__('unhandledPromiseRejectionHandler'); const UNHANDLED_PROMISE_REJECTION_HANDLER_SYMBOL = __symbol__('unhandledPromiseRejectionHandler');
function handleUnhandledRejection(e: any) { function handleUnhandledRejection(this: unknown, e: any) {
api.onUnhandledError(e); api.onUnhandledError(e);
try { try {
const handler = (Zone as any)[UNHANDLED_PROMISE_REJECTION_HANDLER_SYMBOL]; const handler = (Zone as any)[UNHANDLED_PROMISE_REJECTION_HANDLER_SYMBOL];
@ -198,7 +198,7 @@ Zone.__load_patch('ZoneAwarePromise', (global: any, Zone: ZoneType, api: _ZonePr
} }
const REJECTION_HANDLED_HANDLER = __symbol__('rejectionHandledHandler'); const REJECTION_HANDLED_HANDLER = __symbol__('rejectionHandledHandler');
function clearRejectedNoCatch(promise: ZoneAwarePromise<any>): void { function clearRejectedNoCatch(this: unknown, promise: ZoneAwarePromise<any>): void {
if ((promise as any)[symbolState] === REJECTED_NO_CATCH) { if ((promise as any)[symbolState] === REJECTED_NO_CATCH) {
// if the promise is rejected no catch status // if the promise is rejected no catch status
// and queue.length > 0, means there is a error handler // and queue.length > 0, means there is a error handler
@ -453,7 +453,7 @@ Zone.__load_patch('ZoneAwarePromise', (global: any, Zone: ZoneType, api: _ZonePr
api.patchThen = patchThen; api.patchThen = patchThen;
function zoneify(fn: Function) { function zoneify(fn: Function) {
return function() { return function(this: unknown) {
let resultPromise = fn.apply(this, arguments); let resultPromise = fn.apply(this, arguments);
if (resultPromise instanceof ZoneAwarePromise) { if (resultPromise instanceof ZoneAwarePromise) {
return resultPromise; return resultPromise;

View File

@ -29,7 +29,7 @@ export function patchTimer(window: any, setName: string, cancelName: string, nam
function scheduleTask(task: Task) { function scheduleTask(task: Task) {
const data = <TimerOptions>task.data; const data = <TimerOptions>task.data;
function timer() { function timer(this: unknown) {
try { try {
task.invoke.apply(this, arguments); task.invoke.apply(this, arguments);
} finally { } finally {

View File

@ -16,9 +16,9 @@ Zone.__load_patch('toString', (global: any) => {
const ORIGINAL_DELEGATE_SYMBOL = zoneSymbol('OriginalDelegate'); const ORIGINAL_DELEGATE_SYMBOL = zoneSymbol('OriginalDelegate');
const PROMISE_SYMBOL = zoneSymbol('Promise'); const PROMISE_SYMBOL = zoneSymbol('Promise');
const ERROR_SYMBOL = zoneSymbol('Error'); const ERROR_SYMBOL = zoneSymbol('Error');
const newFunctionToString = function toString() { const newFunctionToString = function toString(this: unknown) {
if (typeof this === 'function') { if (typeof this === 'function') {
const originalDelegate = this[ORIGINAL_DELEGATE_SYMBOL]; const originalDelegate = (this as any)[ORIGINAL_DELEGATE_SYMBOL];
if (originalDelegate) { if (originalDelegate) {
if (typeof originalDelegate === 'function') { if (typeof originalDelegate === 'function') {
return originalFunctionToString.call(originalDelegate); return originalFunctionToString.call(originalDelegate);

View File

@ -80,7 +80,7 @@ export function patchPrototype(prototype: any, fnNames: string[]) {
continue; continue;
} }
prototype[name] = ((delegate: Function) => { prototype[name] = ((delegate: Function) => {
const patched: any = function() { const patched: any = function(this: unknown) {
return delegate.apply(this, bindArguments(<any>arguments, source + '.' + name)); return delegate.apply(this, bindArguments(<any>arguments, source + '.' + name));
}; };
attachOriginToPatched(patched, delegate); attachOriginToPatched(patched, delegate);
@ -123,7 +123,7 @@ export const isMix: boolean = typeof _global.process !== 'undefined' &&
const zoneSymbolEventNames: {[eventName: string]: string} = {}; const zoneSymbolEventNames: {[eventName: string]: string} = {};
const wrapFn = function(event: Event) { const wrapFn = function(this: unknown, event: Event) {
// https://github.com/angular/zone.js/issues/911, in IE, sometimes // https://github.com/angular/zone.js/issues/911, in IE, sometimes
// event will be undefined, so we need to use window.event // event will be undefined, so we need to use window.event
event = event || _global.event; event = event || _global.event;
@ -197,7 +197,7 @@ export function patchProperty(obj: any, prop: string, prototype?: any) {
eventNameSymbol = zoneSymbolEventNames[eventName] = zoneSymbol('ON_PROPERTY' + eventName); eventNameSymbol = zoneSymbolEventNames[eventName] = zoneSymbol('ON_PROPERTY' + eventName);
} }
desc.set = function(newValue) { desc.set = function(this: EventSource, newValue) {
// in some of windows's onproperty callback, this is undefined // in some of windows's onproperty callback, this is undefined
// so we need to check it // so we need to check it
let target = this; let target = this;
@ -207,7 +207,7 @@ export function patchProperty(obj: any, prop: string, prototype?: any) {
if (!target) { if (!target) {
return; return;
} }
let previousValue = target[eventNameSymbol]; let previousValue = (target as any)[eventNameSymbol];
if (previousValue) { if (previousValue) {
target.removeEventListener(eventName, wrapFn); target.removeEventListener(eventName, wrapFn);
} }
@ -219,10 +219,10 @@ export function patchProperty(obj: any, prop: string, prototype?: any) {
} }
if (typeof newValue === 'function') { if (typeof newValue === 'function') {
target[eventNameSymbol] = newValue; (target as any)[eventNameSymbol] = newValue;
target.addEventListener(eventName, wrapFn, false); target.addEventListener(eventName, wrapFn, false);
} else { } else {
target[eventNameSymbol] = null; (target as any)[eventNameSymbol] = null;
} }
}; };
@ -238,7 +238,7 @@ export function patchProperty(obj: any, prop: string, prototype?: any) {
if (!target) { if (!target) {
return null; return null;
} }
const listener = target[eventNameSymbol]; const listener = (target as any)[eventNameSymbol];
if (listener) { if (listener) {
return listener; return listener;
} else if (originalDescGet) { } else if (originalDescGet) {
@ -251,8 +251,8 @@ export function patchProperty(obj: any, prop: string, prototype?: any) {
let value = originalDescGet && originalDescGet.call(this); let value = originalDescGet && originalDescGet.call(this);
if (value) { if (value) {
desc !.set !.call(this, value); desc !.set !.call(this, value);
if (typeof target[REMOVE_ATTRIBUTE] === 'function') { if (typeof(target as any)[REMOVE_ATTRIBUTE] === 'function') {
target.removeAttribute(prop); (target as any).removeAttribute(prop);
} }
return value; return value;
} }

View File

@ -42,7 +42,7 @@ Zone.__load_patch('jsonp', (global: any, Zone: ZoneType, api: _ZonePrivate) => {
configurable: true, configurable: true,
enumerable: true, enumerable: true,
get: function() { get: function() {
return function() { return function(this: unknown) {
const task = global[api.symbol('jsonpTask')]; const task = global[api.symbol('jsonpTask')];
const target = this ? this : global; const target = this ? this : global;
const delegate = global[api.symbol(`jsonp${methodName}callback`)]; const delegate = global[api.symbol(`jsonp${methodName}callback`)];

View File

@ -13,7 +13,7 @@
const __extends = function(d: any, b: any) { const __extends = function(d: any, b: any) {
for (const p in b) for (const p in b)
if (b.hasOwnProperty(p)) d[p] = b[p]; if (b.hasOwnProperty(p)) d[p] = b[p];
function __() { this.constructor = d; } function __(this: Object) { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : ((__.prototype = b.prototype), new (__ as any)()); d.prototype = b === null ? Object.create(b) : ((__.prototype = b.prototype), new (__ as any)());
}; };
// Patch jasmine's describe/it/beforeEach/afterEach functions so test code always runs // Patch jasmine's describe/it/beforeEach/afterEach functions so test code always runs
@ -149,13 +149,16 @@
* synchronous-only zone. * synchronous-only zone.
*/ */
function wrapDescribeInZone(describeBody: Function): Function { function wrapDescribeInZone(describeBody: Function): Function {
return function() { return syncZone.run(describeBody, this, (arguments as any) as any[]); }; return function(this: unknown) {
return syncZone.run(describeBody, this, (arguments as any) as any[]);
};
} }
function runInTestZone(testBody: Function, applyThis: any, queueRunner: any, done?: Function) { function runInTestZone(
testBody: Function, applyThis: any, queueRunner: QueueRunner, done?: Function) {
const isClockInstalled = !!(jasmine as any)[symbol('clockInstalled')]; const isClockInstalled = !!(jasmine as any)[symbol('clockInstalled')];
const testProxyZoneSpec = queueRunner.testProxyZoneSpec; const testProxyZoneSpec = queueRunner.testProxyZoneSpec !;
const testProxyZone = queueRunner.testProxyZone; const testProxyZone = queueRunner.testProxyZone !;
let lastDelegate; let lastDelegate;
if (isClockInstalled && enableAutoFakeAsyncWhenClockPatched) { if (isClockInstalled && enableAutoFakeAsyncWhenClockPatched) {
// auto run a fakeAsync // auto run a fakeAsync
@ -180,12 +183,16 @@
// The `done` callback is only passed through if the function expects at least one argument. // The `done` callback is only passed through if the function expects at least one argument.
// Note we have to make a function with correct number of arguments, otherwise jasmine will // Note we have to make a function with correct number of arguments, otherwise jasmine will
// think that all functions are sync or async. // think that all functions are sync or async.
return (testBody && (testBody.length ? function(done: Function) { return (testBody && (testBody.length ? function(this: QueueRunnerUserContext, done: Function) {
return runInTestZone(testBody, this, this.queueRunner, done); return runInTestZone(testBody, this, this.queueRunner !, done);
} : function() { return runInTestZone(testBody, this, this.queueRunner); })); } : function(this: QueueRunnerUserContext) {
return runInTestZone(testBody, this, this.queueRunner !);
}));
} }
interface QueueRunner { interface QueueRunner {
execute(): void; execute(): void;
testProxyZoneSpec: ZoneSpec|null;
testProxyZone: Zone|null;
} }
interface QueueRunnerAttrs { interface QueueRunnerAttrs {
queueableFns: {fn: Function}[]; queueableFns: {fn: Function}[];
@ -194,16 +201,16 @@
fail: () => void; fail: () => void;
onComplete: () => void; onComplete: () => void;
onException: (error: any) => void; onException: (error: any) => void;
userContext: any; userContext: QueueRunnerUserContext;
timeout: {setTimeout: Function; clearTimeout: Function}; timeout: {setTimeout: Function; clearTimeout: Function};
} }
type QueueRunnerUserContext = {queueRunner?: QueueRunner};
const QueueRunner = (jasmine as any).QueueRunner as { const QueueRunner = (jasmine as any).QueueRunner as {
new (attrs: QueueRunnerAttrs): QueueRunner; new (attrs: QueueRunnerAttrs): QueueRunner;
}; };
(jasmine as any).QueueRunner = (function(_super) { (jasmine as any).QueueRunner = (function(_super) {
__extends(ZoneQueueRunner, _super); __extends(ZoneQueueRunner, _super);
function ZoneQueueRunner(attrs: QueueRunnerAttrs) { function ZoneQueueRunner(this: QueueRunner, attrs: QueueRunnerAttrs) {
if (attrs.onComplete) { if (attrs.onComplete) {
attrs.onComplete = (fn => () => { attrs.onComplete = (fn => () => {
// All functions are done, clear the test zone. // All functions are done, clear the test zone.
@ -239,7 +246,7 @@
// patch attrs.onException // patch attrs.onException
const onException = attrs.onException; const onException = attrs.onException;
attrs.onException = function(error: any) { attrs.onException = function(this: undefined|QueueRunner, error: any) {
if (error && if (error &&
error.message === error.message ===
'Timeout - Async callback was not invoked within timeout specified by jasmine.DEFAULT_TIMEOUT_INTERVAL.') { 'Timeout - Async callback was not invoked within timeout specified by jasmine.DEFAULT_TIMEOUT_INTERVAL.') {

View File

@ -67,7 +67,7 @@
function wrapDescribeInZone(args: IArguments): any[] { function wrapDescribeInZone(args: IArguments): any[] {
const syncTest: any = function(fn: Function) { const syncTest: any = function(fn: Function) {
return function() { return syncZone.run(fn, this, arguments as any as any[]); }; return function(this: unknown) { return syncZone.run(fn, this, arguments as any as any[]); };
}; };
return modifyArguments(args, syncTest); return modifyArguments(args, syncTest);
@ -75,11 +75,11 @@
function wrapTestInZone(args: IArguments): any[] { function wrapTestInZone(args: IArguments): any[] {
const asyncTest = function(fn: Function) { const asyncTest = function(fn: Function) {
return function(done: Function) { return testZone !.run(fn, this, [done]); }; return function(this: unknown, done: Function) { return testZone !.run(fn, this, [done]); };
}; };
const syncTest: any = function(fn: Function) { const syncTest: any = function(fn: Function) {
return function() { return testZone !.run(fn, this); }; return function(this: unknown) { return testZone !.run(fn, this); };
}; };
return modifyArguments(args, syncTest, asyncTest); return modifyArguments(args, syncTest, asyncTest);
@ -87,11 +87,11 @@
function wrapSuiteInZone(args: IArguments): any[] { function wrapSuiteInZone(args: IArguments): any[] {
const asyncTest = function(fn: Function) { const asyncTest = function(fn: Function) {
return function(done: Function) { return suiteZone.run(fn, this, [done]); }; return function(this: unknown, done: Function) { return suiteZone.run(fn, this, [done]); };
}; };
const syncTest: any = function(fn: Function) { const syncTest: any = function(fn: Function) {
return function() { return suiteZone.run(fn, this); }; return function(this: unknown) { return suiteZone.run(fn, this); };
}; };
return modifyArguments(args, syncTest, asyncTest); return modifyArguments(args, syncTest, asyncTest);

View File

@ -8,6 +8,10 @@
import {Observable, Subscriber, Subscription} from 'rxjs'; import {Observable, Subscriber, Subscription} from 'rxjs';
type ZoneSubscriberContext = {
_zone: Zone
} & Subscriber<any>;
(Zone as any).__load_patch('rxjs', (global: any, Zone: ZoneType, api: _ZonePrivate) => { (Zone as any).__load_patch('rxjs', (global: any, Zone: ZoneType, api: _ZonePrivate) => {
const symbol: (symbolString: string) => string = (Zone as any).__symbol__; const symbol: (symbolString: string) => string = (Zone as any).__symbol__;
const nextSource = 'rxjs.Subscriber.next'; const nextSource = 'rxjs.Subscriber.next';
@ -46,14 +50,14 @@ import {Observable, Subscriber, Subscription} from 'rxjs';
}, },
set: function(this: Observable<any>, subscribe: any) { set: function(this: Observable<any>, subscribe: any) {
(this as any)._zone = Zone.current; (this as any)._zone = Zone.current;
(this as any)._zoneSubscribe = function() { (this as any)._zoneSubscribe = function(this: ZoneSubscriberContext) {
if (this._zone && this._zone !== Zone.current) { if (this._zone && this._zone !== Zone.current) {
const tearDown = this._zone.run(subscribe, this, arguments); const tearDown = this._zone.run(subscribe, this, arguments as any);
if (tearDown && typeof tearDown === 'function') { if (tearDown && typeof tearDown === 'function') {
const zone = this._zone; const zone = this._zone;
return function() { return function(this: ZoneSubscriberContext) {
if (zone !== Zone.current) { if (zone !== Zone.current) {
return zone.run(tearDown, this, arguments); return zone.run(tearDown, this, arguments as any);
} }
return tearDown.apply(this, arguments); return tearDown.apply(this, arguments);
}; };
@ -136,40 +140,40 @@ import {Observable, Subscriber, Subscription} from 'rxjs';
// patch Subscriber.next to make sure it run // patch Subscriber.next to make sure it run
// into SubscriptionZone // into SubscriptionZone
Subscriber.prototype.next = function() { Subscriber.prototype.next = function(this: ZoneSubscriberContext) {
const currentZone = Zone.current; const currentZone = Zone.current;
const subscriptionZone = this._zone; const subscriptionZone = this._zone;
// for performance concern, check Zone.current // for performance concern, check Zone.current
// equal with this._zone(SubscriptionZone) or not // equal with this._zone(SubscriptionZone) or not
if (subscriptionZone && subscriptionZone !== currentZone) { if (subscriptionZone && subscriptionZone !== currentZone) {
return subscriptionZone.run(next, this, arguments, nextSource); return subscriptionZone.run(next, this, arguments as any, nextSource);
} else { } else {
return next.apply(this, arguments as any); return next.apply(this, arguments as any);
} }
}; };
Subscriber.prototype.error = function() { Subscriber.prototype.error = function(this: ZoneSubscriberContext) {
const currentZone = Zone.current; const currentZone = Zone.current;
const subscriptionZone = this._zone; const subscriptionZone = this._zone;
// for performance concern, check Zone.current // for performance concern, check Zone.current
// equal with this._zone(SubscriptionZone) or not // equal with this._zone(SubscriptionZone) or not
if (subscriptionZone && subscriptionZone !== currentZone) { if (subscriptionZone && subscriptionZone !== currentZone) {
return subscriptionZone.run(error, this, arguments, errorSource); return subscriptionZone.run(error, this, arguments as any, errorSource);
} else { } else {
return error.apply(this, arguments as any); return error.apply(this, arguments as any);
} }
}; };
Subscriber.prototype.complete = function() { Subscriber.prototype.complete = function(this: ZoneSubscriberContext) {
const currentZone = Zone.current; const currentZone = Zone.current;
const subscriptionZone = this._zone; const subscriptionZone = this._zone;
// for performance concern, check Zone.current // for performance concern, check Zone.current
// equal with this._zone(SubscriptionZone) or not // equal with this._zone(SubscriptionZone) or not
if (subscriptionZone && subscriptionZone !== currentZone) { if (subscriptionZone && subscriptionZone !== currentZone) {
return subscriptionZone.run(complete, this, arguments, completeSource); return subscriptionZone.run(complete, this, arguments as any, completeSource);
} else { } else {
return complete.call(this); return complete.call(this);
} }

View File

@ -17,7 +17,7 @@ Zone.__load_patch('asynctest', (global: any, Zone: ZoneType, api: _ZonePrivate)
// function when asynchronous activity is finished. // function when asynchronous activity is finished.
if (global.jasmine) { if (global.jasmine) {
// Not using an arrow function to preserve context passed from call site // Not using an arrow function to preserve context passed from call site
return function(done: any) { return function(this: unknown, done: any) {
if (!done) { if (!done) {
// if we run beforeEach in @angular/core/testing/testing_internal then we get no done // if we run beforeEach in @angular/core/testing/testing_internal then we get no done
// fake it here and assume sync. // fake it here and assume sync.
@ -37,7 +37,7 @@ Zone.__load_patch('asynctest', (global: any, Zone: ZoneType, api: _ZonePrivate)
// is finished. This will be correctly consumed by the Mocha framework with // is finished. This will be correctly consumed by the Mocha framework with
// it('...', async(myFn)); or can be used in a custom framework. // it('...', async(myFn)); or can be used in a custom framework.
// Not using an arrow function to preserve context passed from call site // Not using an arrow function to preserve context passed from call site
return function() { return function(this: unknown) {
return new Promise<void>((finishCallback, failCallback) => { return new Promise<void>((finishCallback, failCallback) => {
runInTestZone(fn, this, finishCallback, failCallback); runInTestZone(fn, this, finishCallback, failCallback);
}); });
@ -96,4 +96,4 @@ Zone.__load_patch('asynctest', (global: any, Zone: ZoneType, api: _ZonePrivate)
}); });
return Zone.current.runGuarded(fn, context); return Zone.current.runGuarded(fn, context);
} }
}); });

View File

@ -52,7 +52,7 @@ Zone.__load_patch('fakeasync', (global: any, Zone: ZoneType, api: _ZonePrivate)
*/ */
function fakeAsync(fn: Function): (...args: any[]) => any { function fakeAsync(fn: Function): (...args: any[]) => any {
// Not using an arrow function to preserve context passed from call site // Not using an arrow function to preserve context passed from call site
return function(...args: any[]) { return function(this: unknown, ...args: any[]) {
const proxyZoneSpec = ProxyZoneSpec.assertPresent(); const proxyZoneSpec = ProxyZoneSpec.assertPresent();
if (Zone.current.get('FakeAsyncTestZoneSpec')) { if (Zone.current.get('FakeAsyncTestZoneSpec')) {
throw new Error('fakeAsync() calls can not be nested'); throw new Error('fakeAsync() calls can not be nested');
@ -150,4 +150,4 @@ Zone.__load_patch('fakeasync', (global: any, Zone: ZoneType, api: _ZonePrivate)
function flushMicrotasks(): void { _getFakeAsyncZoneSpec().flushMicrotasks(); } function flushMicrotasks(): void { _getFakeAsyncZoneSpec().flushMicrotasks(); }
(Zone as any)[api.symbol('fakeAsyncTest')] = { (Zone as any)[api.symbol('fakeAsyncTest')] = {
resetFakeAsyncZone, flushMicrotasks, discardPeriodicTasks, tick, flush, fakeAsync}; resetFakeAsyncZone, flushMicrotasks, discardPeriodicTasks, tick, flush, fakeAsync};
}); });

View File

@ -45,7 +45,7 @@ Zone.__load_patch('promisefortest', (global: any, Zone: ZoneType, api: _ZonePriv
oriThen = (Promise as any)[Zone.__symbol__('ZonePromiseThen')] = Promise.prototype.then; oriThen = (Promise as any)[Zone.__symbol__('ZonePromiseThen')] = Promise.prototype.then;
Promise.prototype.then = function() { Promise.prototype.then = function() {
const chained = oriThen.apply(this, arguments); const chained = oriThen.apply(this, arguments);
if (this[symbolState] === UNRESOLVED) { if ((this as any)[symbolState] === UNRESOLVED) {
// parent promise is unresolved. // parent promise is unresolved.
const asyncTestZoneSpec = Zone.current.get('AsyncTestZoneSpec'); const asyncTestZoneSpec = Zone.current.get('AsyncTestZoneSpec');
if (asyncTestZoneSpec) { if (asyncTestZoneSpec) {
@ -65,4 +65,4 @@ Zone.__load_patch('promisefortest', (global: any, Zone: ZoneType, api: _ZonePriv
(Promise as any)[Zone.__symbol__('ZonePromiseThen')] = undefined; (Promise as any)[Zone.__symbol__('ZonePromiseThen')] = undefined;
} }
}; };
}); });

View File

@ -78,7 +78,9 @@ function renderLongStackTrace(frames: LongStackTrace[], stack?: string): string
return longTrace.join(NEWLINE); return longTrace.join(NEWLINE);
} }
(Zone as any)['longStackTraceZoneSpec'] = <ZoneSpec>{ type LongStackTraceZoneSpec = ZoneSpec & {longStackTraceLimit: number};
(Zone as any)['longStackTraceZoneSpec'] = <LongStackTraceZoneSpec>{
name: 'long-stack-trace', name: 'long-stack-trace',
longStackTraceLimit: 10, // Max number of task to keep the stack trace for. longStackTraceLimit: 10, // Max number of task to keep the stack trace for.
// add a getLongStackTrace method in spec to // add a getLongStackTrace method in spec to

View File

@ -781,8 +781,8 @@ const Zone: ZoneType = (function(global: any) {
} }
const _callback = this._zoneDelegate.intercept(this, callback, source); const _callback = this._zoneDelegate.intercept(this, callback, source);
const zone: Zone = this; const zone: Zone = this;
return function() { return function(this: unknown) {
return zone.runGuarded(_callback, (this as any), <any>arguments, source); return zone.runGuarded(_callback, this, <any>arguments, source);
} as any as T; } as any as T;
} }

View File

@ -13,7 +13,8 @@ const detectTask = Zone.current.scheduleMacroTask('detectTask', noop, undefined,
const originalTransitionTo = detectTask.constructor.prototype._transitionTo; const originalTransitionTo = detectTask.constructor.prototype._transitionTo;
// patch _transitionTo of ZoneTask to add log for test // patch _transitionTo of ZoneTask to add log for test
const logTransitionTo: Function = function( const logTransitionTo: Function = function(
toState: TaskState, fromState1: TaskState, fromState2?: TaskState) { this: Task&{_state: TaskState}, toState: TaskState, fromState1: TaskState,
fromState2?: TaskState) {
log.push({ log.push({
zone: Zone.current.name, zone: Zone.current.name,
taskZone: this.zone && this.zone.name, taskZone: this.zone && this.zone.name,
@ -24,7 +25,7 @@ const logTransitionTo: Function = function(
}; };
function testFnWithLoggedTransitionTo(testFn: Function) { function testFnWithLoggedTransitionTo(testFn: Function) {
return function() { return function(this: unknown) {
detectTask.constructor.prototype._transitionTo = logTransitionTo; detectTask.constructor.prototype._transitionTo = logTransitionTo;
testFn.apply(this, arguments); testFn.apply(this, arguments);
detectTask.constructor.prototype._transitionTo = originalTransitionTo; detectTask.constructor.prototype._transitionTo = originalTransitionTo;

View File

@ -86,7 +86,7 @@ export function isSupportSetErrorStack() {
(isSupportSetErrorStack as any).message = 'supportSetErrorStack'; (isSupportSetErrorStack as any).message = 'supportSetErrorStack';
export function asyncTest(testFn: Function, zone: Zone = Zone.current) { export function asyncTest(this: unknown, testFn: Function, zone: Zone = Zone.current) {
const AsyncTestZoneSpec = (Zone as any)['AsyncTestZoneSpec']; const AsyncTestZoneSpec = (Zone as any)['AsyncTestZoneSpec'];
return (done: Function) => { return (done: Function) => {
let asyncTestZone: Zone = let asyncTestZone: Zone =

View File

@ -247,9 +247,9 @@ describe('AsyncTestZoneSpec', function() {
const asyncTest: any = (Zone as any)[Zone.__symbol__('asyncTest')]; const asyncTest: any = (Zone as any)[Zone.__symbol__('asyncTest')];
function wrapAsyncTest(fn: Function, doneFn?: Function) { function wrapAsyncTest(fn: Function, doneFn?: Function) {
return function(done: Function) { return function(this: unknown, done: Function) {
const asyncWrapper = asyncTest(fn); const asyncWrapper = asyncTest(fn);
return asyncWrapper.apply(this, [function() { return asyncWrapper.apply(this, [function(this: unknown) {
if (doneFn) { if (doneFn) {
doneFn(); doneFn();
} }

View File

@ -2,9 +2,6 @@
"compilerOptions": { "compilerOptions": {
"module": "commonjs", "module": "commonjs",
"target": "es5", "target": "es5",
"noImplicitAny": true,
"noImplicitReturns": false,
"noImplicitThis": false,
"outDir": "build", "outDir": "build",
"inlineSourceMap": true, "inlineSourceMap": true,
"inlineSources": true, "inlineSources": true,