MemoryFileSystem addStream onError (#220)
Route stream errors to the stream completer rather than the file completer.
Fixes #219
diff --git a/packages/file/lib/src/backends/memory/memory_file.dart b/packages/file/lib/src/backends/memory/memory_file.dart
index 5236744..c2a46f7 100644
--- a/packages/file/lib/src/backends/memory/memory_file.dart
+++ b/packages/file/lib/src/backends/memory/memory_file.dart
@@ -416,19 +416,18 @@
Future<void> addStream(Stream<List<int>> stream) {
_checkNotStreaming();
_streamCompleter = Completer<void>();
- void finish() {
- _streamCompleter!.complete();
- _streamCompleter = null;
- }
stream.listen(
(List<int> data) => _addData(data),
cancelOnError: true,
onError: (Object error, StackTrace stackTrace) {
- _completer.completeError(error, stackTrace);
- finish();
+ _streamCompleter!.completeError(error, stackTrace);
+ _streamCompleter = null;
},
- onDone: finish,
+ onDone: () {
+ _streamCompleter!.complete();
+ _streamCompleter = null;
+ },
);
return _streamCompleter!.future;
}
diff --git a/packages/file/test/memory_test.dart b/packages/file/test/memory_test.dart
index 8e358be..f3b324e 100644
--- a/packages/file/test/memory_test.dart
+++ b/packages/file/test/memory_test.dart
@@ -2,6 +2,7 @@
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
+import 'dart:async';
import 'dart:io' as io;
import 'package:file/file.dart';
@@ -148,4 +149,25 @@
expect(tempDir.existsSync(), true);
});
+
+ test(
+ 'addStream forwards error to returned future and file can still be '
+ 'closed', () async {
+ final file = MemoryFileSystem.test().file('foo').openWrite();
+ await expectLater(file.addStream(Stream.error('bar')), throwsA('bar'));
+ await file.close();
+ });
+
+ test(
+ 'addStream cancels on error and does not misbehave if the stream '
+ 'produces multiple errors and then closes', () async {
+ final file = MemoryFileSystem.test().file('foo').openWrite();
+ final controller = StreamController<List<int>>()
+ ..addError('bar')
+ ..addError('baz');
+ final close = controller.close();
+ await expectLater(file.addStream(controller.stream), throwsA('bar'));
+ await file.close();
+ await close;
+ });
}