Add utilities to sharedStdIn. (dart-lang/io#26)
diff --git a/pkgs/io/CHANGELOG.md b/pkgs/io/CHANGELOG.md
index a16a183..3dc176d 100644
--- a/pkgs/io/CHANGELOG.md
+++ b/pkgs/io/CHANGELOG.md
@@ -1,3 +1,19 @@
+## 0.3.1
+
+- Added `SharedStdIn.nextLine` (similar to `readLineSync`) and `lines`:
+
+```dart
+main() async {
+ // Prints the first line entered on stdin.
+ print(await sharedStdIn.nextLine());
+
+ // Prints all remaining lines.
+ await for (final line in sharedStdIn.lines) {
+ print(line);
+ }
+}
+```
+
## 0.3.0
- **BREAKING CHANGE**: The `arguments` argument to `ProcessManager.spawn` is
@@ -5,7 +21,9 @@
built-in `Process.start`, and easier to use as a drop in replacement:
```dart
-processManager.spawn('dart', ['--version']);
+main() {
+ processManager.spawn('dart', ['--version']);
+}
```
- Fixed a bug where processes created from `ProcessManager.spawn` could not
diff --git a/pkgs/io/lib/src/shared_stdin.dart b/pkgs/io/lib/src/shared_stdin.dart
index 79ff97d..23b3d50 100644
--- a/pkgs/io/lib/src/shared_stdin.dart
+++ b/pkgs/io/lib/src/shared_stdin.dart
@@ -3,6 +3,7 @@
// BSD-style license that can be found in the LICENSE file.
import 'dart:async';
+import 'dart:convert';
import 'dart:io';
import 'package:meta/meta.dart';
@@ -32,6 +33,28 @@
_sub = (stream ??= stdin).listen(_onInput);
}
+ /// Returns a future that completes with the next line.
+ ///
+ /// This is similar to the standard [Stdin.readLineSync], but asynchronous.
+ Future<String> nextLine({Encoding encoding: SYSTEM_ENCODING}) {
+ return lines(encoding: encoding).first;
+ }
+
+ /// Returns the stream transformed as UTF8 strings separated by line breaks.
+ ///
+ /// This is similar to synchronous code using [Stdin.readLineSync]:
+ /// ```dart
+ /// while (true) {
+ /// var line = stdin.readLineSync();
+ /// // ...
+ /// }
+ /// ```
+ ///
+ /// ... but asynchronous.
+ Stream<String> lines({Encoding encoding: SYSTEM_ENCODING}) {
+ return transform(UTF8.decoder).transform(const LineSplitter());
+ }
+
void _onInput(List<int> event) => _getCurrent().add(event);
StreamController<List<int>> _getCurrent() {
diff --git a/pkgs/io/test/shared_stdin_test.dart b/pkgs/io/test/shared_stdin_test.dart
index 722ec1f..82e833f 100644
--- a/pkgs/io/test/shared_stdin_test.dart
+++ b/pkgs/io/test/shared_stdin_test.dart
@@ -43,4 +43,37 @@
await active.cancel();
expect(() => sharedStdIn.listen((_) {}), returnsNormally);
});
+
+ test('should return a stream of lines', () async {
+ expect(
+ sharedStdIn.lines(),
+ emitsInOrder(<dynamic>[
+ 'I',
+ 'Think',
+ 'Therefore',
+ 'I',
+ 'Am',
+ ]),
+ );
+ [
+ 'I\nThink\n',
+ 'Therefore\n',
+ 'I\n',
+ 'Am\n',
+ ].forEach(fakeStdIn.add);
+ });
+
+ test('should return the next line', () {
+ expect(sharedStdIn.nextLine(), completion('Hello World'));
+ fakeStdIn.add('Hello World\n');
+ });
+
+ test('should allow listening for new lines multiple times', () async {
+ expect(sharedStdIn.nextLine(), completion('Hello World'));
+ fakeStdIn.add('Hello World\n');
+ await new Future<Null>.value();
+
+ expect(sharedStdIn.nextLine(), completion('Hello World'));
+ fakeStdIn.add('Hello World\n');
+ });
}