mirror of
https://github.com/dart-lang/sdk
synced 2024-10-01 19:29:09 +00:00
New implementation of runZoned.
A combination of `runZoned` and `runZonedGuarded` where only the latter allows an `onError` parameter, and only that has a nullable return type. Retains the `onError` parameter on `runZoned` for now because it's too breaking to remove it until packages have been migrated off of it. It will be removed in a follow-up CL. Change-Id: If0e86c8d14e13fa089c66f4af975aeacb2616cf6 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/137302 Reviewed-by: Jake Macdonald <jakemac@google.com> Reviewed-by: Nate Bosch <nbosch@google.com>
This commit is contained in:
parent
289c4d5990
commit
8760283247
19
CHANGELOG.md
19
CHANGELOG.md
|
@ -13,6 +13,13 @@
|
|||
stack trace rather than propagate a `null` value.
|
||||
Error handling functions need no longer be prepared for `null` stack traces.
|
||||
|
||||
* **Breaking change**: [#40681](https://github.com/dart-lang/sdk/issues/40681)
|
||||
The `runZoned` function is split into two functions: `runZoned` and
|
||||
`runZonedGuarded`, where the latter has a required `onError` parameter,
|
||||
and the former has none.
|
||||
This prepares the functions for Null Safety where the two functions will
|
||||
differ in the nullability of their return types.
|
||||
|
||||
#### `dart:core`
|
||||
|
||||
* Adds `StackTrace.empty` constant which is the stack trace used as default
|
||||
|
@ -137,6 +144,18 @@ used (see Issue [39627][]).
|
|||
address in byte format for Internet addresses or raw file path for Unix
|
||||
domain addresses.
|
||||
|
||||
* **Breaking change** [#40681](https://github.com/dart-lang/sdk/issues/40681)
|
||||
The static method `runZoned` and `runWithHttpOverrides` on `HttpOverrides`
|
||||
no longer accept `zoneSpecification` and `onError` parameters.
|
||||
Use the `runZoned` or `runZonedGuarded` functions from `dart:async`
|
||||
directly if needing to specify those.
|
||||
|
||||
* **Breaking change** [#40681](https://github.com/dart-lang/sdk/issues/40681)
|
||||
The static method `runZoned` and `runWithIOOverrides` on `IOOverrides`
|
||||
no longer accept `zoneSpecification` and `onError` parameters.
|
||||
Use the `runZoned` or `runZonedGuarded` functions from `dart:async`
|
||||
directly if needing to specify those.
|
||||
|
||||
#### `dart:mirrors`
|
||||
|
||||
* Added `MirrorSystem.neverType`.
|
||||
|
|
|
@ -312,7 +312,7 @@ class AnalysisServer extends AbstractAnalysisServer {
|
|||
/// Handle a [request] that was read from the communication channel.
|
||||
void handleRequest(Request request) {
|
||||
performance.logRequestTiming(request.clientRequestTime);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
ServerPerformanceStatistics.serverRequests.makeCurrentWhile(() {
|
||||
int count = handlers.length;
|
||||
for (int i = 0; i < count; i++) {
|
||||
|
@ -341,7 +341,7 @@ class AnalysisServer extends AbstractAnalysisServer {
|
|||
}
|
||||
channel.sendResponse(Response.unknownRequest(request));
|
||||
});
|
||||
}, onError: (exception, stackTrace) {
|
||||
}, (exception, stackTrace) {
|
||||
AnalysisEngine.instance.instrumentationService.logException(
|
||||
FatalException('Failed to handle request: ${request.method}',
|
||||
exception, stackTrace));
|
||||
|
|
|
@ -144,9 +144,9 @@ class ByteStreamServerChannel implements ServerCommunicationChannel {
|
|||
|
||||
/// Send the string [s] to [_output] followed by a newline.
|
||||
void _outputLine(String s) {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
_output.writeln(s);
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
close();
|
||||
});
|
||||
}
|
||||
|
|
|
@ -217,7 +217,7 @@ class CompletionDomainHandler extends AbstractRequestHandler {
|
|||
);
|
||||
}
|
||||
|
||||
return runZoned(() {
|
||||
return runZonedGuarded(() {
|
||||
String requestName = request.method;
|
||||
|
||||
if (requestName == COMPLETION_REQUEST_GET_SUGGESTION_DETAILS) {
|
||||
|
@ -233,7 +233,7 @@ class CompletionDomainHandler extends AbstractRequestHandler {
|
|||
return setSubscriptions(request);
|
||||
}
|
||||
return null;
|
||||
}, onError: (exception, stackTrace) {
|
||||
}, (exception, stackTrace) {
|
||||
AnalysisEngine.instance.instrumentationService.logException(
|
||||
CaughtException.withMessage(
|
||||
'Failed to handle completion domain request: ${request.method}',
|
||||
|
|
|
@ -942,7 +942,7 @@ class _RefactoringManager {
|
|||
?.sendEvent('refactor', params.kind.name.toLowerCase());
|
||||
}
|
||||
|
||||
runZoned(() async {
|
||||
runZonedGuarded(() async {
|
||||
// TODO(brianwilkerson) Determine whether this await is necessary.
|
||||
await null;
|
||||
await _init(params.kind, file, params.offset, params.length);
|
||||
|
@ -990,7 +990,7 @@ class _RefactoringManager {
|
|||
_checkForReset_afterCreateChange();
|
||||
result.potentialEdits = nullIfEmpty(refactoring.potentialEditIds);
|
||||
_sendResultResponse();
|
||||
}, onError: (exception, stackTrace) {
|
||||
}, (exception, stackTrace) {
|
||||
if (exception is _ResetError ||
|
||||
exception is InconsistentAnalysisException) {
|
||||
cancel();
|
||||
|
|
|
@ -128,9 +128,9 @@ class LspByteStreamServerChannel implements LspServerCommunicationChannel {
|
|||
|
||||
/// Send [bytes] to [_output].
|
||||
void _write(List<int> bytes) {
|
||||
runZoned(
|
||||
runZonedGuarded(
|
||||
() => _output.add(bytes),
|
||||
onError: (e) => close(),
|
||||
(e, s) => close(),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -245,7 +245,7 @@ class LspAnalysisServer extends AbstractAnalysisServer {
|
|||
/// Handle a [message] that was read from the communication channel.
|
||||
void handleMessage(Message message) {
|
||||
performance.logRequestTiming(null);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
ServerPerformanceStatistics.serverRequests.makeCurrentWhile(() async {
|
||||
try {
|
||||
if (message is ResponseMessage) {
|
||||
|
@ -284,7 +284,7 @@ class LspAnalysisServer extends AbstractAnalysisServer {
|
|||
logException(errorMessage, error, stackTrace);
|
||||
}
|
||||
});
|
||||
}, onError: socketError);
|
||||
}, socketError);
|
||||
}
|
||||
|
||||
/// Logs the error on the client using window/logMessage.
|
||||
|
|
|
@ -140,10 +140,10 @@ Future listenAsyncStarThrowAsync() async {
|
|||
|
||||
Future<void> customErrorZone() async {
|
||||
final completer = Completer<void>();
|
||||
runZoned(() async {
|
||||
runZonedGuarded(() async {
|
||||
await allYield();
|
||||
completer.complete(null);
|
||||
}, onError: (e, s) {
|
||||
}, (e, s) {
|
||||
completer.completeError(e, s);
|
||||
});
|
||||
return completer.future;
|
||||
|
@ -550,7 +550,7 @@ Future<void> doTestsCausal() async {
|
|||
r'#5 _rootRun ',
|
||||
r'#6 _CustomZone.run ',
|
||||
r'#7 _runZoned ',
|
||||
r'#8 runZoned ',
|
||||
r'#8 runZonedGuarded ',
|
||||
r'#9 customErrorZone \(.*/utils.dart:143(:3)?\)$',
|
||||
];
|
||||
await doTestAwait(
|
||||
|
|
|
@ -14,9 +14,9 @@ main(args) async {
|
|||
|
||||
{
|
||||
final caughtErrorCompleter = Completer<String>();
|
||||
await runZoned(() {
|
||||
await runZonedGuarded(() {
|
||||
Isolate.spawn(isolate, x);
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
caughtErrorCompleter.complete(e.toString());
|
||||
});
|
||||
Expect.equals(
|
||||
|
|
|
@ -51,27 +51,20 @@ abstract class HttpOverrides {
|
|||
static R runZoned<R>(R body(),
|
||||
{HttpClient Function(SecurityContext) createHttpClient,
|
||||
String Function(Uri uri, Map<String, String> environment)
|
||||
findProxyFromEnvironment,
|
||||
ZoneSpecification zoneSpecification,
|
||||
Function onError}) {
|
||||
findProxyFromEnvironment}) {
|
||||
HttpOverrides overrides =
|
||||
new _HttpOverridesScope(createHttpClient, findProxyFromEnvironment);
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_httpOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
zoneValues: {_httpOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Runs [body] in a fresh [Zone] using the overrides found in [overrides].
|
||||
///
|
||||
/// Note that [overrides] should be an instance of a class that extends
|
||||
/// [HttpOverrides].
|
||||
static R runWithHttpOverrides<R>(R body(), HttpOverrides overrides,
|
||||
{ZoneSpecification zoneSpecification, Function onError}) {
|
||||
static R runWithHttpOverrides<R>(R body(), HttpOverrides overrides) {
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_httpOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
zoneValues: {_httpOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Returns a new [HttpClient] using the given [context].
|
||||
|
|
|
@ -1467,43 +1467,91 @@ const _rootZone = const _RootZone();
|
|||
* var future2 = future.then((_) { throw "error in first error-zone"; });
|
||||
* runZoned(() {
|
||||
* var future3 = future2.catchError((e) { print("Never reached!"); });
|
||||
* }, onError: (e) { print("unused error handler"); });
|
||||
* }, onError: (e) { print("catches error of first error-zone."); });
|
||||
* }, onError: (e, s) { print("unused error handler"); });
|
||||
* }, onError: (e, s) { print("catches error of first error-zone."); });
|
||||
*
|
||||
* Example:
|
||||
*
|
||||
* runZoned(() {
|
||||
* new Future(() { throw "asynchronous error"; });
|
||||
* }, onError: print); // Will print "asynchronous error".
|
||||
* }, onError: (e, s) => print(e)); // Will print "asynchronous error".
|
||||
*
|
||||
* It is possible to manually pass an error from one error zone to another
|
||||
* by re-throwing it in the new zone. If [onError] throws, that error will
|
||||
* occur in the original zone where [runZoned] was called.
|
||||
*/
|
||||
R runZoned<R>(R body(),
|
||||
{Map zoneValues, ZoneSpecification zoneSpecification, Function onError}) {
|
||||
if (onError == null) {
|
||||
{Map zoneValues,
|
||||
ZoneSpecification zoneSpecification,
|
||||
@Deprecated("Use runZonedGuarded instead") Function onError}) {
|
||||
ArgumentError.checkNotNull(body, "body");
|
||||
|
||||
if (onError != null) {
|
||||
void Function(Object, StackTrace) typedOnError;
|
||||
if (onError is void Function(Object, StackTrace)) {
|
||||
typedOnError = onError;
|
||||
} else if (onError is void Function(Object)) {
|
||||
typedOnError = (Object e, StackTrace _) => onError(e);
|
||||
} else {
|
||||
throw ArgumentError.value(onError, "onError",
|
||||
"Should accept one error, or one error and a stack trace");
|
||||
}
|
||||
return runZonedGuarded(body, typedOnError,
|
||||
zoneValues: zoneValues, zoneSpecification: zoneSpecification);
|
||||
}
|
||||
return _runZoned<R>(body, zoneValues, zoneSpecification);
|
||||
}
|
||||
void Function(Object) unaryOnError;
|
||||
void Function(Object, StackTrace) binaryOnError;
|
||||
if (onError is void Function(Object, StackTrace)) {
|
||||
binaryOnError = onError;
|
||||
} else if (onError is void Function(Object)) {
|
||||
unaryOnError = onError;
|
||||
} else {
|
||||
throw new ArgumentError("onError callback must take either an Object "
|
||||
"(the error), or both an Object (the error) and a StackTrace.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs [body] in its own error zone.
|
||||
*
|
||||
* Creates a new zone using [Zone.fork] based on [zoneSpecification] and
|
||||
* [zoneValues], then runs [body] in that zone and returns the result.
|
||||
*
|
||||
* The [onError] function is used *both* to handle asynchronous errors
|
||||
* by overriding [ZoneSpecification.handleUncaughtError] in [zoneSpecification],
|
||||
* if any, *and* to handle errors thrown synchronously by the call to [body].
|
||||
*
|
||||
* If an error occurs synchronously in [body],
|
||||
* then throwing in the [onError] handler
|
||||
* makes the call to `runZonedGuarded` throw that error,
|
||||
* and otherwise the call to `runZonedGuarded` returns `null`.
|
||||
*
|
||||
* If the zone specification has a `handleUncaughtError` value or the [onError]
|
||||
* parameter is provided, the zone becomes an error-zone.
|
||||
*
|
||||
* Errors will never cross error-zone boundaries by themselves.
|
||||
* Errors that try to cross error-zone boundaries are considered uncaught in
|
||||
* their originating error zone.
|
||||
*
|
||||
* var future = new Future.value(499);
|
||||
* runZoned(() {
|
||||
* var future2 = future.then((_) { throw "error in first error-zone"; });
|
||||
* runZoned(() {
|
||||
* var future3 = future2.catchError((e) { print("Never reached!"); });
|
||||
* }, onError: (e, s) { print("unused error handler"); });
|
||||
* }, onError: (e, s) { print("catches error of first error-zone."); });
|
||||
*
|
||||
* Example:
|
||||
*
|
||||
* runZoned(() {
|
||||
* new Future(() { throw "asynchronous error"; });
|
||||
* }, onError: (e, s) => print(e)); // Will print "asynchronous error".
|
||||
*
|
||||
* It is possible to manually pass an error from one error zone to another
|
||||
* by re-throwing it in the new zone. If [onError] throws, that error will
|
||||
* occur in the original zone where [runZoned] was called.
|
||||
*/
|
||||
@Since("2.8")
|
||||
R runZonedGuarded<R>(R body(), void onError(Object error, StackTrace stack),
|
||||
{Map zoneValues, ZoneSpecification zoneSpecification}) {
|
||||
ArgumentError.checkNotNull(body, "body");
|
||||
ArgumentError.checkNotNull(onError, "onError");
|
||||
|
||||
HandleUncaughtErrorHandler errorHandler = (Zone self, ZoneDelegate parent,
|
||||
Zone zone, error, StackTrace stackTrace) {
|
||||
try {
|
||||
if (binaryOnError != null) {
|
||||
self.parent.runBinary(binaryOnError, error, stackTrace);
|
||||
} else {
|
||||
assert(unaryOnError != null);
|
||||
self.parent.runUnary(unaryOnError, error);
|
||||
}
|
||||
self.parent.runBinary(onError, error, stackTrace);
|
||||
} catch (e, s) {
|
||||
if (identical(e, error)) {
|
||||
parent.handleUncaughtError(zone, error, stackTrace);
|
||||
|
@ -1521,13 +1569,8 @@ R runZoned<R>(R body(),
|
|||
}
|
||||
try {
|
||||
return _runZoned<R>(body, zoneValues, zoneSpecification);
|
||||
} catch (e, stackTrace) {
|
||||
if (binaryOnError != null) {
|
||||
binaryOnError(e, stackTrace);
|
||||
} else {
|
||||
assert(unaryOnError != null);
|
||||
unaryOnError(e);
|
||||
}
|
||||
} catch (error, stackTrace) {
|
||||
onError(error, stackTrace);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
|
|
@ -92,11 +92,7 @@ abstract class IOOverrides {
|
|||
// ServerSocket
|
||||
Future<ServerSocket> Function(dynamic, int,
|
||||
{int backlog, bool v6Only, bool shared})
|
||||
serverSocketBind,
|
||||
|
||||
// Optional Zone parameters
|
||||
ZoneSpecification zoneSpecification,
|
||||
Function onError}) {
|
||||
serverSocketBind}) {
|
||||
IOOverrides overrides = new _IOOverridesScope(
|
||||
// Directory
|
||||
createDirectory,
|
||||
|
@ -131,22 +127,15 @@ abstract class IOOverrides {
|
|||
// ServerSocket
|
||||
serverSocketBind,
|
||||
);
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_ioOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
return _asyncRunZoned<R>(body, zoneValues: {_ioOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Runs [body] in a fresh [Zone] using the overrides found in [overrides].
|
||||
///
|
||||
/// Note that [overrides] should be an instance of a class that extends
|
||||
/// [IOOverrides].
|
||||
static R runWithIOOverrides<R>(R body(), IOOverrides overrides,
|
||||
{ZoneSpecification zoneSpecification, Function onError}) {
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_ioOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
static R runWithIOOverrides<R>(R body(), IOOverrides overrides) {
|
||||
return _asyncRunZoned<R>(body, zoneValues: {_ioOverridesToken: overrides});
|
||||
}
|
||||
|
||||
// Directory
|
||||
|
|
|
@ -49,27 +49,20 @@ abstract class HttpOverrides {
|
|||
static R runZoned<R>(R body(),
|
||||
{HttpClient Function(SecurityContext?)? createHttpClient,
|
||||
String Function(Uri uri, Map<String, String>? environment)?
|
||||
findProxyFromEnvironment,
|
||||
ZoneSpecification? zoneSpecification,
|
||||
Function? onError}) {
|
||||
findProxyFromEnvironment}) {
|
||||
HttpOverrides overrides =
|
||||
new _HttpOverridesScope(createHttpClient, findProxyFromEnvironment);
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_httpOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
zoneValues: {_httpOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Runs [body] in a fresh [Zone] using the overrides found in [overrides].
|
||||
///
|
||||
/// Note that [overrides] should be an instance of a class that extends
|
||||
/// [HttpOverrides].
|
||||
static R runWithHttpOverrides<R>(R body(), HttpOverrides overrides,
|
||||
{ZoneSpecification? zoneSpecification, Function? onError}) {
|
||||
static R runWithHttpOverrides<R>(R body(), HttpOverrides overrides) {
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_httpOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
zoneValues: {_httpOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Returns a new [HttpClient] using the given [context].
|
||||
|
|
|
@ -1465,7 +1465,7 @@ const _Zone _rootZone = const _RootZone();
|
|||
* If an error occurs synchronously in [body],
|
||||
* then throwing in the [onError] handler
|
||||
* makes the call to `runZone` throw that error,
|
||||
* and otherwise the call to `runZoned` returns `null`.
|
||||
* and otherwise the call to `runZoned` attempt to return `null`.
|
||||
*
|
||||
* If the zone specification has a `handleUncaughtError` value or the [onError]
|
||||
* parameter is provided, the zone becomes an error-zone.
|
||||
|
@ -1474,19 +1474,19 @@ const _Zone _rootZone = const _RootZone();
|
|||
* Errors that try to cross error-zone boundaries are considered uncaught in
|
||||
* their originating error zone.
|
||||
*
|
||||
* var future = Future.value(499);
|
||||
* var future = new Future.value(499);
|
||||
* runZoned(() {
|
||||
* var future2 = future.then((_) { throw "error in first error-zone"; });
|
||||
* runZoned(() {
|
||||
* var future3 = future2.catchError((e) { print("Never reached!"); });
|
||||
* }, onError: (e) { print("unused error handler"); });
|
||||
* }, onError: (e) { print("catches error of first error-zone."); });
|
||||
* }, onError: (e, s) { print("unused error handler"); });
|
||||
* }, onError: (e, s) { print("catches error of first error-zone."); });
|
||||
*
|
||||
* Example:
|
||||
*
|
||||
* runZoned(() {
|
||||
* new Future(() { throw "asynchronous error"; });
|
||||
* }, onError: print); // Will print "asynchronous error".
|
||||
* }, onError: (e, s) => print(e)); // Will print "asynchronous error".
|
||||
*
|
||||
* It is possible to manually pass an error from one error zone to another
|
||||
* by re-throwing it in the new zone. If [onError] throws, that error will
|
||||
|
@ -1495,30 +1495,74 @@ const _Zone _rootZone = const _RootZone();
|
|||
R runZoned<R>(R body(),
|
||||
{Map<Object?, Object?>? zoneValues,
|
||||
ZoneSpecification? zoneSpecification,
|
||||
Function? onError}) {
|
||||
if (onError == null) {
|
||||
@Deprecated("Use runZonedGuarded instead") Function? onError}) {
|
||||
ArgumentError.checkNotNull(body, "body");
|
||||
if (onError != null) {
|
||||
// TODO: Remove this when code have been migrated off using [onError].
|
||||
if (onError is! void Function(Object, StackTrace)) {
|
||||
if (onError is void Function(Object)) {
|
||||
var originalOnError = onError;
|
||||
onError = (Object error, StackTrace stack) => originalOnError(error);
|
||||
} else {
|
||||
throw ArgumentError.value(onError, "onError",
|
||||
"Must be Function(Object) or Function(Object, StackTrace)");
|
||||
}
|
||||
}
|
||||
return runZonedGuarded(body, onError,
|
||||
zoneSpecification: zoneSpecification, zoneValues: zoneValues) as R;
|
||||
}
|
||||
return _runZoned<R>(body, zoneValues, zoneSpecification);
|
||||
}
|
||||
void Function(Object)? unaryOnError;
|
||||
void Function(Object, StackTrace)? binaryOnError;
|
||||
if (onError is void Function(Object, StackTrace)) {
|
||||
binaryOnError = onError;
|
||||
} else if (onError is void Function(Object)) {
|
||||
unaryOnError = onError;
|
||||
} else {
|
||||
throw new ArgumentError("onError callback must take either an Object "
|
||||
"(the error), or both an Object (the error) and a StackTrace.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs [body] in its own error zone.
|
||||
*
|
||||
* Creates a new zone using [Zone.fork] based on [zoneSpecification] and
|
||||
* [zoneValues], then runs [body] in that zone and returns the result.
|
||||
*
|
||||
* The [onError] function is used *both* to handle asynchronous errors
|
||||
* by overriding [ZoneSpecification.handleUncaughtError] in [zoneSpecification],
|
||||
* if any, *and* to handle errors thrown synchronously by the call to [body].
|
||||
*
|
||||
* If an error occurs synchronously in [body],
|
||||
* then throwing in the [onError] handler
|
||||
* makes the call to `runZonedGuarded` throw that error,
|
||||
* and otherwise the call to `runZonedGuarded` returns `null`.
|
||||
*
|
||||
* The zone will always be an error-zone.
|
||||
*
|
||||
* Errors will never cross error-zone boundaries by themselves.
|
||||
* Errors that try to cross error-zone boundaries are considered uncaught in
|
||||
* their originating error zone.
|
||||
* ```dart
|
||||
* var future = Future.value(499);
|
||||
* runZonedGuarded(() {
|
||||
* var future2 = future.then((_) { throw "error in first error-zone"; });
|
||||
* runZonedGuarded(() {
|
||||
* var future3 = future2.catchError((e) { print("Never reached!"); });
|
||||
* }, (e, s) { print("unused error handler"); });
|
||||
* }, (e, s) { print("catches error of first error-zone."); });
|
||||
* ```
|
||||
* Example:
|
||||
* ```dart
|
||||
* runZonedGuarded(() {
|
||||
* new Future(() { throw "asynchronous error"; });
|
||||
* }, (e, s) => print(e)); // Will print "asynchronous error".
|
||||
* ```
|
||||
* It is possible to manually pass an error from one error zone to another
|
||||
* by re-throwing it in the new zone. If [onError] throws, that error will
|
||||
* occur in the original zone where [runZoned] was called.
|
||||
*/
|
||||
@Since("2.8")
|
||||
R? runZonedGuarded<R>(R body(), void onError(Object error, StackTrace stack),
|
||||
{Map<Object?, Object?>? zoneValues, ZoneSpecification? zoneSpecification}) {
|
||||
ArgumentError.checkNotNull(body, "body");
|
||||
ArgumentError.checkNotNull(onError, "onError");
|
||||
_Zone parentZone = Zone._current;
|
||||
HandleUncaughtErrorHandler errorHandler = (Zone self, ZoneDelegate parent,
|
||||
Zone zone, Object error, StackTrace stackTrace) {
|
||||
try {
|
||||
if (binaryOnError != null) {
|
||||
parentZone.runBinary(binaryOnError, error, stackTrace);
|
||||
} else {
|
||||
assert(unaryOnError != null);
|
||||
parentZone.runUnary(unaryOnError!, error);
|
||||
}
|
||||
parentZone.runBinary(onError, error, stackTrace);
|
||||
} catch (e, s) {
|
||||
if (identical(e, error)) {
|
||||
parent.handleUncaughtError(zone, error, stackTrace);
|
||||
|
@ -1536,17 +1580,10 @@ R runZoned<R>(R body(),
|
|||
}
|
||||
try {
|
||||
return _runZoned<R>(body, zoneValues, zoneSpecification);
|
||||
} catch (e, stackTrace) {
|
||||
if (binaryOnError != null) {
|
||||
binaryOnError(e, stackTrace);
|
||||
} else {
|
||||
assert(unaryOnError != null);
|
||||
unaryOnError!(e);
|
||||
} catch (error, stackTrace) {
|
||||
onError(error, stackTrace);
|
||||
}
|
||||
}
|
||||
// TODO(lrn): Change behavior to throw the actual resulting error,
|
||||
// perhaps even synchronously.
|
||||
return null as R;
|
||||
return null;
|
||||
}
|
||||
|
||||
/// Runs [body] in a new zone based on [zoneValues] and [specification].
|
||||
|
|
|
@ -90,11 +90,7 @@ abstract class IOOverrides {
|
|||
// ServerSocket
|
||||
Future<ServerSocket> Function(dynamic, int,
|
||||
{int backlog, bool v6Only, bool shared})?
|
||||
serverSocketBind,
|
||||
|
||||
// Optional Zone parameters
|
||||
ZoneSpecification? zoneSpecification,
|
||||
Function? onError}) {
|
||||
serverSocketBind}) {
|
||||
IOOverrides overrides = new _IOOverridesScope(
|
||||
// Directory
|
||||
createDirectory,
|
||||
|
@ -129,22 +125,15 @@ abstract class IOOverrides {
|
|||
// ServerSocket
|
||||
serverSocketBind,
|
||||
);
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_ioOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
return _asyncRunZoned<R>(body, zoneValues: {_ioOverridesToken: overrides});
|
||||
}
|
||||
|
||||
/// Runs [body] in a fresh [Zone] using the overrides found in [overrides].
|
||||
///
|
||||
/// Note that [overrides] should be an instance of a class that extends
|
||||
/// [IOOverrides].
|
||||
static R runWithIOOverrides<R>(R body(), IOOverrides overrides,
|
||||
{ZoneSpecification? zoneSpecification, Function? onError}) {
|
||||
return _asyncRunZoned<R>(body,
|
||||
zoneValues: {_ioOverridesToken: overrides},
|
||||
zoneSpecification: zoneSpecification,
|
||||
onError: onError);
|
||||
static R runWithIOOverrides<R>(R body(), IOOverrides overrides) {
|
||||
return _asyncRunZoned<R>(body, zoneValues: {_ioOverridesToken: overrides});
|
||||
}
|
||||
|
||||
// Directory
|
||||
|
|
|
@ -11,7 +11,7 @@ Stream catchErrors(dynamic body()) {
|
|||
}
|
||||
|
||||
void onListen() {
|
||||
runZoned(body, onError: onError);
|
||||
runZonedGuarded(body, onError);
|
||||
}
|
||||
|
||||
controller = new StreamController(onListen: onListen);
|
||||
|
@ -21,7 +21,7 @@ Stream catchErrors(dynamic body()) {
|
|||
runZonedScheduleMicrotask(body(),
|
||||
{void onScheduleMicrotask(void callback()), Function? onError}) {
|
||||
if (onScheduleMicrotask == null) {
|
||||
return runZoned(body, onError: onError);
|
||||
return runZonedGuarded(body, onError);
|
||||
}
|
||||
HandleUncaughtErrorHandler errorHandler;
|
||||
if (onError != null) {
|
||||
|
|
|
@ -868,7 +868,7 @@ void testWaitCleanUpError() {
|
|||
asyncStart();
|
||||
asyncStart();
|
||||
asyncStart();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Future.wait([
|
||||
new Future.delayed(cms, () => 0),
|
||||
new Future.delayed(cms * 2, () => throw 1),
|
||||
|
@ -882,7 +882,7 @@ void testWaitCleanUpError() {
|
|||
Expect.equals(e, 1);
|
||||
asyncEnd();
|
||||
});
|
||||
}, onError: (e, s) {
|
||||
}, (e, s) {
|
||||
int index = e;
|
||||
Expect.isTrue(index == 0 || index == 2, "$index");
|
||||
Expect.isFalse(uncaughts[index]);
|
||||
|
|
|
@ -10,7 +10,7 @@ main() {
|
|||
// error handler is defined.
|
||||
Expect.equals(
|
||||
499,
|
||||
runZoned(() => 499, onError: (e) {
|
||||
runZonedGuarded(() => 499, (e, s) {
|
||||
throw "Unexpected";
|
||||
}));
|
||||
}
|
||||
|
|
|
@ -9,9 +9,9 @@ import 'dart:async';
|
|||
main() {
|
||||
asyncStart();
|
||||
// Ensure that `runZoned`'s onError handles synchronous errors.
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
asyncEnd();
|
||||
});
|
||||
|
|
|
@ -12,9 +12,9 @@ main() {
|
|||
// in the error handler at that point (when it is a synchronous error) yields
|
||||
// a synchronous error.
|
||||
try {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
throw e; //#01 : ok
|
||||
asyncEnd();
|
||||
|
|
|
@ -13,7 +13,7 @@ main() {
|
|||
|
||||
var events = [];
|
||||
// Test runZoned with periodic Timers.
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
int counter = 0;
|
||||
new Timer.periodic(const Duration(milliseconds: 50), (timer) {
|
||||
if (counter == 1) {
|
||||
|
@ -24,7 +24,7 @@ main() {
|
|||
events.add(counter);
|
||||
throw counter;
|
||||
});
|
||||
}, onError: (e, [s]) {
|
||||
}, (e, [s]) {
|
||||
events.add("error: $e");
|
||||
Expect.isNotNull(s); // Regression test for http://dartbug.com/33589
|
||||
});
|
||||
|
|
|
@ -12,15 +12,15 @@ main() {
|
|||
// to the next runZoned when the handler returns false.
|
||||
bool sawInnerHandler = false;
|
||||
try {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
runZoned(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, onError: (e, s) {
|
||||
Expect.equals(0, e);
|
||||
sawInnerHandler = true;
|
||||
throw e;
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
Expect.isTrue(sawInnerHandler);
|
||||
// If we are waiting for an error, don't asyncEnd, but let it time out.
|
||||
|
|
|
@ -267,7 +267,7 @@ main() {
|
|||
|
||||
bool streamIsDone = false;
|
||||
int errorCount = 0;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
controller.stream
|
||||
.transform(new SinkTransformer((sink) =>
|
||||
new FutureWaitingTransformerSink(sink, closeCompleter.future)))
|
||||
|
@ -280,7 +280,7 @@ main() {
|
|||
Expect.listEquals([], events);
|
||||
streamIsDone = true;
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.isTrue(e is StateError);
|
||||
errorCount++;
|
||||
});
|
||||
|
|
|
@ -114,7 +114,7 @@ main() {
|
|||
});
|
||||
|
||||
test("subscription.asFuture failure in cancel", () {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var completer = new Completer();
|
||||
var controller =
|
||||
new StreamController(onCancel: () => completer.future, sync: true);
|
||||
|
@ -135,7 +135,7 @@ main() {
|
|||
Expect.isFalse(catchErrorHasRun);
|
||||
completer.completeError(499);
|
||||
}));
|
||||
}, onError: expectAsync((e) {
|
||||
}, expectAsync2((e, s) {
|
||||
Expect.equals(499, e);
|
||||
}));
|
||||
});
|
||||
|
|
|
@ -10,8 +10,8 @@ import 'dart:async';
|
|||
test1() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
|
@ -19,8 +19,8 @@ test1() {
|
|||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -33,18 +33,18 @@ test1() {
|
|||
test2() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -57,16 +57,16 @@ test2() {
|
|||
test3() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -79,18 +79,18 @@ test3() {
|
|||
test4() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -104,20 +104,20 @@ test4() {
|
|||
test5() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -130,18 +130,18 @@ test6() {
|
|||
var events = [];
|
||||
var done = new Completer();
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
runZoned(() {
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
runZonedGuarded(() {
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e, s"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -155,16 +155,16 @@ test7() {
|
|||
var events = [];
|
||||
var done = new Completer();
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
runZoned(() {
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
runZonedGuarded(() {
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
|
|
@ -10,7 +10,7 @@ main() {
|
|||
// error handler is defined.
|
||||
Expect.equals(
|
||||
499,
|
||||
runZoned(() => 499, onError: (e) {
|
||||
runZonedGuarded(() => 499, (e, s) {
|
||||
throw "Unexpected";
|
||||
}));
|
||||
}
|
||||
|
|
|
@ -9,9 +9,9 @@ import 'dart:async';
|
|||
main() {
|
||||
asyncStart();
|
||||
// Ensure that `runZoned`'s onError handles synchronous errors.
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
asyncEnd();
|
||||
});
|
||||
|
|
|
@ -12,9 +12,9 @@ main() {
|
|||
// in the error handler at that point (when it is a synchronous error) yields
|
||||
// a synchronous error.
|
||||
try {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
throw e; //#01 : ok
|
||||
asyncEnd();
|
||||
|
|
|
@ -12,15 +12,15 @@ main() {
|
|||
// to the next runZoned when the handler returns false.
|
||||
bool sawInnerHandler = false;
|
||||
try {
|
||||
runZoned(() {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
runZonedGuarded(() {
|
||||
throw 0;
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
sawInnerHandler = true;
|
||||
throw e;
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.equals(0, e);
|
||||
Expect.isTrue(sawInnerHandler);
|
||||
// If we are waiting for an error, don't asyncEnd, but let it time out.
|
||||
|
|
|
@ -267,7 +267,7 @@ main() {
|
|||
|
||||
bool streamIsDone = false;
|
||||
int errorCount = 0;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
controller.stream
|
||||
.transform(new SinkTransformer((sink) =>
|
||||
new FutureWaitingTransformerSink(sink, closeCompleter.future)))
|
||||
|
@ -280,7 +280,7 @@ main() {
|
|||
Expect.listEquals([], events);
|
||||
streamIsDone = true;
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.isTrue(e is StateError);
|
||||
errorCount++;
|
||||
});
|
||||
|
|
|
@ -114,7 +114,7 @@ main() {
|
|||
});
|
||||
|
||||
test("subscription.asFuture failure in cancel", () {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var completer = new Completer();
|
||||
var controller =
|
||||
new StreamController(onCancel: () => completer.future, sync: true);
|
||||
|
@ -135,7 +135,7 @@ main() {
|
|||
Expect.isFalse(catchErrorHasRun);
|
||||
completer.completeError(499);
|
||||
}));
|
||||
}, onError: expectAsync((e) {
|
||||
}, expectAsync2((e, s) {
|
||||
Expect.equals(499, e);
|
||||
}));
|
||||
});
|
||||
|
|
|
@ -10,8 +10,8 @@ import 'dart:async';
|
|||
test1() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
|
@ -19,8 +19,8 @@ test1() {
|
|||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -33,18 +33,18 @@ test1() {
|
|||
test2() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -57,16 +57,16 @@ test2() {
|
|||
test3() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -79,18 +79,18 @@ test3() {
|
|||
test4() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -104,20 +104,20 @@ test4() {
|
|||
test5() {
|
||||
var events = [];
|
||||
var done = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"),
|
||||
onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -130,18 +130,18 @@ test6() {
|
|||
var events = [];
|
||||
var done = new Completer();
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
runZoned(() {
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
runZonedGuarded(() {
|
||||
var c2 = new StreamController();
|
||||
c.addStream(c2.stream).whenComplete(c.close);
|
||||
c2.add(1);
|
||||
c2.addError(2);
|
||||
c2.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
@ -155,16 +155,16 @@ test7() {
|
|||
var events = [];
|
||||
var done = new Completer();
|
||||
var c;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
c = new StreamController();
|
||||
c.stream.listen((x) => events.add("stream: $x"),
|
||||
onError: (x) => events.add("stream: error $x"), onDone: done.complete);
|
||||
}, onError: (x) => events.add("rza: error $x"));
|
||||
runZoned(() {
|
||||
}, (e, s) => events.add("rza: error $e"));
|
||||
runZonedGuarded(() {
|
||||
c.add(1);
|
||||
c.addError(2);
|
||||
c.close();
|
||||
}, onError: (x) => events.add("rzb: error $x"));
|
||||
}, (e, s) => events.add("rzb: error $e"));
|
||||
return [
|
||||
done.future,
|
||||
() {
|
||||
|
|
|
@ -12,11 +12,11 @@ var events = [];
|
|||
|
||||
Future testSocketException() {
|
||||
var completer = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Socket.connect("4", 1).then((Socket s) {
|
||||
Expect.fail("Socket should not be able to connect");
|
||||
});
|
||||
}, onError: (err) {
|
||||
}, (err, s) {
|
||||
if (err is! SocketException) Expect.fail("Not expected error: $err");
|
||||
completer.complete("socket test, ok.");
|
||||
events.add("SocketException");
|
||||
|
@ -26,9 +26,9 @@ Future testSocketException() {
|
|||
|
||||
Future testFileSystemException() {
|
||||
var completer = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
new File("lol it's not a file\n").openRead().listen(null);
|
||||
}, onError: (err) {
|
||||
}, (err, s) {
|
||||
if (err is! FileSystemException) Expect.fail("Not expected error: $err");
|
||||
completer.complete("file test, ok.");
|
||||
events.add("FileSystemException");
|
||||
|
|
|
@ -452,11 +452,11 @@ testWatchOverflow() async {
|
|||
}
|
||||
|
||||
void watcher(SendPort sendPort) async {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var watcher = Directory.systemTemp.watch(recursive: true);
|
||||
watcher.listen((data) async {});
|
||||
sendPort.send('start');
|
||||
}, onError: (error) {
|
||||
}, (error, stack) {
|
||||
print(error);
|
||||
sendPort.send('end');
|
||||
});
|
||||
|
|
|
@ -159,7 +159,7 @@ void testHttpServerZone() {
|
|||
void testHttpServerZoneError() {
|
||||
asyncStart();
|
||||
Expect.equals(Zone.root, Zone.current);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
HttpServer.bind("127.0.0.1", 0).then((server) {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
|
@ -178,14 +178,14 @@ void testHttpServerZoneError() {
|
|||
socket.listen(null);
|
||||
});
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
asyncEnd();
|
||||
});
|
||||
}
|
||||
|
||||
void testHttpServerClientClose() {
|
||||
HttpServer.bind("127.0.0.1", 0).then((server) {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
server.listen((request) {
|
||||
request.response.bufferOutput = false;
|
||||
request.response.add(new Uint8List(64 * 1024));
|
||||
|
@ -195,7 +195,7 @@ void testHttpServerClientClose() {
|
|||
});
|
||||
});
|
||||
});
|
||||
}, onError: (e, s) {
|
||||
}, (e, s) {
|
||||
Expect.fail("Unexpected error: $e(${e.hashCode})\n$s");
|
||||
});
|
||||
var client = new HttpClient();
|
||||
|
|
|
@ -426,7 +426,7 @@ void testSocketZone() {
|
|||
void testSocketZoneError() {
|
||||
asyncStart();
|
||||
Expect.equals(Zone.root, Zone.current);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
RawServerSocket.bind(InternetAddress.loopbackIPv4, 0).then((server) {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
|
@ -451,7 +451,7 @@ void testSocketZoneError() {
|
|||
socket.close();
|
||||
});
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
asyncEnd();
|
||||
});
|
||||
}
|
||||
|
|
|
@ -17,12 +17,12 @@ main() {
|
|||
initWaitForEvent();
|
||||
asyncStart();
|
||||
bool flag = false;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Timer.run(() {
|
||||
asyncEnd();
|
||||
throw "Exception";
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
flag = true;
|
||||
});
|
||||
Expect.isFalse(flag);
|
||||
|
|
|
@ -11,12 +11,12 @@ import 'package:expect/expect.dart';
|
|||
main() {
|
||||
asyncStart();
|
||||
Completer<bool> c = new Completer<bool>();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Timer.run(() {
|
||||
asyncEnd();
|
||||
throw "Error";
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.isTrue(e is String);
|
||||
c.complete(true);
|
||||
});
|
||||
|
|
|
@ -12,11 +12,11 @@ var events = [];
|
|||
|
||||
Future testSocketException() {
|
||||
var completer = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Socket.connect("4", 1).then((Socket s) {
|
||||
Expect.fail("Socket should not be able to connect");
|
||||
});
|
||||
}, onError: (err) {
|
||||
}, (err, s) {
|
||||
if (err is! SocketException) Expect.fail("Not expected error: $err");
|
||||
completer.complete("socket test, ok.");
|
||||
events.add("SocketException");
|
||||
|
@ -26,9 +26,9 @@ Future testSocketException() {
|
|||
|
||||
Future testFileSystemException() {
|
||||
var completer = new Completer();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
new File("lol it's not a file\n").openRead().listen(null);
|
||||
}, onError: (err) {
|
||||
}, (err, s) {
|
||||
if (err is! FileSystemException) Expect.fail("Not expected error: $err");
|
||||
completer.complete("file test, ok.");
|
||||
events.add("FileSystemException");
|
||||
|
|
|
@ -451,11 +451,11 @@ testWatchOverflow() async {
|
|||
}
|
||||
|
||||
void watcher(SendPort sendPort) async {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
var watcher = Directory.systemTemp.watch(recursive: true);
|
||||
watcher.listen((data) async {});
|
||||
sendPort.send('start');
|
||||
}, onError: (error) {
|
||||
}, (error, stack) {
|
||||
print(error);
|
||||
sendPort.send('end');
|
||||
});
|
||||
|
|
|
@ -159,7 +159,7 @@ void testHttpServerZone() {
|
|||
void testHttpServerZoneError() {
|
||||
asyncStart();
|
||||
Expect.equals(Zone.root, Zone.current);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
HttpServer.bind("127.0.0.1", 0).then((server) {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
|
@ -178,14 +178,14 @@ void testHttpServerZoneError() {
|
|||
socket.listen(null);
|
||||
});
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
asyncEnd();
|
||||
});
|
||||
}
|
||||
|
||||
void testHttpServerClientClose() {
|
||||
HttpServer.bind("127.0.0.1", 0).then((server) {
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
server.listen((request) {
|
||||
request.response.bufferOutput = false;
|
||||
request.response.add(new Uint8List(64 * 1024));
|
||||
|
@ -195,7 +195,7 @@ void testHttpServerClientClose() {
|
|||
});
|
||||
});
|
||||
});
|
||||
}, onError: (e, s) {
|
||||
}, (e, s) {
|
||||
Expect.fail("Unexpected error: $e(${e.hashCode})\n$s");
|
||||
});
|
||||
var client = new HttpClient();
|
||||
|
|
|
@ -429,7 +429,7 @@ void testSocketZone() {
|
|||
void testSocketZoneError() {
|
||||
asyncStart();
|
||||
Expect.equals(Zone.root, Zone.current);
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
RawServerSocket.bind(InternetAddress.loopbackIPv4, 0).then((server) {
|
||||
Expect.notEquals(Zone.root, Zone.current);
|
||||
|
@ -454,7 +454,7 @@ void testSocketZoneError() {
|
|||
socket.close();
|
||||
});
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
asyncEnd();
|
||||
});
|
||||
}
|
||||
|
|
|
@ -17,12 +17,12 @@ main() {
|
|||
initWaitForEvent();
|
||||
asyncStart();
|
||||
bool flag = false;
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Timer.run(() {
|
||||
asyncEnd();
|
||||
throw "Exception";
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
flag = true;
|
||||
});
|
||||
Expect.isFalse(flag);
|
||||
|
|
|
@ -11,12 +11,12 @@ import 'package:expect/expect.dart';
|
|||
main() {
|
||||
asyncStart();
|
||||
Completer<bool> c = new Completer<bool>();
|
||||
runZoned(() {
|
||||
runZonedGuarded(() {
|
||||
Timer.run(() {
|
||||
asyncEnd();
|
||||
throw "Error";
|
||||
});
|
||||
}, onError: (e) {
|
||||
}, (e, s) {
|
||||
Expect.isTrue(e is String);
|
||||
c.complete(true);
|
||||
});
|
||||
|
|
Loading…
Reference in a new issue