firstToFuture<T> method
Returns a Future that completes with the first value from the stream
.
Unlike stream.first
, this method completes with null
if the stream
finishes without emitting any values, rather than throwing a StateError.
If the stream emits an error before the first data event, the returned
Future will complete with that error.
{@tool snippet}
final numbers = Stream.fromIterable([10, 20]);
final first = await StreamHelper.i.firstToFuture(numbers);
print(first); // Prints: 10
final emptyStream = Stream<int>.empty();
final result = await StreamHelper.i.firstToFuture(emptyStream);
print(result); // Prints: null
{@end-tool}
Implementation
Future<T?> firstToFuture<T>(Stream<T> stream) {
// A Completer<T?> is required because the Future can complete with null.
final completer = Completer<T?>();
StreamSubscription<T>? subscription;
subscription = stream.listen(
(data) {
if (!completer.isCompleted) {
completer.complete(data);
subscription?.cancel();
}
},
onError: (Object e, StackTrace s) {
if (!completer.isCompleted) {
completer.completeError(e, s);
subscription?.cancel();
}
},
onDone: () {
if (!completer.isCompleted) {
completer.complete(null);
}
},
cancelOnError: true,
);
return completer.future;
}