Skip to content

Commit 6f9c68d

Browse files
committed
Merge package:test_process into the test monorepo
2 parents dc0f8ea + 200097b commit 6f9c68d

File tree

13 files changed

+778
-0
lines changed

13 files changed

+778
-0
lines changed
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
# Set update schedule for GitHub Actions
2+
# See https://docs.github.com/en/free-pro-team@latest/github/administering-a-repository/keeping-your-actions-up-to-date-with-dependabot
3+
4+
version: 2
5+
updates:
6+
7+
- package-ecosystem: github-actions
8+
directory: /
9+
schedule:
10+
interval: monthly
11+
labels:
12+
- autosubmit
13+
groups:
14+
github-actions:
15+
patterns:
16+
- "*"
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
name: Dart CI
2+
3+
on:
4+
# Run on PRs and pushes to the default branch.
5+
push:
6+
branches: [ master ]
7+
pull_request:
8+
branches: [ master ]
9+
schedule:
10+
- cron: "0 0 * * 0"
11+
12+
env:
13+
PUB_ENVIRONMENT: bot.github
14+
15+
jobs:
16+
# Check code formatting and static analysis on a single OS (linux)
17+
# against Dart dev.
18+
analyze:
19+
runs-on: ubuntu-latest
20+
strategy:
21+
fail-fast: false
22+
matrix:
23+
sdk: [dev]
24+
steps:
25+
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
26+
- uses: dart-lang/setup-dart@e630b99d28a3b71860378cafdc2a067c71107f94
27+
with:
28+
sdk: ${{ matrix.sdk }}
29+
- id: install
30+
name: Install dependencies
31+
run: dart pub get
32+
- name: Check formatting
33+
run: dart format --output=none --set-exit-if-changed .
34+
if: always() && steps.install.outcome == 'success'
35+
- name: Analyze code
36+
run: dart analyze --fatal-infos
37+
if: always() && steps.install.outcome == 'success'
38+
39+
# Run tests on a matrix consisting of two dimensions:
40+
# 1. OS: ubuntu-latest, (macos-latest, windows-latest)
41+
# 2. release: dev
42+
test:
43+
needs: analyze
44+
runs-on: ${{ matrix.os }}
45+
strategy:
46+
fail-fast: false
47+
matrix:
48+
# Add macos-latest and/or windows-latest if relevant for this package.
49+
os: [ubuntu-latest]
50+
sdk: [3.1, dev]
51+
steps:
52+
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
53+
- uses: dart-lang/setup-dart@e630b99d28a3b71860378cafdc2a067c71107f94
54+
with:
55+
sdk: ${{ matrix.sdk }}
56+
- id: install
57+
name: Install dependencies
58+
run: dart pub get
59+
- name: Run VM tests
60+
run: dart test --platform vm
61+
if: always() && steps.install.outcome == 'success'

pkgs/test_process/.gitignore

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
.buildlog
2+
.DS_Store
3+
.idea
4+
.settings/
5+
build/
6+
packages
7+
.packages
8+
pubspec.lock
9+
.dart_tool/

pkgs/test_process/AUTHORS

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# Below is a list of people and organizations that have contributed
2+
# to the project. Names should be added to the list like so:
3+
#
4+
# Name/Organization <email address>
5+
6+
Google Inc.

pkgs/test_process/CHANGELOG.md

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
## 2.1.1-wip
2+
3+
* Require Dart 3.1.
4+
5+
## 2.1.0
6+
7+
- Remove the expectation that the process exits during the normal test body.
8+
The process will still be killed during teardown if it has not exited. The
9+
check can be manually restored with `shouldExit()`.
10+
11+
## 2.0.3
12+
13+
- Populate the pubspec `repository` field.
14+
- Fixed examples in `readme.md`.
15+
- Added `example/example.dart`
16+
- Require Dart >=2.17
17+
18+
## 2.0.2
19+
20+
- Reverted `meta` constraint to `^1.3.0`.
21+
22+
## 2.0.1
23+
24+
- Update `meta` constraint to `>=1.3.0 <3.0.0`.
25+
26+
## 2.0.0
27+
28+
- Migrate to null safety.
29+
30+
## 1.0.6
31+
32+
- Require Dart >=2.1
33+
34+
## 1.0.5
35+
36+
- Don't allow the test to time out as long as the process is emitting output.
37+
38+
## 1.0.4
39+
40+
- Set max SDK version to `<3.0.0`, and adjust other dependencies.
41+
42+
## 1.0.3
43+
44+
- Support test `1.x.x`.
45+
46+
## 1.0.2
47+
48+
- Update SDK version to 2.0.0-dev.17.0
49+
50+
## 1.0.1
51+
52+
- Declare support for `async` 2.0.0.
53+
54+
## 1.0.0
55+
56+
- Added `pid` and `exitCode` getters to `TestProcess`.
57+
58+
## 1.0.0-rc.2
59+
60+
- Subclassed `TestProcess`es now emit log output based on the superclass's
61+
standard IO streams rather than the subclass's. This matches the documented
62+
behavior.
63+
64+
## 1.0.0-rc.1
65+
66+
- Initial release candidate.

