| Index: sdk/lib/async/zone.dart
|
| diff --git a/sdk/lib/async/zone.dart b/sdk/lib/async/zone.dart
|
| index 541a66f1a52ec3754e4f4e43c2764d91ab628e8e..1f2993d2f5413689f361b52c13832173370be43b 100644
|
| --- a/sdk/lib/async/zone.dart
|
| +++ b/sdk/lib/async/zone.dart
|
| @@ -21,6 +21,8 @@ typedef ZoneUnaryCallback RegisterUnaryCallbackHandler(
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg));
|
| typedef ZoneBinaryCallback RegisterBinaryCallbackHandler(
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg1, arg2));
|
| +typedef AsyncError ErrorCallbackHandler(Zone self, ZoneDelegate parent,
|
| + Zone zone, Object error, StackTrace stackTrace);
|
| typedef void ScheduleMicrotaskHandler(
|
| Zone self, ZoneDelegate parent, Zone zone, f());
|
| typedef Timer CreateTimerHandler(
|
| @@ -34,6 +36,16 @@ typedef Zone ForkHandler(Zone self, ZoneDelegate parent, Zone zone,
|
| ZoneSpecification specification,
|
| Map zoneValues);
|
|
|
| +/// Pair of error and stack trace. Returned by [Zone.errorCallback].
|
| +class AsyncError implements Error {
|
| + final error;
|
| + final StackTrace stackTrace;
|
| +
|
| + AsyncError(this.error, this.stackTrace);
|
| + String toString() => error.toString();
|
| +}
|
| +
|
| +
|
| class _ZoneFunction {
|
| final _Zone zone;
|
| final Function function;
|
| @@ -77,6 +89,8 @@ abstract class ZoneSpecification {
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg)),
|
| ZoneBinaryCallback registerBinaryCallback(
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg1, arg2)),
|
| + AsyncError errorCallback(Zone self, ZoneDelegate parent, Zone zone,
|
| + Object error, StackTrace stackTrace),
|
| void scheduleMicrotask(
|
| Zone self, ZoneDelegate parent, Zone zone, f()),
|
| Timer createTimer(Zone self, ZoneDelegate parent, Zone zone,
|
| @@ -106,6 +120,8 @@ abstract class ZoneSpecification {
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg)): null,
|
| ZoneBinaryCallback registerBinaryCallback(
|
| Zone self, ZoneDelegate parent, Zone zone, f(arg1, arg2)): null,
|
| + AsyncError errorCallback(Zone self, ZoneDelegate parent, Zone zone,
|
| + Object error, StackTrace stackTrace),
|
| void scheduleMicrotask(
|
| Zone self, ZoneDelegate parent, Zone zone, f()): null,
|
| Timer createTimer(Zone self, ZoneDelegate parent, Zone zone,
|
| @@ -133,6 +149,9 @@ abstract class ZoneSpecification {
|
| registerBinaryCallback: registerBinaryCallback != null
|
| ? registerBinaryCallback
|
| : other.registerBinaryCallback,
|
| + errorCallback: errorCallback != null
|
| + ? errorCallback
|
| + : other.errorCallback,
|
| scheduleMicrotask: scheduleMicrotask != null
|
| ? scheduleMicrotask
|
| : other.scheduleMicrotask,
|
| @@ -151,6 +170,7 @@ abstract class ZoneSpecification {
|
| RegisterCallbackHandler get registerCallback;
|
| RegisterUnaryCallbackHandler get registerUnaryCallback;
|
| RegisterBinaryCallbackHandler get registerBinaryCallback;
|
| + ErrorCallbackHandler get errorCallback;
|
| ScheduleMicrotaskHandler get scheduleMicrotask;
|
| CreateTimerHandler get createTimer;
|
| CreatePeriodicTimerHandler get createPeriodicTimer;
|
| @@ -174,6 +194,7 @@ class _ZoneSpecification implements ZoneSpecification {
|
| this.registerCallback: null,
|
| this.registerUnaryCallback: null,
|
| this.registerBinaryCallback: null,
|
| + this.errorCallback: null,
|
| this.scheduleMicrotask: null,
|
| this.createTimer: null,
|
| this.createPeriodicTimer: null,
|
| @@ -189,6 +210,7 @@ class _ZoneSpecification implements ZoneSpecification {
|
| final /*RegisterCallbackHandler*/ registerCallback;
|
| final /*RegisterUnaryCallbackHandler*/ registerUnaryCallback;
|
| final /*RegisterBinaryCallbackHandler*/ registerBinaryCallback;
|
| + final /*ErrorCallbackHandler*/ errorCallback;
|
| final /*ScheduleMicrotaskHandler*/ scheduleMicrotask;
|
| final /*CreateTimerHandler*/ createTimer;
|
| final /*CreatePeriodicTimerHandler*/ createPeriodicTimer;
|
| @@ -214,6 +236,7 @@ abstract class ZoneDelegate {
|
| ZoneCallback registerCallback(Zone zone, f());
|
| ZoneUnaryCallback registerUnaryCallback(Zone zone, f(arg));
|
| ZoneBinaryCallback registerBinaryCallback(Zone zone, f(arg1, arg2));
|
| + AsyncError errorCallback(Zone zone, Object error, StackTrace stackTrace);
|
| void scheduleMicrotask(Zone zone, f());
|
| Timer createTimer(Zone zone, Duration duration, void f());
|
| Timer createPeriodicTimer(Zone zone, Duration period, void f(Timer timer));
|
| @@ -380,6 +403,23 @@ abstract class Zone {
|
| f(arg1, arg2), { bool runGuarded: true });
|
|
|
| /**
|
| + * Intercepts errors when added programmtically to a `Future` or `Stream`.
|
| + *
|
| + * When caling [Completer.completeError], [Stream.addError],
|
| + * or [Future] constructors that take an error or a callback that may throw,
|
| + * the current zone is allowed to intercept and replace the error.
|
| + *
|
| + * When other libraries use intermediate controllers or completers, such
|
| + * calls may contain errors that have already been processed.
|
| + *
|
| + * Return `null` if no replacement is desired.
|
| + * The original error is used unchanged in that case.
|
| + * Otherwise return an instance of [AsyncError] holding
|
| + * the new pair of error and stack trace.
|
| + */
|
| + AsyncError errorCallback(Object error, StackTrace stackTrace);
|
| +
|
| + /**
|
| * Runs [f] asynchronously in this zone.
|
| */
|
| void scheduleMicrotask(void f());
|
| @@ -495,6 +535,14 @@ class _ZoneDelegate implements ZoneDelegate {
|
| implZone, _parentDelegate(implZone), zone, f);
|
| }
|
|
|
| + AsyncError errorCallback(Zone zone, Object error, StackTrace stackTrace) {
|
| + _ZoneFunction implementation = _delegationTarget._errorCallback;
|
| + _Zone implZone = implementation.zone;
|
| + if (identical(implZone, _ROOT_ZONE)) return null;
|
| + return (implementation.function)(implZone, _parentDelegate(implZone), zone,
|
| + error, stackTrace);
|
| + }
|
| +
|
| void scheduleMicrotask(Zone zone, f()) {
|
| _ZoneFunction implementation = _delegationTarget._scheduleMicrotask;
|
| _Zone implZone = implementation.zone;
|
| @@ -545,6 +593,7 @@ abstract class _Zone implements Zone {
|
| _ZoneFunction get _registerCallback;
|
| _ZoneFunction get _registerUnaryCallback;
|
| _ZoneFunction get _registerBinaryCallback;
|
| + _ZoneFunction get _errorCallback;
|
| _ZoneFunction get _scheduleMicrotask;
|
| _ZoneFunction get _createTimer;
|
| _ZoneFunction get _createPeriodicTimer;
|
| @@ -569,6 +618,7 @@ class _CustomZone extends _Zone {
|
| _ZoneFunction _registerCallback;
|
| _ZoneFunction _registerUnaryCallback;
|
| _ZoneFunction _registerBinaryCallback;
|
| + _ZoneFunction _errorCallback;
|
| _ZoneFunction _scheduleMicrotask;
|
| _ZoneFunction _createTimer;
|
| _ZoneFunction _createPeriodicTimer;
|
| @@ -615,6 +665,9 @@ class _CustomZone extends _Zone {
|
| _registerBinaryCallback = (specification.registerBinaryCallback != null)
|
| ? new _ZoneFunction(this, specification.registerBinaryCallback)
|
| : parent._registerBinaryCallback;
|
| + _errorCallback = (specification.errorCallback != null)
|
| + ? new _ZoneFunction(this, specification.errorCallback)
|
| + : parent._errorCallback;
|
| _scheduleMicrotask = (specification.scheduleMicrotask != null)
|
| ? new _ZoneFunction(this, specification.scheduleMicrotask)
|
| : parent._scheduleMicrotask;
|
| @@ -781,6 +834,16 @@ class _CustomZone extends _Zone {
|
| implementation.zone, parentDelegate, this, f);
|
| }
|
|
|
| + AsyncError errorCallback(Object error, StackTrace stackTrace) {
|
| + final _ZoneFunction implementation = this._errorCallback;
|
| + assert(implementation != null);
|
| + final Zone implementationZone = implementation.zone;
|
| + if (identical(implementationZone, _ROOT_ZONE)) return null;
|
| + final ZoneDelegate parentDelegate = _parentDelegate(implementationZone);
|
| + return (implementation.function)(
|
| + implementationZone, parentDelegate, this, error, stackTrace);
|
| + }
|
| +
|
| void scheduleMicrotask(void f()) {
|
| _ZoneFunction implementation = this._scheduleMicrotask;
|
| assert(implementation != null);
|
| @@ -870,6 +933,9 @@ ZoneBinaryCallback _rootRegisterBinaryCallback(
|
| return f;
|
| }
|
|
|
| +AsyncError _rootErrorCallback(Zone self, ZoneDelegate parent, Zone zone,
|
| + Object error, StackTrace stackTrace) => null;
|
| +
|
| void _rootScheduleMicrotask(Zone self, ZoneDelegate parent, Zone zone, f()) {
|
| if (!identical(_ROOT_ZONE, zone)) {
|
| f = zone.bindCallback(f);
|
| @@ -940,6 +1006,7 @@ class _RootZoneSpecification implements ZoneSpecification {
|
| _rootRegisterUnaryCallback;
|
| RegisterBinaryCallbackHandler get registerBinaryCallback =>
|
| _rootRegisterBinaryCallback;
|
| + ErrorCallbackHandler get errorCallback => _rootErrorCallback;
|
| ScheduleMicrotaskHandler get scheduleMicrotask => _rootScheduleMicrotask;
|
| CreateTimerHandler get createTimer => _rootCreateTimer;
|
| CreatePeriodicTimerHandler get createPeriodicTimer =>
|
| @@ -963,6 +1030,8 @@ class _RootZone extends _Zone {
|
| const _ZoneFunction(_ROOT_ZONE, _rootRegisterUnaryCallback);
|
| _ZoneFunction get _registerBinaryCallback =>
|
| const _ZoneFunction(_ROOT_ZONE, _rootRegisterBinaryCallback);
|
| + _ZoneFunction get _errorCallback =>
|
| + const _ZoneFunction(_ROOT_ZONE, _rootErrorCallback);
|
| _ZoneFunction get _scheduleMicrotask =>
|
| const _ZoneFunction(_ROOT_ZONE, _rootScheduleMicrotask);
|
| _ZoneFunction get _createTimer =>
|
| @@ -1094,6 +1163,8 @@ class _RootZone extends _Zone {
|
|
|
| ZoneBinaryCallback registerBinaryCallback(f(arg1, arg2)) => f;
|
|
|
| + AsyncError errorCallback(Object error, StackTrace stackTrace) => null;
|
| +
|
| void scheduleMicrotask(void f()) {
|
| _rootScheduleMicrotask(null, null, this, f);
|
| }
|
|
|