waitF<R> function
FutureOr<R>
waitF<
R>( - Iterable<_TFactory> itemFactories,
- _TSyncOrAsyncMapper<Iterable, R> callback, {
- _TOnErrorCallback? onError,
- bool eagerError = true,
})
Implementation
FutureOr<R> waitF<R>(
Iterable<_TFactory<dynamic>> itemFactories,
_TSyncOrAsyncMapper<Iterable<dynamic>, R> callback, {
_TOnErrorCallback? onError,
bool eagerError = true,
}) {
final buffer = <FutureOr<dynamic>>[];
Object? firstSyncError;
StackTrace? firstSyncStackTrace;
var isFuture = false;
for (final itemFactory in itemFactories) {
try {
if (eagerError && firstSyncError != null) {
itemFactory();
continue;
}
final item = itemFactory();
buffer.add(item);
if (item is Future) {
isFuture = true;
}
} catch (e, s) {
if (eagerError) {
if (onError != null) {
final errorResult = onError(e, s);
if (errorResult is Future) {
return errorResult.then((_) => _throwError(e, s));
}
}
_throwError(e, s);
}
if (firstSyncError == null) {
firstSyncError = e;
firstSyncStackTrace = s;
buffer.add(Future.error(e, s));
isFuture = true;
}
}
}
if (!isFuture) {
try {
final result = callback(buffer);
if (result is Future<R>) {
return result.catchError((Object e, StackTrace? s) {
if (onError != null) {
return Future.sync(() => onError(e, s)).then((_) => throw e);
}
throw e;
});
}
return result;
} catch (e, s) {
if (onError != null) {
final errResult = onError(e, s);
if (errResult is Future) return errResult.then((_) => throw e);
}
rethrow;
}
} else {
return Future.wait(
buffer.map((e) => Future.value(e)),
eagerError: eagerError,
)
.then((items) {
if (firstSyncError != null) {
if (onError != null) {
final errResult = onError(firstSyncError, firstSyncStackTrace);
if (errResult is Future) {
return errResult.then(
(_) => _throwError(firstSyncError!, firstSyncStackTrace),
);
}
}
_throwError(firstSyncError, firstSyncStackTrace);
}
return callback(items);
})
.catchError((Object e, StackTrace? s) {
if (onError != null) {
final errResult = onError(e, s);
if (errResult is Future) {
return errResult.then((_) => throw e);
}
}
throw e;
});
}
}