pkgs/test_process/CONTRIBUTING.md

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
Want to contribute? Great! First, read this page (including the small print at
2+
the end).
3+
4+
### Before you contribute
5+
Before we can use your code, you must sign the
6+
[Google Individual Contributor License Agreement](https://cla.developers.google.com/about/google-individual)
7+
(CLA), which you can do online. The CLA is necessary mainly because you own the
8+
copyright to your changes, even after your contribution becomes part of our
9+
codebase, so we need your permission to use and distribute your code. We also
10+
need to be sure of various other things—for instance that you'll tell us if you
11+
know that your code infringes on other people's patents. You don't have to sign
12+
the CLA until after you've submitted your code for review and a member has
13+
approved it, but you must do it before we can put your code into our codebase.
14+
15+
Before you start working on a larger contribution, you should get in touch with
16+
us first through the issue tracker with your idea so that we can help out and
17+
possibly guide you. Coordinating up front makes it much easier to avoid
18+
frustration later on.
19+
20+
### Code reviews
21+
All submissions, including submissions by project members, require review.
22+
23+
### File headers
24+
All files in the project must start with the following header.
25+
26+
// Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file
27+
// for details. All rights reserved. Use of this source code is governed by a
28+
// BSD-style license that can be found in the LICENSE file.
29+
30+
### The small print
31+
Contributions made by corporations are covered by a different agreement than the
32+
one above, the
33+
[Software Grant and Corporate Contributor License Agreement](https://developers.google.com/open-source/cla/corporate).

pkgs/test_process/LICENSE

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
Copyright 2017, the Dart project authors.
2+
3+
Redistribution and use in source and binary forms, with or without
4+
modification, are permitted provided that the following conditions are
5+
met:
6+
7+
* Redistributions of source code must retain the above copyright
8+
notice, this list of conditions and the following disclaimer.
9+
* Redistributions in binary form must reproduce the above
10+
copyright notice, this list of conditions and the following
11+
disclaimer in the documentation and/or other materials provided
12+
with the distribution.
13+
* Neither the name of Google LLC nor the names of its
14+
contributors may be used to endorse or promote products derived
15+
from this software without specific prior written permission.
16+
17+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18+
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19+
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
20+
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
21+
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22+
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23+
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24+
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25+
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26+
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

pkgs/test_process/README.md

Lines changed: 123 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
[![Dart CI](https://github.com/dart-lang/test_process/actions/workflows/test-package.yml/badge.svg)](https://github.com/dart-lang/test_process/actions/workflows/test-package.yml)
2+
[![pub package](https://img.shields.io/pub/v/test_process.svg)](https://pub.dev/packages/test_process)
3+
[![package publisher](https://img.shields.io/pub/publisher/test_process.svg)](https://pub.dev/packages/test_process/publisher)
4+
5+
A package for testing subprocesses.
6+
7+
This exposes a [`TestProcess`][TestProcess] class that wraps `dart:io`'s
8+
[`Process`][Process] class and makes it easy to read standard output
9+
line-by-line. `TestProcess` works the same as `Process` in many ways, but there
10+
are a few major differences.
11+
12+
[TestProcess]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess-class.html
13+
[Process]: https://api.dart.dev/stable/dart-io/Process-class.html
14+
15+
## Standard Output
16+
17+
`Process.stdout` and `Process.stderr` are binary streams, which is the most
18+
general API but isn't the most helpful when working with a program that produces
19+
plain text. Instead, [`TestProcess.stdout`][stdout] and
20+
[`TestProcess.stderr`][stderr] emit a string for each line of output the process
21+
produces. What's more, they're [`StreamQueue`][StreamQueue]s, which means
22+
they provide a *pull-based API*. For example:
23+
24+
[stdout]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/stdout.html
25+
[stderr]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/stderr.html
26+
[StreamQueue]: https://pub.dev/documentation/async/latest/async/StreamQueue-class.html
27+
28+
```dart
29+
import 'package:test/test.dart';
30+
import 'package:test_process/test_process.dart';
31+
32+
void main() {
33+
test('pub get gets dependencies', () async {
34+
// TestProcess.start() works just like Process.start() from dart:io.
35+
var process = await TestProcess.start('dart', ['pub', 'get']);
36+
37+
// StreamQueue.next returns the next line emitted on standard out.
38+
var firstLine = await process.stdout.next;
39+
expect(firstLine, equals('Resolving dependencies...'));
40+
41+
// Each call to StreamQueue.next moves one line further.
42+
String next;
43+
do {
44+
next = await process.stdout.next;
45+
} while (next != 'Got dependencies!');
46+
47+
// Assert that the process exits with code 0.
48+
await process.shouldExit(0);
49+
});
50+
}
51+
```
52+
53+
The `test` package's [stream matchers][] have built-in support for
54+
`StreamQueues`, which makes them perfect for making assertions about a process's
55+
output. We can use this to clean up the previous example:
56+
57+
[stream matchers]: https://github.com/dart-lang/test#stream-matchers
58+
59+
```dart
60+
import 'package:test/test.dart';
61+
import 'package:test_process/test_process.dart';
62+
63+
void main() {
64+
test('pub get gets dependencies', () async {
65+
var process = await TestProcess.start('dart', ['pub', 'get']);
66+
67+
// Each stream matcher will consume as many lines as it matches from a
68+
// StreamQueue, and no more, so it's safe to use them in sequence.
69+
await expectLater(process.stdout, emits('Resolving dependencies...'));
70+
71+
// The emitsThrough matcher matches and consumes any number of lines, as
72+
// long as they end with one matching the argument.
73+
await expectLater(process.stdout, emitsThrough('Got dependencies!'));
74+
75+
await process.shouldExit(0);
76+
});
77+
}
78+
```
79+
80+
If you want to access the standard output streams without consuming any values
81+
from the queues, you can use the [`stdoutStream()`][stdoutStream] and
82+
[`stderrStream()`][stderrStream] methods. Each time you call one of these, it
83+
produces an entirely new stream that replays the corresponding output stream
84+
from the beginning, regardless of what's already been produced by `stdout`,
85+
`stderr`, or other calls to the stream method.
86+
87+
[stdoutStream]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/stdoutStream.html
88+
[stderrStream]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/stderrStream.html
89+
90+
## Signals and Termination
91+
92+
The way signaling works is different from `dart:io` as well. `TestProcess` still
93+
has a [`kill()`][kill] method, but it defaults to `SIGKILL` on Mac OS and Linux
94+
to ensure (as best as possible) that processes die without leaving behind
95+
zombies. If you want to send a particular signal (which is unsupported on
96+
Windows), you can do so by explicitly calling [`signal()`][signal].
97+
98+
[kill]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/kill.html
99+
[signal]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/signal.html
100+
101+
In addition to [`exitCode`][exitCode], which works the same as in `dart:io`,
102+
`TestProcess` also adds a new method named [`shouldExit()`][shouldExit]. This
103+
lets tests wait for a process to exit, and (if desired) assert what particular
104+
exit code it produced.
105+
106+
[exitCode]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/exitCode.html
107+
[shouldExit]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/shouldExit.html
108+
109+
## Debugging Output
110+
111+
When a test using `TestProcess` fails, it will print all the output produced by
112+
that process. This makes it much easier to figure out what went wrong and why.
113+
The debugging output uses a header based on the process's invocation by
114+
default, but you can pass in custom `description` parameters to
115+
[`TestProcess.start()`][start] to control the headers.
116+
117+
[start]: https://pub.dev/documentation/test_process/latest/test_process/TestProcess/start.html
118+
119+
`TestProcess` will also produce debugging output as the test runs if you pass
120+
`forwardStdio: true` to `TestProcess.start()`. This can be particularly useful
121+
when you're using an interactive debugger and you want to figure out what a
122+
process is doing before the test finishes and the normal debugging output is
123+
printed.
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# https://dart.dev/tools/analysis#the-analysis-options-file
2+
include: package:dart_flutter_team_lints/analysis_options.yaml
3+
4+
analyzer:
5+
language:
6+
strict-casts: true
7+
strict-inference: true
8+
strict-raw-types: true
9+
10+
linter:
11+
rules:
12+
- avoid_unused_constructor_parameters
13+
- cancel_subscriptions
14+
- literal_only_boolean_expressions
15+
- missing_whitespace_between_adjacent_strings
16+
- no_adjacent_strings_in_list
17+
- no_runtimeType_toString
18+
- unnecessary_await_in_return
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
// Copyright (c) 2022, the Dart project authors. Please see the AUTHORS file
2+
// for details. All rights reserved. Use of this source code is governed by a
3+
// BSD-style license that can be found in the LICENSE file.
4+
5+
import 'package:test/test.dart';
6+
import 'package:test_process/test_process.dart';
7+
8+
void main() {
9+
test('pub get gets dependencies', () async {
10+
// TestProcess.start() works just like Process.start() from dart:io.
11+
var process = await TestProcess.start('dart', ['pub', 'get']);
12+
13+
// StreamQueue.next returns the next line emitted on standard out.
14+
var firstLine = await process.stdout.next;
15+
expect(firstLine, equals('Resolving dependencies...'));
16+
17+
// Each call to StreamQueue.next moves one line further.
18+
String next;
19+
do {
20+
next = await process.stdout.next;
21+
} while (next != 'Got dependencies!');
22+
23+
// Assert that the process exits with code 0.
24+
await process.shouldExit(0);
25+
});
26+
}

0 commit comments

Comments
 (0)