Move to `expect` from `package:matcher` (#1969)

- Delete `test_api` copy of the `expect` libraries and tests.
- Re-export `package:matcher/expect.dart` from `test_api`.
- Re-export from `package:matcher/expect.dart` directly to maintain the
  same library surface from `package:test/test.dart` and
  `package:test/expect.dart`.
- Remove some documentation about specific matchers from the README.
- Re-export some `lib/src` libraries that are used in libraries that we can't
  roll synchronously with this package.

Temporarily add dependency overrides on `matcher` while it is
unpublished.
diff --git a/integration_tests/spawn_hybrid/pubspec.yaml b/integration_tests/spawn_hybrid/pubspec.yaml
index d5b58e1..d5cb8d0 100644
--- a/integration_tests/spawn_hybrid/pubspec.yaml
+++ b/integration_tests/spawn_hybrid/pubspec.yaml
@@ -18,3 +18,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/integration_tests/wasm/pubspec.yaml b/integration_tests/wasm/pubspec.yaml
index 145898c..e216aba 100644
--- a/integration_tests/wasm/pubspec.yaml
+++ b/integration_tests/wasm/pubspec.yaml
@@ -11,3 +11,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/legacy_tests/nnbd_opted_in/pubspec.yaml b/legacy_tests/nnbd_opted_in/pubspec.yaml
index 2d7af3d..7547ecf 100644
--- a/legacy_tests/nnbd_opted_in/pubspec.yaml
+++ b/legacy_tests/nnbd_opted_in/pubspec.yaml
@@ -12,3 +12,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/legacy_tests/nnbd_opted_in_with_optout/pubspec.yaml b/legacy_tests/nnbd_opted_in_with_optout/pubspec.yaml
index f75f97d..7117612 100644
--- a/legacy_tests/nnbd_opted_in_with_optout/pubspec.yaml
+++ b/legacy_tests/nnbd_opted_in_with_optout/pubspec.yaml
@@ -12,3 +12,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/legacy_tests/nnbd_opted_out/pubspec.yaml b/legacy_tests/nnbd_opted_out/pubspec.yaml
index 9a03e1b..37cd7e7 100644
--- a/legacy_tests/nnbd_opted_out/pubspec.yaml
+++ b/legacy_tests/nnbd_opted_out/pubspec.yaml
@@ -12,3 +12,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/legacy_tests/spawn_hybrid_with_optout/pubspec.yaml b/legacy_tests/spawn_hybrid_with_optout/pubspec.yaml
index d02bf9f..f9c0b22 100644
--- a/legacy_tests/spawn_hybrid_with_optout/pubspec.yaml
+++ b/legacy_tests/spawn_hybrid_with_optout/pubspec.yaml
@@ -12,3 +12,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/legacy_tests/unit_tests/pubspec.yaml b/legacy_tests/unit_tests/pubspec.yaml
index 4703f1e..6da383b 100644
--- a/legacy_tests/unit_tests/pubspec.yaml
+++ b/legacy_tests/unit_tests/pubspec.yaml
@@ -16,3 +16,7 @@
     path: ../../pkgs/test_api
   test_core:
     path: ../../pkgs/test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/pkgs/checks/pubspec_overrides.yaml b/pkgs/checks/pubspec_overrides.yaml
index 7d9aba4..d7fd34c 100644
--- a/pkgs/checks/pubspec_overrides.yaml
+++ b/pkgs/checks/pubspec_overrides.yaml
@@ -5,3 +5,7 @@
     path: ../test_core
   test:
     path: ../test
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3b48930a01f678e2921cea16563af67460e6f765
diff --git a/pkgs/test/README.md b/pkgs/test/README.md
index 1dd8f69..9b4aef8 100644
--- a/pkgs/test/README.md
+++ b/pkgs/test/README.md
@@ -35,12 +35,12 @@
 
 ## Writing Tests
 
-Tests are specified using the top-level [`test()`] function, and test assertions
-are made using [`expect()`]:
+Tests are specified using the top-level [`test()`] function.
+Test asserts can be made using [`expect` from `package:matcher`][expect]
 
 [`test()`]: https://pub.dev/documentation/test_core/latest/test_core.scaffolding/test.html
 
-[`expect()`]: https://pub.dev/documentation/test_api/latest/expect/expect.html
+[expect]: https://pub.dev/documentation/matcher/latest/expect/expect.html
 
 ```dart
 import 'package:test/test.dart';
@@ -91,42 +91,6 @@
 }
 ```
 
-Any matchers from the [`matcher`] package can be used with `expect()` to do
-complex validations:
-
-[`matcher`]: https://pub.dev/documentation/matcher/latest/matcher/matcher-library.html
-
-```dart
-import 'package:test/test.dart';
-
-void main() {
-  test('.split() splits the string on the delimiter', () {
-    expect('foo,bar,baz', allOf([
-      contains('foo'),
-      isNot(startsWith('bar')),
-      endsWith('baz')
-    ]));
-  });
-}
-```
-
-You can also test exceptions with the [`throwsA()`] function or a matcher
-such as [`throwsFormatException`]:
-
-[`throwsA()`]: https://pub.dev/documentation/test_api/latest/expect/throwsA.html
-
-[`throwsFormatException`]: https://pub.dev/documentation/test_api/latest/expect/throwsFormatException-constant.html
-
-```dart
-import 'package:test/test.dart';
-
-void main() {
-  test('.parse() fails on invalid input', () {
-    expect(() => int.parse('X'), throwsFormatException);
-  });
-}
-```
-
 You can use the [`setUp()`] and [`tearDown()`] functions to share code between
 tests. The `setUp()` callback will run before every test in a group or test
 suite, and `tearDown()` will run after. `tearDown()` will run even if a test
@@ -478,189 +442,6 @@
 
 [early-handler]:https://dart.dev/guides/libraries/futures-error-handling#potential-problem-failing-to-register-error-handlers-early
 
-### Future Matchers
-
-There are a number of useful functions and matchers for more advanced
-asynchrony. The [`completion()`] matcher can be used to test `Futures`; it
-ensures that the test doesn't finish until the `Future` completes, and runs a
-matcher against that `Future`'s value.
-
-[`completion()`]: https://pub.dev/documentation/test_api/latest/expect/completion.html
-
-```dart
-import 'dart:async';
-
-import 'package:test/test.dart';
-
-void main() {
-  test('Future.value() returns the value', () {
-    expect(Future.value(10), completion(equals(10)));
-  });
-}
-```
-
-The [`throwsA()`] matcher and the various [`throwsExceptionType`] matchers work
-with both synchronous callbacks and asynchronous `Future`s. They ensure that a
-particular type of exception is thrown:
-
-[`throwsExceptionType`]: https://pub.dev/documentation/test_api/latest/expect/throwsException-constant.html
-
-```dart
-import 'dart:async';
-
-import 'package:test/test.dart';
-
-void main() {
-  test('Future.error() throws the error', () {
-    expect(Future.error('oh no'), throwsA(equals('oh no')));
-    expect(Future.error(StateError('bad state')), throwsStateError);
-  });
-}
-```
-
-The [`expectAsync()`] function wraps another function and has two jobs. First,
-it asserts that the wrapped function is called a certain number of times, and
-will cause the test to fail if it's called too often; second, it keeps the test
-from finishing until the function is called the requisite number of times.
-
-```dart
-import 'dart:async';
-
-import 'package:test/test.dart';
-
-void main() {
-  test('Stream.fromIterable() emits the values in the iterable', () {
-    var stream = Stream.fromIterable([1, 2, 3]);
-
-    stream.listen(expectAsync1((number) {
-      expect(number, inInclusiveRange(1, 3));
-    }, count: 3));
-  });
-}
-```
-
-[`expectAsync()`]: https://pub.dev/documentation/test_api/latest/test_api/expectAsync.html
-
-### Stream Matchers
-
-The `test` package provides a suite of powerful matchers for dealing with
-[asynchronous streams][Stream]. They're expressive and composable, and make it
-easy to write complex expectations about the values emitted by a stream. For
-example:
-
-[Stream]: https://api.dart.dev/stable/dart-async/Stream-class.html
-
-```dart
-import 'dart:async';
-
-import 'package:test/test.dart';
-
-void main() {
-  test('process emits status messages', () {
-    // Dummy data to mimic something that might be emitted by a process.
-    var stdoutLines = Stream.fromIterable([
-      'Ready.',
-      'Loading took 150ms.',
-      'Succeeded!'
-    ]);
-
-    expect(stdoutLines, emitsInOrder([
-      // Values match individual events.
-      'Ready.',
-
-      // Matchers also run against individual events.
-      startsWith('Loading took'),
-
-      // Stream matchers can be nested. This asserts that one of two events are
-      // emitted after the "Loading took" line.
-      emitsAnyOf(['Succeeded!', 'Failed!']),
-
-      // By default, more events are allowed after the matcher finishes
-      // matching. This asserts instead that the stream emits a done event and
-      // nothing else.
-      emitsDone
-    ]));
-  });
-}
-```
-
-A stream matcher can also match the [`async`] package's [`StreamQueue`] class,
-which allows events to be requested from a stream rather than pushed to the
-consumer. The matcher will consume the matched events, but leave the rest of the
-queue alone so that it can still be used by the test, unlike a normal `Stream`
-which can only have one subscriber. For example:
-
-[`async`]: https://pub.dev/packages/async
-
-[`StreamQueue`]: https://pub.dev/documentation/async/latest/async/StreamQueue-class.html
-
-```dart
-import 'dart:async';
-
-import 'package:async/async.dart';
-import 'package:test/test.dart';
-
-void main() {
-  test('process emits a WebSocket URL', () async {
-    // Wrap the Stream in a StreamQueue so that we can request events.
-    var stdout = StreamQueue(Stream.fromIterable([
-      'WebSocket URL:',
-      'ws://localhost:1234/',
-      'Waiting for connection...'
-    ]));
-
-    // Ignore lines from the process until it's about to emit the URL.
-    await expectLater(stdout, emitsThrough('WebSocket URL:'));
-
-    // Parse the next line as a URL.
-    var url = Uri.parse(await stdout.next);
-    expect(url.host, equals('localhost'));
-
-    // You can match against the same StreamQueue multiple times.
-    await expectLater(stdout, emits('Waiting for connection...'));
-  });
-}
-```
-
-The following built-in stream matchers are available:
-
-* [`emits()`] matches a single data event.
-* [`emitsError()`] matches a single error event.
-* [`emitsDone`] matches a single done event.
-* [`mayEmit()`] consumes events if they match an inner matcher, without
-  requiring them to match.
-* [`mayEmitMultiple()`] works like `mayEmit()`, but it matches events against
-  the matcher as many times as possible.
-* [`emitsAnyOf()`] consumes events matching one (or more) of several possible
-  matchers.
-* [`emitsInOrder()`] consumes events matching multiple matchers in a row.
-* [`emitsInAnyOrder()`] works like `emitsInOrder()`, but it allows the matchers
-  to match in any order.
-* [`neverEmits()`] matches a stream that finishes *without* matching an inner
-  matcher.
-
-You can also define your own custom stream matchers with [`StreamMatcher()`].
-
-[`emits()`]: https://pub.dev/documentation/test_api/latest/expect/emits.html
-
-[`emitsError()`]: https://pub.dev/documentation/test_api/latest/expect/emitsError.html
-
-[`emitsDone`]: https://pub.dev/documentation/test_api/latest/expect/emitsDone.html
-
-[`mayEmit()`]: https://pub.dev/documentation/test_api/latest/expect/mayEmit.html
-
-[`mayEmitMultiple()`]: https://pub.dev/documentation/test_api/latest/expect/mayEmitMultiple.html
-
-[`emitsAnyOf()`]: https://pub.dev/documentation/test_api/latest/expect/emitsAnyOf.html
-
-[`emitsInOrder()`]: https://pub.dev/documentation/test_api/latest/expect/emitsInOrder.html
-
-[`emitsInAnyOrder()`]: https://pub.dev/documentation/test_api/latest/expect/emitsInAnyOrder.html
-
-[`neverEmits()`]: https://pub.dev/documentation/test_api/latest/expect/neverEmits.html
-
-[`StreamMatcher()`]: https://pub.dev/documentation/test_api/latest/expect/StreamMatcher-class.html
-
 ## Running Tests With Custom HTML
 
 By default, the test runner will generate its own empty HTML file for browser
diff --git a/pkgs/test/lib/expect.dart b/pkgs/test/lib/expect.dart
index 28f64f7..5e62622 100644
--- a/pkgs/test/lib/expect.dart
+++ b/pkgs/test/lib/expect.dart
@@ -2,4 +2,4 @@
 // 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.
 
-export 'package:test_api/expect.dart';
+export 'package:matcher/expect.dart';
diff --git a/pkgs/test/lib/test.dart b/pkgs/test/lib/test.dart
index 961dae1..d976c56 100644
--- a/pkgs/test/lib/test.dart
+++ b/pkgs/test/lib/test.dart
@@ -2,5 +2,14 @@
 // 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.
 
+export 'package:matcher/expect.dart';
+// Deprecated exports not surfaced through focused libraries.
+// ignore: deprecated_member_use
+export 'package:matcher/src/expect/expect.dart' show ErrorFormatter;
+// ignore: deprecated_member_use
+export 'package:matcher/src/expect/expect_async.dart' show expectAsync;
+// ignore: deprecated_member_use
+export 'package:matcher/src/expect/throws_matcher.dart' show throws, Throws;
+// The non-deprecated API (through a deprecated import).
 // ignore: deprecated_member_use
 export 'package:test_core/test_core.dart';
diff --git a/pkgs/test/pubspec.yaml b/pkgs/test/pubspec.yaml
index b9ae53f..b30df97 100644
--- a/pkgs/test/pubspec.yaml
+++ b/pkgs/test/pubspec.yaml
@@ -34,6 +34,9 @@
   # Use an exact version until the test_api and test_core package are stable.
   test_api: 0.5.0
   test_core: 0.5.0
+  # Use a tight version constraint to ensure that a constraint on matcher
+  # properly constrains all features it provides.
+  matcher: '>=0.12.15 <0.12.16'
 
 dev_dependencies:
   fake_async: ^1.0.0
diff --git a/pkgs/test/pubspec_overrides.yaml b/pkgs/test/pubspec_overrides.yaml
index d02d71d..3b714dc 100644
--- a/pkgs/test/pubspec_overrides.yaml
+++ b/pkgs/test/pubspec_overrides.yaml
@@ -3,3 +3,7 @@
     path: ../test_core
   test_api:
     path: ../test_api
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416
diff --git a/pkgs/test/test/runner/github_reporter_test.dart b/pkgs/test/test/runner/github_reporter_test.dart
index 96bc863..c4c75b3 100644
--- a/pkgs/test/test/runner/github_reporter_test.dart
+++ b/pkgs/test/test/runner/github_reporter_test.dart
@@ -154,8 +154,9 @@
         test.dart 8:62  main.<fn>.<fn>
         ::endgroup::
         ::group::❌ fail after completion (failed after test completion)
-        This test failed after it had already completed. Make sure to use [expectAsync]
-        or the [completes] matcher when testing async code.
+        This test failed after it had already completed.
+        Make sure to use a matching library which informs the test runner
+        of pending async work.
         test.dart 8:62  main.<fn>.<fn>
         ::endgroup::
         ✅ second test so that the first failure is reported
diff --git a/pkgs/test/test/runner/json_reporter_test.dart b/pkgs/test/test/runner/json_reporter_test.dart
index 029d557..6ddcabf 100644
--- a/pkgs/test/test/runner/json_reporter_test.dart
+++ b/pkgs/test/test/runner/json_reporter_test.dart
@@ -172,9 +172,9 @@
         errorJson(3, 'oh no'),
         errorJson(
             3,
-            'This test failed after it had already completed. Make sure to '
-            'use [expectAsync]\n'
-            'or the [completes] matcher when testing async code.'),
+            'This test failed after it had already completed.\n'
+            'Make sure to use a matching library which informs the '
+            'test runner\nof pending async work.'),
         testDoneJson(4),
       ]
     ], doneJson(success: false));
diff --git a/pkgs/test/test/runner/skip_expect_test.dart b/pkgs/test/test/runner/skip_expect_test.dart
index 97e1330..41376e3 100644
--- a/pkgs/test/test/runner/skip_expect_test.dart
+++ b/pkgs/test/test/runner/skip_expect_test.dart
@@ -197,9 +197,9 @@
             '+0: skip',
             '+1: wait',
             '+0 -1: skip',
-            'This test was marked as skipped after it had already completed. '
-                'Make sure to use',
-            '[expectAsync] or the [completes] matcher when testing async code.',
+            'This test was marked as skipped after it had already completed.',
+            'Make sure to use a matching library which informs the test runner',
+            'of pending async work.',
             '+1 -1: Some tests failed.'
           ]));
       await test.shouldExit(1);
@@ -239,9 +239,9 @@
             '+0: skip',
             '+1: wait',
             '+0 -1: skip',
-            'This test was marked as skipped after it had already completed. '
-                'Make sure to use',
-            '[expectAsync] or the [completes] matcher when testing async code.',
+            'This test was marked as skipped after it had already completed.',
+            'Make sure to use a matching library which informs the test runner',
+            'of pending async work.',
             '+1 -1: Some tests failed.'
           ]));
       await test.shouldExit(1);
diff --git a/pkgs/test_api/CHANGELOG.md b/pkgs/test_api/CHANGELOG.md
index 0b5dd84..f90dbc2 100644
--- a/pkgs/test_api/CHANGELOG.md
+++ b/pkgs/test_api/CHANGELOG.md
@@ -8,6 +8,8 @@
   to `Runtime`.
 * Add `package:test_api/hooks_testing.dart` library for writing tests against
   code that uses `package:test_api/hooks.dart`.
+* **BREAKING** Remove `ErrorFormatter`, `expectAsync`,  `throws`, and `Throws`
+  from `package:test_api/test_api.dart`.
 
 ## 0.4.18
 
diff --git a/pkgs/test_api/lib/expect.dart b/pkgs/test_api/lib/expect.dart
index 30a8071..5e62622 100644
--- a/pkgs/test_api/lib/expect.dart
+++ b/pkgs/test_api/lib/expect.dart
@@ -2,60 +2,4 @@
 // 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.
 
-export 'package:matcher/matcher.dart';
-
-export 'src/expect/expect.dart' show expect, expectLater, fail;
-export 'src/expect/expect_async.dart'
-    show
-        Func0,
-        Func1,
-        Func2,
-        Func3,
-        Func4,
-        Func5,
-        Func6,
-        expectAsync0,
-        expectAsync1,
-        expectAsync2,
-        expectAsync3,
-        expectAsync4,
-        expectAsync5,
-        expectAsync6,
-        expectAsyncUntil0,
-        expectAsyncUntil1,
-        expectAsyncUntil2,
-        expectAsyncUntil3,
-        expectAsyncUntil4,
-        expectAsyncUntil5,
-        expectAsyncUntil6;
-export 'src/expect/future_matchers.dart'
-    show completes, completion, doesNotComplete;
-export 'src/expect/never_called.dart' show neverCalled;
-export 'src/expect/prints_matcher.dart' show prints;
-export 'src/expect/stream_matcher.dart' show StreamMatcher;
-export 'src/expect/stream_matchers.dart'
-    show
-        emitsDone,
-        emits,
-        emitsError,
-        mayEmit,
-        emitsAnyOf,
-        emitsInOrder,
-        emitsInAnyOrder,
-        emitsThrough,
-        mayEmitMultiple,
-        neverEmits;
-export 'src/expect/throws_matcher.dart' show throwsA;
-export 'src/expect/throws_matchers.dart'
-    show
-        throwsArgumentError,
-        throwsConcurrentModificationError,
-        throwsCyclicInitializationError,
-        throwsException,
-        throwsFormatException,
-        throwsNoSuchMethodError,
-        throwsNullThrownError,
-        throwsRangeError,
-        throwsStateError,
-        throwsUnimplementedError,
-        throwsUnsupportedError;
+export 'package:matcher/expect.dart';
diff --git a/pkgs/test_api/lib/src/backend/invoker.dart b/pkgs/test_api/lib/src/backend/invoker.dart
index 582d9f9..0274f90 100644
--- a/pkgs/test_api/lib/src/backend/invoker.dart
+++ b/pkgs/test_api/lib/src/backend/invoker.dart
@@ -305,9 +305,9 @@
       // Set the state explicitly so we don't get an extra error about the test
       // failing after being complete.
       _controller.setState(const State(Status.complete, Result.error));
-      throw 'This test was marked as skipped after it had already completed. '
-          'Make sure to use\n'
-          '[expectAsync] or the [completes] matcher when testing async code.';
+      throw 'This test was marked as skipped after it had already completed.\n'
+          'Make sure to use a matching library which informs the test runner\n'
+          'of pending async work.';
     }
 
     if (message != null) _controller.message(Message.skip(message));
@@ -367,9 +367,9 @@
 
     _handleError(
         zone,
-        'This test failed after it had already completed. Make sure to use '
-        '[expectAsync]\n'
-        'or the [completes] matcher when testing async code.',
+        'This test failed after it had already completed.\n'
+        'Make sure to use a matching library which informs the test runner\n'
+        'of pending async work.',
         stackTrace);
   }
 
diff --git a/pkgs/test_api/lib/src/backend/stack_trace_formatter.dart b/pkgs/test_api/lib/src/backend/stack_trace_formatter.dart
index d200143..35d56f1 100644
--- a/pkgs/test_api/lib/src/backend/stack_trace_formatter.dart
+++ b/pkgs/test_api/lib/src/backend/stack_trace_formatter.dart
@@ -23,7 +23,7 @@
   StackTraceMapper? _mapper;
 
   /// The set of packages to fold when producing terse [Chain]s.
-  var _except = {'test', 'stream_channel', 'test_api'};
+  var _except = {'matcher', 'stream_channel', 'test', 'test_api'};
 
   /// If non-empty, all packages not in this list will be folded when producing
   /// terse [Chain]s.
diff --git a/pkgs/test_api/lib/src/expect/async_matcher.dart b/pkgs/test_api/lib/src/expect/async_matcher.dart
index a3cc965..044c192 100644
--- a/pkgs/test_api/lib/src/expect/async_matcher.dart
+++ b/pkgs/test_api/lib/src/expect/async_matcher.dart
@@ -2,56 +2,4 @@
 // 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 'package:matcher/matcher.dart';
-import 'package:test_api/hooks.dart';
-
-import 'expect.dart';
-
-/// A matcher that does asynchronous computation.
-///
-/// Rather than implementing [matches], subclasses implement [matchAsync].
-/// [AsyncMatcher.matches] ensures that the test doesn't complete until the
-/// returned future completes, and [expect] returns a future that completes when
-/// the returned future completes so that tests can wait for it.
-abstract class AsyncMatcher extends Matcher {
-  const AsyncMatcher();
-
-  /// Returns `null` if this matches [item], or a [String] description of the
-  /// failure if it doesn't match.
-  ///
-  /// This can return a [Future] or a synchronous value. If it returns a
-  /// [Future], neither [expect] nor the test will complete until that [Future]
-  /// completes.
-  ///
-  /// If this returns a [String] synchronously, [expect] will synchronously
-  /// throw a [TestFailure] and [matches] will synchronously return `false`.
-  dynamic /*FutureOr<String>*/ matchAsync(item);
-
-  @override
-  bool matches(item, Map matchState) {
-    final result = matchAsync(item);
-    expect(result,
-        anyOf([equals(null), TypeMatcher<Future>(), TypeMatcher<String>()]),
-        reason: 'matchAsync() may only return a String, a Future, or null.');
-
-    if (result is Future) {
-      final outstandingWork = TestHandle.current.markPending();
-      result.then((realResult) {
-        if (realResult != null) {
-          fail(formatFailure(this, item, realResult as String));
-        }
-        outstandingWork.complete();
-      });
-    } else if (result is String) {
-      matchState[this] = result;
-      return false;
-    }
-
-    return true;
-  }
-
-  @override
-  Description describeMismatch(item, Description mismatchDescription,
-          Map matchState, bool verbose) =>
-      StringDescription(matchState[this] as String);
-}
+export 'package:matcher/src/expect/async_matcher.dart';
diff --git a/pkgs/test_api/lib/src/expect/expect.dart b/pkgs/test_api/lib/src/expect/expect.dart
deleted file mode 100644
index 3773000..0000000
--- a/pkgs/test_api/lib/src/expect/expect.dart
+++ /dev/null
@@ -1,145 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-import 'package:test_api/hooks.dart';
-
-import 'async_matcher.dart';
-import 'util/pretty_print.dart';
-
-/// The type used for functions that can be used to build up error reports
-/// upon failures in [expect].
-@Deprecated('Will be removed in 0.13.0.')
-typedef ErrorFormatter = String Function(dynamic actual, Matcher matcher,
-    String? reason, Map matchState, bool verbose);
-
-/// Assert that [actual] matches [matcher].
-///
-/// This is the main assertion function. [reason] is optional and is typically
-/// not supplied, as a reason is generated from [matcher]; if [reason]
-/// is included it is appended to the reason generated by the matcher.
-///
-/// [matcher] can be a value in which case it will be wrapped in an
-/// [equals] matcher.
-///
-/// If the assertion fails a [TestFailure] is thrown.
-///
-/// If [skip] is a String or `true`, the assertion is skipped. The arguments are
-/// still evaluated, but [actual] is not verified to match [matcher]. If
-/// [actual] is a [Future], the test won't complete until the future emits a
-/// value.
-///
-/// If [skip] is a string, it should explain why the assertion is skipped; this
-/// reason will be printed when running the test.
-///
-/// Certain matchers, like [completion] and [throwsA], either match or fail
-/// asynchronously. When you use [expect] with these matchers, it ensures that
-/// the test doesn't complete until the matcher has either matched or failed. If
-/// you want to wait for the matcher to complete before continuing the test, you
-/// can call [expectLater] instead and `await` the result.
-void expect(actual, matcher,
-    {String? reason,
-    skip,
-    @Deprecated('Will be removed in 0.13.0.') bool verbose = false,
-    @Deprecated('Will be removed in 0.13.0.') ErrorFormatter? formatter}) {
-  _expect(actual, matcher,
-      reason: reason, skip: skip, verbose: verbose, formatter: formatter);
-}
-
-/// Just like [expect], but returns a [Future] that completes when the matcher
-/// has finished matching.
-///
-/// For the [completes] and [completion] matchers, as well as [throwsA] and
-/// related matchers when they're matched against a [Future], the returned
-/// future completes when the matched future completes. For the [prints]
-/// matcher, it completes when the future returned by the callback completes.
-/// Otherwise, it completes immediately.
-///
-/// If the matcher fails asynchronously, that failure is piped to the returned
-/// future where it can be handled by user code.
-Future expectLater(actual, matcher, {String? reason, skip}) =>
-    _expect(actual, matcher, reason: reason, skip: skip);
-
-/// The implementation of [expect] and [expectLater].
-Future _expect(actual, matcher,
-    {String? reason, skip, bool verbose = false, ErrorFormatter? formatter}) {
-  final test = TestHandle.current;
-  formatter ??= (actual, matcher, reason, matchState, verbose) {
-    var mismatchDescription = StringDescription();
-    matcher.describeMismatch(actual, mismatchDescription, matchState, verbose);
-
-    return formatFailure(matcher, actual, mismatchDescription.toString(),
-        reason: reason);
-  };
-
-  if (skip != null && skip is! bool && skip is! String) {
-    throw ArgumentError.value(skip, 'skip', 'must be a bool or a String');
-  }
-
-  matcher = wrapMatcher(matcher);
-  if (skip != null && skip != false) {
-    String message;
-    if (skip is String) {
-      message = 'Skip expect: $skip';
-    } else if (reason != null) {
-      message = 'Skip expect ($reason).';
-    } else {
-      var description = StringDescription().addDescriptionOf(matcher);
-      message = 'Skip expect ($description).';
-    }
-
-    test.markSkipped(message);
-    return Future.sync(() {});
-  }
-
-  if (matcher is AsyncMatcher) {
-    // Avoid async/await so that expect() throws synchronously when possible.
-    var result = matcher.matchAsync(actual);
-    expect(result,
-        anyOf([equals(null), TypeMatcher<Future>(), TypeMatcher<String>()]),
-        reason: 'matchAsync() may only return a String, a Future, or null.');
-
-    if (result is String) {
-      fail(formatFailure(matcher, actual, result, reason: reason));
-    } else if (result is Future) {
-      final outstandingWork = test.markPending();
-      return result.then((realResult) {
-        if (realResult == null) return;
-        fail(formatFailure(matcher as Matcher, actual, realResult as String,
-            reason: reason));
-      }).whenComplete(() {
-        // Always remove this, in case the failure is caught and handled
-        // gracefully.
-        outstandingWork.complete();
-      });
-    }
-
-    return Future.sync(() {});
-  }
-
-  var matchState = {};
-  try {
-    if ((matcher as Matcher).matches(actual, matchState)) {
-      return Future.sync(() {});
-    }
-  } catch (e, trace) {
-    reason ??= '$e at $trace';
-  }
-  fail(formatter(actual, matcher as Matcher, reason, matchState, verbose));
-}
-
-/// Convenience method for throwing a new [TestFailure] with the provided
-/// [message].
-Never fail(String message) => throw TestFailure(message);
-
-// The default error formatter.
-@Deprecated('Will be removed in 0.13.0.')
-String formatFailure(Matcher expected, actual, String which, {String? reason}) {
-  var buffer = StringBuffer();
-  buffer.writeln(indent(prettyPrint(expected), first: 'Expected: '));
-  buffer.writeln(indent(prettyPrint(actual), first: '  Actual: '));
-  if (which.isNotEmpty) buffer.writeln(indent(which, first: '   Which: '));
-  if (reason != null) buffer.writeln(reason);
-  return buffer.toString();
-}
diff --git a/pkgs/test_api/lib/src/expect/expect_async.dart b/pkgs/test_api/lib/src/expect/expect_async.dart
deleted file mode 100644
index dee7c1e..0000000
--- a/pkgs/test_api/lib/src/expect/expect_async.dart
+++ /dev/null
@@ -1,585 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test_api/hooks.dart';
-
-import 'util/placeholder.dart';
-
-// Function types returned by expectAsync# methods.
-
-typedef Func0<T> = T Function();
-typedef Func1<T, A> = T Function([A a]);
-typedef Func2<T, A, B> = T Function([A a, B b]);
-typedef Func3<T, A, B, C> = T Function([A a, B b, C c]);
-typedef Func4<T, A, B, C, D> = T Function([A a, B b, C c, D d]);
-typedef Func5<T, A, B, C, D, E> = T Function([A a, B b, C c, D d, E e]);
-typedef Func6<T, A, B, C, D, E, F> = T Function([A a, B b, C c, D d, E e, F f]);
-
-/// A wrapper for a function that ensures that it's called the appropriate
-/// number of times.
-///
-/// The containing test won't be considered to have completed successfully until
-/// this function has been called the appropriate number of times.
-///
-/// The wrapper function is accessible via [func]. It supports up to six
-/// optional and/or required positional arguments, but no named arguments.
-class _ExpectedFunction<T> {
-  /// The wrapped callback.
-  final Function _callback;
-
-  /// The minimum number of calls that are expected to be made to the function.
-  ///
-  /// If fewer calls than this are made, the test will fail.
-  final int _minExpectedCalls;
-
-  /// The maximum number of calls that are expected to be made to the function.
-  ///
-  /// If more calls than this are made, the test will fail.
-  final int _maxExpectedCalls;
-
-  /// A callback that should return whether the function is not expected to have
-  /// any more calls.
-  ///
-  /// This will be called after every time the function is run. The test case
-  /// won't be allowed to terminate until it returns `true`.
-  ///
-  /// This may be `null`. If so, the function is considered to be done after
-  /// it's been run once.
-  final bool Function()? _isDone;
-
-  /// A descriptive name for the function.
-  final String _id;
-
-  /// An optional description of why the function is expected to be called.
-  ///
-  /// If not passed, this will be an empty string.
-  final String _reason;
-
-  /// The number of times the function has been called.
-  int _actualCalls = 0;
-
-  /// The test in which this function was wrapped.
-  late final TestHandle _test;
-
-  /// Whether this function has been called the requisite number of times.
-  late bool _complete;
-
-  OutstandingWork? _outstandingWork;
-
-  /// Wraps [callback] in a function that asserts that it's called at least
-  /// [minExpected] times and no more than [maxExpected] times.
-  ///
-  /// If passed, [id] is used as a descriptive name fo the function and [reason]
-  /// as a reason it's expected to be called. If [isDone] is passed, the test
-  /// won't be allowed to complete until it returns `true`.
-  _ExpectedFunction(Function callback, int minExpected, int maxExpected,
-      {String? id, String? reason, bool Function()? isDone})
-      : _callback = callback,
-        _minExpectedCalls = minExpected,
-        _maxExpectedCalls =
-            (maxExpected == 0 && minExpected > 0) ? minExpected : maxExpected,
-        _isDone = isDone,
-        _reason = reason == null ? '' : '\n$reason',
-        _id = _makeCallbackId(id, callback) {
-    try {
-      _test = TestHandle.current;
-    } on OutsideTestException {
-      throw StateError('`expectAsync` must be called within a test.');
-    }
-
-    if (maxExpected > 0 && minExpected > maxExpected) {
-      throw ArgumentError('max ($maxExpected) may not be less than count '
-          '($minExpected).');
-    }
-
-    if (isDone != null || minExpected > 0) {
-      _outstandingWork = _test.markPending();
-      _complete = false;
-    } else {
-      _complete = true;
-    }
-  }
-
-  /// Tries to find a reasonable name for [callback].
-  ///
-  /// If [id] is passed, uses that. Otherwise, tries to determine a name from
-  /// calling `toString`. If no name can be found, returns the empty string.
-  static String _makeCallbackId(String? id, Function callback) {
-    if (id != null) return '$id ';
-
-    // If the callback is not an anonymous closure, try to get the
-    // name.
-    var toString = callback.toString();
-    var prefix = "Function '";
-    var start = toString.indexOf(prefix);
-    if (start == -1) return '';
-
-    start += prefix.length;
-    var end = toString.indexOf("'", start);
-    if (end == -1) return '';
-    return '${toString.substring(start, end)} ';
-  }
-
-  /// Returns a function that has the same number of positional arguments as the
-  /// wrapped function (up to a total of 6).
-  Function get func {
-    if (_callback is Function(Never, Never, Never, Never, Never, Never)) {
-      return max6;
-    }
-    if (_callback is Function(Never, Never, Never, Never, Never)) return max5;
-    if (_callback is Function(Never, Never, Never, Never)) return max4;
-    if (_callback is Function(Never, Never, Never)) return max3;
-    if (_callback is Function(Never, Never)) return max2;
-    if (_callback is Function(Never)) return max1;
-    if (_callback is Function()) return max0;
-
-    _outstandingWork?.complete();
-    throw ArgumentError(
-        'The wrapped function has more than 6 required arguments');
-  }
-
-  // This indirection is critical. It ensures the returned function has an
-  // argument count of zero.
-  T max0() => max6();
-
-  T max1([Object? a0 = placeholder]) => max6(a0);
-
-  T max2([Object? a0 = placeholder, Object? a1 = placeholder]) => max6(a0, a1);
-
-  T max3(
-          [Object? a0 = placeholder,
-          Object? a1 = placeholder,
-          Object? a2 = placeholder]) =>
-      max6(a0, a1, a2);
-
-  T max4(
-          [Object? a0 = placeholder,
-          Object? a1 = placeholder,
-          Object? a2 = placeholder,
-          Object? a3 = placeholder]) =>
-      max6(a0, a1, a2, a3);
-
-  T max5(
-          [Object? a0 = placeholder,
-          Object? a1 = placeholder,
-          Object? a2 = placeholder,
-          Object? a3 = placeholder,
-          Object? a4 = placeholder]) =>
-      max6(a0, a1, a2, a3, a4);
-
-  T max6(
-          [Object? a0 = placeholder,
-          Object? a1 = placeholder,
-          Object? a2 = placeholder,
-          Object? a3 = placeholder,
-          Object? a4 = placeholder,
-          Object? a5 = placeholder]) =>
-      _run([a0, a1, a2, a3, a4, a5].where((a) => a != placeholder));
-
-  /// Runs the wrapped function with [args] and returns its return value.
-  T _run(Iterable args) {
-    // Note that in the old test, this returned `null` if it encountered an
-    // error, where now it just re-throws that error because Zone machinery will
-    // pass it to the invoker anyway.
-    try {
-      _actualCalls++;
-      if (_test.shouldBeDone) {
-        throw 'Callback ${_id}called ($_actualCalls) after test case '
-            '${_test.name} had already completed.$_reason';
-      } else if (_maxExpectedCalls >= 0 && _actualCalls > _maxExpectedCalls) {
-        throw TestFailure('Callback ${_id}called more times than expected '
-            '($_maxExpectedCalls).$_reason');
-      }
-
-      return Function.apply(_callback, args.toList()) as T;
-    } finally {
-      _afterRun();
-    }
-  }
-
-  /// After each time the function is run, check to see if it's complete.
-  void _afterRun() {
-    if (_complete) return;
-    if (_minExpectedCalls > 0 && _actualCalls < _minExpectedCalls) return;
-    if (_isDone != null && !_isDone!()) return;
-
-    // Mark this callback as complete and remove it from the test case's
-    // outstanding callback count; if that hits zero the test is done.
-    _complete = true;
-    _outstandingWork?.complete();
-  }
-}
-
-/// This function is deprecated because it doesn't work well with strong mode.
-/// Use [expectAsync0], [expectAsync1],
-/// [expectAsync2], [expectAsync3], [expectAsync4], [expectAsync5], or
-/// [expectAsync6] instead.
-@Deprecated('Will be removed in 0.13.0')
-Function expectAsync(Function callback,
-        {int count = 1, int max = 0, String? id, String? reason}) =>
-    _ExpectedFunction(callback, count, max, id: id, reason: reason).func;
-
-/// Informs the framework that the given [callback] of arity 0 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with zero arguments. See also
-/// [expectAsync1], [expectAsync2], [expectAsync3], [expectAsync4],
-/// [expectAsync5], and [expectAsync6] for callbacks with different arity.
-Func0<T> expectAsync0<T>(T Function() callback,
-        {int count = 1, int max = 0, String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max0;
-
-/// Informs the framework that the given [callback] of arity 1 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with one argument. See also
-/// [expectAsync0], [expectAsync2], [expectAsync3], [expectAsync4],
-/// [expectAsync5], and [expectAsync6] for callbacks with different arity.
-Func1<T, A> expectAsync1<T, A>(T Function(A) callback,
-        {int count = 1, int max = 0, String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max1;
-
-/// Informs the framework that the given [callback] of arity 2 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with two arguments. See also
-/// [expectAsync0], [expectAsync1], [expectAsync3], [expectAsync4],
-/// [expectAsync5], and [expectAsync6] for callbacks with different arity.
-Func2<T, A, B> expectAsync2<T, A, B>(T Function(A, B) callback,
-        {int count = 1, int max = 0, String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max2;
-
-/// Informs the framework that the given [callback] of arity 3 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with three arguments. See also
-/// [expectAsync0], [expectAsync1], [expectAsync2], [expectAsync4],
-/// [expectAsync5], and [expectAsync6] for callbacks with different arity.
-Func3<T, A, B, C> expectAsync3<T, A, B, C>(T Function(A, B, C) callback,
-        {int count = 1, int max = 0, String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max3;
-
-/// Informs the framework that the given [callback] of arity 4 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with four arguments. See also
-/// [expectAsync0], [expectAsync1], [expectAsync2], [expectAsync3],
-/// [expectAsync5], and [expectAsync6] for callbacks with different arity.
-Func4<T, A, B, C, D> expectAsync4<T, A, B, C, D>(
-        T Function(A, B, C, D) callback,
-        {int count = 1,
-        int max = 0,
-        String? id,
-        String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max4;
-
-/// Informs the framework that the given [callback] of arity 5 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with five arguments. See also
-/// [expectAsync0], [expectAsync1], [expectAsync2], [expectAsync3],
-/// [expectAsync4], and [expectAsync6] for callbacks with different arity.
-Func5<T, A, B, C, D, E> expectAsync5<T, A, B, C, D, E>(
-        T Function(A, B, C, D, E) callback,
-        {int count = 1,
-        int max = 0,
-        String? id,
-        String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max5;
-
-/// Informs the framework that the given [callback] of arity 6 is expected to be
-/// called [count] number of times (by default 1).
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// The test framework will wait for the callback to run the [count] times
-/// before it considers the current test to be complete.
-///
-/// [max] can be used to specify an upper bound on the number of calls; if this
-/// is exceeded the test will fail. If [max] is `0` (the default), the callback
-/// is expected to be called exactly [count] times. If [max] is `-1`, the
-/// callback is allowed to be called any number of times greater than [count].
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with six arguments. See also
-/// [expectAsync0], [expectAsync1], [expectAsync2], [expectAsync3],
-/// [expectAsync4], and [expectAsync5] for callbacks with different arity.
-Func6<T, A, B, C, D, E, F> expectAsync6<T, A, B, C, D, E, F>(
-        T Function(A, B, C, D, E, F) callback,
-        {int count = 1,
-        int max = 0,
-        String? id,
-        String? reason}) =>
-    _ExpectedFunction<T>(callback, count, max, id: id, reason: reason).max6;
-
-/// This function is deprecated because it doesn't work well with strong mode.
-/// Use [expectAsyncUntil0], [expectAsyncUntil1],
-/// [expectAsyncUntil2], [expectAsyncUntil3], [expectAsyncUntil4],
-/// [expectAsyncUntil5], or [expectAsyncUntil6] instead.
-@Deprecated('Will be removed in 0.13.0')
-Function expectAsyncUntil(Function callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction(callback, 0, -1, id: id, reason: reason, isDone: isDone)
-        .func;
-
-/// Informs the framework that the given [callback] of arity 0 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with zero arguments. See also
-/// [expectAsyncUntil1], [expectAsyncUntil2], [expectAsyncUntil3],
-/// [expectAsyncUntil4], [expectAsyncUntil5], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func0<T> expectAsyncUntil0<T>(T Function() callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max0;
-
-/// Informs the framework that the given [callback] of arity 1 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with one argument. See also
-/// [expectAsyncUntil0], [expectAsyncUntil2], [expectAsyncUntil3],
-/// [expectAsyncUntil4], [expectAsyncUntil5], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func1<T, A> expectAsyncUntil1<T, A>(
-        T Function(A) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max1;
-
-/// Informs the framework that the given [callback] of arity 2 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with two arguments. See also
-/// [expectAsyncUntil0], [expectAsyncUntil1], [expectAsyncUntil3],
-/// [expectAsyncUntil4], [expectAsyncUntil5], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func2<T, A, B> expectAsyncUntil2<T, A, B>(
-        T Function(A, B) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max2;
-
-/// Informs the framework that the given [callback] of arity 3 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with three arguments. See also
-/// [expectAsyncUntil0], [expectAsyncUntil1], [expectAsyncUntil2],
-/// [expectAsyncUntil4], [expectAsyncUntil5], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func3<T, A, B, C> expectAsyncUntil3<T, A, B, C>(
-        T Function(A, B, C) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max3;
-
-/// Informs the framework that the given [callback] of arity 4 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with four arguments. See also
-/// [expectAsyncUntil0], [expectAsyncUntil1], [expectAsyncUntil2],
-/// [expectAsyncUntil3], [expectAsyncUntil5], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func4<T, A, B, C, D> expectAsyncUntil4<T, A, B, C, D>(
-        T Function(A, B, C, D) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max4;
-
-/// Informs the framework that the given [callback] of arity 5 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with five arguments. See also
-/// [expectAsyncUntil0], [expectAsyncUntil1], [expectAsyncUntil2],
-/// [expectAsyncUntil3], [expectAsyncUntil4], and [expectAsyncUntil6] for
-/// callbacks with different arity.
-Func5<T, A, B, C, D, E> expectAsyncUntil5<T, A, B, C, D, E>(
-        T Function(A, B, C, D, E) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max5;
-
-/// Informs the framework that the given [callback] of arity 6 is expected to be
-/// called until [isDone] returns true.
-///
-/// Returns a wrapped function that should be used as a replacement of the
-/// original callback.
-///
-/// [isDone] is called after each time the function is run. Only when it returns
-/// true will the callback be considered complete.
-///
-/// Both [id] and [reason] are optional and provide extra information about the
-/// callback when debugging. [id] should be the name of the callback, while
-/// [reason] should be the reason the callback is expected to be called.
-///
-/// This method takes callbacks with six arguments. See also
-/// [expectAsyncUntil0], [expectAsyncUntil1], [expectAsyncUntil2],
-/// [expectAsyncUntil3], [expectAsyncUntil4], and [expectAsyncUntil5] for
-/// callbacks with different arity.
-Func6<T, A, B, C, D, E, F> expectAsyncUntil6<T, A, B, C, D, E, F>(
-        T Function(A, B, C, D, E, F) callback, bool Function() isDone,
-        {String? id, String? reason}) =>
-    _ExpectedFunction<T>(callback, 0, -1,
-            id: id, reason: reason, isDone: isDone)
-        .max6;
diff --git a/pkgs/test_api/lib/src/expect/future_matchers.dart b/pkgs/test_api/lib/src/expect/future_matchers.dart
deleted file mode 100644
index 9900c97..0000000
--- a/pkgs/test_api/lib/src/expect/future_matchers.dart
+++ /dev/null
@@ -1,115 +0,0 @@
-// Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-import 'package:test_api/hooks.dart' show pumpEventQueue;
-
-import 'async_matcher.dart';
-import 'expect.dart';
-import 'util/pretty_print.dart';
-
-/// Matches a [Future] that completes successfully with any value.
-///
-/// This creates an asynchronous expectation. The call to [expect] will return
-/// immediately and execution will continue. Later, when the future completes,
-/// the expectation against [matcher] will run. To wait for the future to
-/// complete and the expectation to run use [expectLater] and wait on the
-/// returned future.
-///
-/// To test that a Future completes with an exception, you can use [throws] and
-/// [throwsA].
-final Matcher completes = const _Completes(null);
-
-/// Matches a [Future] that completes successfully with a value that matches
-/// [matcher].
-///
-/// This creates an asynchronous expectation. The call to [expect] will return
-/// immediately and execution will continue. Later, when the future completes,
-/// the expectation against [matcher] will run. To wait for the future to
-/// complete and the expectation to run use [expectLater] and wait on the
-/// returned future.
-///
-/// To test that a Future completes with an exception, you can use [throws] and
-/// [throwsA].
-Matcher completion(matcher,
-        [@Deprecated('this parameter is ignored') String? description]) =>
-    _Completes(wrapMatcher(matcher));
-
-class _Completes extends AsyncMatcher {
-  final Matcher? _matcher;
-
-  const _Completes(this._matcher);
-
-  // Avoid async/await so we synchronously start listening to [item].
-  @override
-  dynamic /*FutureOr<String>*/ matchAsync(item) {
-    if (item is! Future) return 'was not a Future';
-
-    return item.then((value) async {
-      if (_matcher == null) return null;
-
-      String? result;
-      if (_matcher is AsyncMatcher) {
-        result = await (_matcher as AsyncMatcher).matchAsync(value) as String?;
-        if (result == null) return null;
-      } else {
-        var matchState = {};
-        if (_matcher!.matches(value, matchState)) return null;
-        result = _matcher!
-            .describeMismatch(value, StringDescription(), matchState, false)
-            .toString();
-      }
-
-      var buffer = StringBuffer();
-      buffer.writeln(indent(prettyPrint(value), first: 'emitted '));
-      if (result.isNotEmpty) buffer.writeln(indent(result, first: '  which '));
-      return buffer.toString().trimRight();
-    });
-  }
-
-  @override
-  Description describe(Description description) {
-    if (_matcher == null) {
-      description.add('completes successfully');
-    } else {
-      description.add('completes to a value that ').addDescriptionOf(_matcher);
-    }
-    return description;
-  }
-}
-
-/// Matches a [Future] that does not complete.
-///
-/// Note that this creates an asynchronous expectation. The call to
-/// `expect()` that includes this will return immediately and execution will
-/// continue.
-final Matcher doesNotComplete = const _DoesNotComplete();
-
-class _DoesNotComplete extends Matcher {
-  const _DoesNotComplete();
-
-  @override
-  Description describe(Description description) {
-    description.add('does not complete');
-    return description;
-  }
-
-  @override
-  bool matches(item, Map matchState) {
-    if (item is! Future) return false;
-    item.then((value) {
-      fail('Future was not expected to complete but completed with a value of '
-          '$value');
-    });
-    expect(pumpEventQueue(), completes);
-    return true;
-  }
-
-  @override
-  Description describeMismatch(
-      item, Description description, Map matchState, bool verbose) {
-    if (item is! Future) return description.add('$item is not a Future');
-    return description;
-  }
-}
diff --git a/pkgs/test_api/lib/src/expect/never_called.dart b/pkgs/test_api/lib/src/expect/never_called.dart
deleted file mode 100644
index 96c81cb..0000000
--- a/pkgs/test_api/lib/src/expect/never_called.dart
+++ /dev/null
@@ -1,68 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:stack_trace/stack_trace.dart';
-import 'package:test_api/hooks.dart';
-
-import 'expect.dart';
-import 'future_matchers.dart';
-import 'util/placeholder.dart';
-import 'util/pretty_print.dart';
-
-/// Returns a function that causes the test to fail if it's called.
-///
-/// This can safely be passed in place of any callback that takes ten or fewer
-/// positional parameters. For example:
-///
-/// ```
-/// // Asserts that the stream never emits an event.
-/// stream.listen(neverCalled);
-/// ```
-///
-/// This also ensures that the test doesn't complete until a call to
-/// [pumpEventQueue] finishes, so that the callback has a chance to be called.
-Null Function(
-    [Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?,
-    Object?]) get neverCalled {
-  // Make sure the test stays alive long enough to call the function if it's
-  // going to.
-  expect(pumpEventQueue(), completes);
-
-  var zone = Zone.current;
-  return (
-      [a1 = placeholder,
-      a2 = placeholder,
-      a3 = placeholder,
-      a4 = placeholder,
-      a5 = placeholder,
-      a6 = placeholder,
-      a7 = placeholder,
-      a8 = placeholder,
-      a9 = placeholder,
-      a10 = placeholder]) {
-    var arguments = [a1, a2, a3, a4, a5, a6, a7, a8, a9, a10]
-        .where((argument) => argument != placeholder)
-        .toList();
-
-    var argsText = arguments.isEmpty
-        ? ' no arguments.'
-        : ':\n${bullet(arguments.map(prettyPrint))}';
-    zone.handleUncaughtError(
-        TestFailure(
-            'Callback should never have been called, but it was called with'
-            '$argsText'),
-        zone.run(() => Chain.current()));
-    return null;
-  };
-}
diff --git a/pkgs/test_api/lib/src/expect/prints_matcher.dart b/pkgs/test_api/lib/src/expect/prints_matcher.dart
deleted file mode 100644
index 5e9769b..0000000
--- a/pkgs/test_api/lib/src/expect/prints_matcher.dart
+++ /dev/null
@@ -1,71 +0,0 @@
-// Copyright (c) 2014, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-
-import 'async_matcher.dart';
-import 'expect.dart';
-import 'util/pretty_print.dart';
-
-/// Matches a [Function] that prints text that matches [matcher].
-///
-/// [matcher] may be a String or a [Matcher].
-///
-/// If the function this runs against returns a [Future], all text printed by
-/// the function (using [Zone] scoping) until that Future completes is matched.
-///
-/// This only tracks text printed using the [print] function.
-///
-/// This returns an [AsyncMatcher], so [expect] won't complete until the matched
-/// function does.
-Matcher prints(matcher) => _Prints(wrapMatcher(matcher));
-
-class _Prints extends AsyncMatcher {
-  final Matcher _matcher;
-
-  _Prints(this._matcher);
-
-  // Avoid async/await so we synchronously fail if the function is
-  // synchronous.
-  @override
-  dynamic /*FutureOr<String>*/ matchAsync(item) {
-    if (item is! Function()) return 'was not a unary Function';
-
-    var buffer = StringBuffer();
-    var result = runZoned(item,
-        zoneSpecification: ZoneSpecification(print: (_, __, ____, line) {
-      buffer.writeln(line);
-    }));
-
-    return result is Future
-        ? result.then((_) => _check(buffer.toString()))
-        : _check(buffer.toString());
-  }
-
-  @override
-  Description describe(Description description) =>
-      description.add('prints ').addDescriptionOf(_matcher);
-
-  /// Verifies that [actual] matches [_matcher] and returns a [String]
-  /// description of the failure if it doesn't.
-  String? _check(String actual) {
-    var matchState = {};
-    if (_matcher.matches(actual, matchState)) return null;
-
-    var result = _matcher
-        .describeMismatch(actual, StringDescription(), matchState, false)
-        .toString();
-
-    var buffer = StringBuffer();
-    if (actual.isEmpty) {
-      buffer.writeln('printed nothing');
-    } else {
-      buffer.writeln(indent(prettyPrint(actual), first: 'printed '));
-    }
-    if (result.isNotEmpty) buffer.writeln(indent(result, first: '  which '));
-    return buffer.toString().trimRight();
-  }
-}
diff --git a/pkgs/test_api/lib/src/expect/stream_matcher.dart b/pkgs/test_api/lib/src/expect/stream_matcher.dart
deleted file mode 100644
index 6d7bddf..0000000
--- a/pkgs/test_api/lib/src/expect/stream_matcher.dart
+++ /dev/null
@@ -1,194 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:async/async.dart';
-import 'package:matcher/matcher.dart';
-import 'package:test_api/hooks.dart';
-
-import 'async_matcher.dart';
-import 'util/pretty_print.dart';
-
-/// A matcher that matches events from [Stream]s or [StreamQueue]s.
-///
-/// Stream matchers are designed to make it straightforward to create complex
-/// expectations for streams, and to interleave expectations with the rest of a
-/// test. They can be used on a [Stream] to match all events it emits:
-///
-/// ```dart
-/// expect(stream, emitsInOrder([
-///   // Values match individual events.
-///   "Ready.",
-///
-///   // Matchers also run against individual events.
-///   startsWith("Loading took"),
-///
-///   // Stream matchers can be nested. This asserts that one of two events are
-///   // emitted after the "Loading took" line.
-///   emitsAnyOf(["Succeeded!", "Failed!"]),
-///
-///   // By default, more events are allowed after the matcher finishes
-///   // matching. This asserts instead that the stream emits a done event and
-///   // nothing else.
-///   emitsDone
-/// ]));
-/// ```
-///
-/// It can also match a [StreamQueue], in which case it consumes the matched
-/// events. The call to [expect] returns a [Future] that completes when the
-/// matcher is done matching. You can `await` this to consume different events
-/// at different times:
-///
-/// ```dart
-/// var stdout = StreamQueue(stdoutLineStream);
-///
-/// // Ignore lines from the process until it's about to emit the URL.
-/// await expectLater(stdout, emitsThrough('WebSocket URL:'));
-///
-/// // Parse the next line as a URL.
-/// var url = Uri.parse(await stdout.next);
-/// expect(url.host, equals('localhost'));
-///
-/// // You can match against the same StreamQueue multiple times.
-/// await expectLater(stdout, emits('Waiting for connection...'));
-/// ```
-///
-/// Users can call [StreamMatcher] to create custom matchers.
-abstract class StreamMatcher extends Matcher {
-  /// The description of this matcher.
-  ///
-  /// This is in the subjunctive mood, which means it can be used after the word
-  /// "should". For example, it might be "emit the right events".
-  String get description;
-
-  /// Creates a new [StreamMatcher] described by [description] that matches
-  /// events with [matchQueue].
-  ///
-  /// The [matchQueue] callback is used to implement [StreamMatcher.matchQueue],
-  /// and should follow all the guarantees of that method. In particular:
-  ///
-  /// * If it matches successfully, it should return `null` and possibly consume
-  ///   events.
-  /// * If it fails to match, consume no events and return a description of the
-  ///   failure.
-  /// * The description should be in past tense.
-  /// * The description should be grammatically valid when used after "the
-  ///   stream"—"emitted the wrong events", for example.
-  ///
-  /// The [matchQueue] callback may return the empty string to indicate a
-  /// failure if it has no information to add beyond the description of the
-  /// failure and the events actually emitted by the stream.
-  ///
-  /// The [description] should be in the subjunctive mood. This means that it
-  /// should be grammatically valid when used after the word "should". For
-  /// example, it might be "emit the right events".
-  factory StreamMatcher(Future<String?> Function(StreamQueue) matchQueue,
-      String description) = _StreamMatcher;
-
-  /// Tries to match events emitted by [queue].
-  ///
-  /// If this matches successfully, it consumes the matching events from [queue]
-  /// and returns `null`.
-  ///
-  /// If this fails to match, it doesn't consume any events and returns a
-  /// description of the failure. This description is in the past tense, and
-  /// could grammatically be used after "the stream". For example, it might
-  /// return "emitted the wrong events".
-  ///
-  /// The description string may also be empty, which indicates that the
-  /// matcher's description and the events actually emitted by the stream are
-  /// enough to understand the failure.
-  ///
-  /// If the queue emits an error, that error is re-thrown unless otherwise
-  /// indicated by the matcher.
-  Future<String?> matchQueue(StreamQueue queue);
-}
-
-/// A concrete implementation of [StreamMatcher].
-///
-/// This is separate from the original type to hide the private [AsyncMatcher]
-/// interface.
-class _StreamMatcher extends AsyncMatcher implements StreamMatcher {
-  @override
-  final String description;
-
-  /// The callback used to implement [matchQueue].
-  final Future<String?> Function(StreamQueue) _matchQueue;
-
-  _StreamMatcher(this._matchQueue, this.description);
-
-  @override
-  Future<String?> matchQueue(StreamQueue queue) => _matchQueue(queue);
-
-  @override
-  dynamic /*FutureOr<String>*/ matchAsync(item) {
-    StreamQueue queue;
-    var shouldCancelQueue = false;
-    if (item is StreamQueue) {
-      queue = item;
-    } else if (item is Stream) {
-      queue = StreamQueue(item);
-      shouldCancelQueue = true;
-    } else {
-      return 'was not a Stream or a StreamQueue';
-    }
-
-    // Avoid async/await in the outer method so that we synchronously error out
-    // for an invalid argument type.
-    var transaction = queue.startTransaction();
-    var copy = transaction.newQueue();
-    return matchQueue(copy).then((result) async {
-      // Accept the transaction if the result is null, indicating that the match
-      // succeeded.
-      if (result == null) {
-        transaction.commit(copy);
-        return null;
-      }
-
-      // Get a list of events emitted by the stream so we can emit them as part
-      // of the error message.
-      var replay = transaction.newQueue();
-      var events = <Result?>[];
-      var subscription = Result.captureStreamTransformer
-          .bind(replay.rest.cast())
-          .listen(events.add, onDone: () => events.add(null));
-
-      // Wait on a timer tick so all buffered events are emitted.
-      await Future.delayed(Duration.zero);
-      _unawaited(subscription.cancel());
-
-      var eventsString = events.map((event) {
-        if (event == null) {
-          return 'x Stream closed.';
-        } else if (event.isValue) {
-          return addBullet(event.asValue!.value.toString());
-        } else {
-          var error = event.asError!;
-          var chain = TestHandle.current.formatStackTrace(error.stackTrace);
-          var text = '${error.error}\n$chain';
-          return indent(text, first: '! ');
-        }
-      }).join('\n');
-      if (eventsString.isEmpty) eventsString = 'no events';
-
-      transaction.reject();
-
-      var buffer = StringBuffer();
-      buffer.writeln(indent(eventsString, first: 'emitted '));
-      if (result.isNotEmpty) buffer.writeln(indent(result, first: '  which '));
-      return buffer.toString().trimRight();
-    }, onError: (Object error) {
-      transaction.reject();
-      throw error;
-    }).then((result) {
-      if (shouldCancelQueue) queue.cancel();
-      return result;
-    });
-  }
-
-  @override
-  Description describe(Description description) =>
-      description.add('should ').add(this.description);
-}
-
-void _unawaited(Future<void> f) {}
diff --git a/pkgs/test_api/lib/src/expect/stream_matchers.dart b/pkgs/test_api/lib/src/expect/stream_matchers.dart
deleted file mode 100644
index df2fbbd..0000000
--- a/pkgs/test_api/lib/src/expect/stream_matchers.dart
+++ /dev/null
@@ -1,375 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:async/async.dart';
-import 'package:matcher/matcher.dart';
-
-import 'async_matcher.dart';
-import 'stream_matcher.dart';
-import 'throws_matcher.dart';
-import 'util/pretty_print.dart';
-
-/// Returns a [StreamMatcher] that asserts that the stream emits a "done" event.
-final emitsDone = StreamMatcher(
-    (queue) async => (await queue.hasNext) ? '' : null, 'be done');
-
-/// Returns a [StreamMatcher] for [matcher].
-///
-/// If [matcher] is already a [StreamMatcher], it's returned as-is. If it's any
-/// other [Matcher], this matches a single event that matches that matcher. If
-/// it's any other Object, this matches a single event that's equal to that
-/// object.
-///
-/// This functions like [wrapMatcher] for [StreamMatcher]s: it can convert any
-/// matcher-like value into a proper [StreamMatcher].
-StreamMatcher emits(matcher) {
-  if (matcher is StreamMatcher) return matcher;
-  var wrapped = wrapMatcher(matcher);
-
-  var matcherDescription = wrapped.describe(StringDescription());
-
-  return StreamMatcher((queue) async {
-    if (!await queue.hasNext) return '';
-
-    var matchState = {};
-    var actual = await queue.next;
-    if (wrapped.matches(actual, matchState)) return null;
-
-    var mismatchDescription = StringDescription();
-    wrapped.describeMismatch(actual, mismatchDescription, matchState, false);
-
-    if (mismatchDescription.length == 0) return '';
-    return 'emitted an event that $mismatchDescription';
-  },
-      // TODO(nweiz): add "should" once matcher#42 is fixed.
-      'emit an event that $matcherDescription');
-}
-
-/// Returns a [StreamMatcher] that matches a single error event that matches
-/// [matcher].
-StreamMatcher emitsError(matcher) {
-  var wrapped = wrapMatcher(matcher);
-  var matcherDescription = wrapped.describe(StringDescription());
-  var throwsMatcher = throwsA(wrapped) as AsyncMatcher;
-
-  return StreamMatcher(
-      (queue) => throwsMatcher.matchAsync(queue.next) as Future<String?>,
-      // TODO(nweiz): add "should" once matcher#42 is fixed.
-      'emit an error that $matcherDescription');
-}
-
-/// Returns a [StreamMatcher] that allows (but doesn't require) [matcher] to
-/// match the stream.
-///
-/// This matcher always succeeds; if [matcher] doesn't match, this just consumes
-/// no events.
-StreamMatcher mayEmit(matcher) {
-  var streamMatcher = emits(matcher);
-  return StreamMatcher((queue) async {
-    await queue.withTransaction(
-        (copy) async => (await streamMatcher.matchQueue(copy)) == null);
-    return null;
-  }, 'maybe ${streamMatcher.description}');
-}
-
-/// Returns a [StreamMatcher] that matches the stream if at least one of
-/// [matchers] matches.
-///
-/// If multiple matchers match the stream, this chooses the matcher that
-/// consumes as many events as possible.
-///
-/// If any matchers match the stream, no errors from other matchers are thrown.
-/// If no matchers match and multiple matchers threw errors, the first error is
-/// re-thrown.
-StreamMatcher emitsAnyOf(Iterable matchers) {
-  var streamMatchers = matchers.map(emits).toList();
-  if (streamMatchers.isEmpty) {
-    throw ArgumentError('matcher may not be empty');
-  }
-
-  if (streamMatchers.length == 1) return streamMatchers.first;
-  var description = 'do one of the following:\n'
-      '${bullet(streamMatchers.map((matcher) => matcher.description))}';
-
-  return StreamMatcher((queue) async {
-    var transaction = queue.startTransaction();
-
-    // Allocate the failures list ahead of time so that its order matches the
-    // order of [matchers], and thus the order the matchers will be listed in
-    // the description.
-    var failures = List<String?>.filled(matchers.length, null);
-
-    // The first error thrown. If no matchers match and this exists, we rethrow
-    // it.
-    Object? firstError;
-    StackTrace? firstStackTrace;
-
-    var futures = <Future>[];
-    StreamQueue? consumedMost;
-    for (var i = 0; i < matchers.length; i++) {
-      futures.add(() async {
-        var copy = transaction.newQueue();
-
-        String? result;
-        try {
-          result = await streamMatchers[i].matchQueue(copy);
-        } catch (error, stackTrace) {
-          if (firstError == null) {
-            firstError = error;
-            firstStackTrace = stackTrace;
-          }
-          return;
-        }
-
-        if (result != null) {
-          failures[i] = result;
-        } else if (consumedMost == null ||
-            consumedMost!.eventsDispatched < copy.eventsDispatched) {
-          consumedMost = copy;
-        }
-      }());
-    }
-
-    await Future.wait(futures);
-
-    if (consumedMost == null) {
-      transaction.reject();
-      if (firstError != null) {
-        await Future.error(firstError!, firstStackTrace);
-      }
-
-      var failureMessages = <String>[];
-      for (var i = 0; i < matchers.length; i++) {
-        var message = 'failed to ${streamMatchers[i].description}';
-        if ((failures[i])!.isNotEmpty) {
-          message += message.contains('\n') ? '\n' : ' ';
-          message += 'because it ${failures[i]}';
-        }
-
-        failureMessages.add(message);
-      }
-
-      return 'failed all options:\n${bullet(failureMessages)}';
-    } else {
-      transaction.commit(consumedMost!);
-      return null;
-    }
-  }, description);
-}
-
-/// Returns a [StreamMatcher] that matches the stream if each matcher in
-/// [matchers] matches, one after another.
-///
-/// If any matcher fails to match, this fails and consumes no events.
-StreamMatcher emitsInOrder(Iterable matchers) {
-  var streamMatchers = matchers.map(emits).toList();
-  if (streamMatchers.length == 1) return streamMatchers.first;
-
-  var description = 'do the following in order:\n'
-      '${bullet(streamMatchers.map((matcher) => matcher.description))}';
-
-  return StreamMatcher((queue) async {
-    for (var i = 0; i < streamMatchers.length; i++) {
-      var matcher = streamMatchers[i];
-      var result = await matcher.matchQueue(queue);
-      if (result == null) continue;
-
-      var newResult = "didn't ${matcher.description}";
-      if (result.isNotEmpty) {
-        newResult += newResult.contains('\n') ? '\n' : ' ';
-        newResult += 'because it $result';
-      }
-      return newResult;
-    }
-    return null;
-  }, description);
-}
-
-/// Returns a [StreamMatcher] that matches any number of events followed by
-/// events that match [matcher].
-///
-/// This consumes all events matched by [matcher], as well as all events before.
-/// If the stream emits a done event without matching [matcher], this fails and
-/// consumes no events.
-StreamMatcher emitsThrough(matcher) {
-  var streamMatcher = emits(matcher);
-  return StreamMatcher((queue) async {
-    var failures = <String>[];
-
-    Future<bool> tryHere() => queue.withTransaction((copy) async {
-          var result = await streamMatcher.matchQueue(copy);
-          if (result == null) return true;
-          failures.add(result);
-          return false;
-        });
-
-    while (await queue.hasNext) {
-      if (await tryHere()) return null;
-      await queue.next;
-    }
-
-    // Try after the queue is done in case the matcher can match an empty
-    // stream.
-    if (await tryHere()) return null;
-
-    var result = 'never did ${streamMatcher.description}';
-
-    var failureMessages =
-        bullet(failures.where((failure) => failure.isNotEmpty));
-    if (failureMessages.isNotEmpty) {
-      result += result.contains('\n') ? '\n' : ' ';
-      result += 'because it:\n$failureMessages';
-    }
-
-    return result;
-  }, 'eventually ${streamMatcher.description}');
-}
-
-/// Returns a [StreamMatcher] that matches any number of events that match
-/// [matcher].
-///
-/// This consumes events until [matcher] no longer matches. It always succeeds;
-/// if [matcher] doesn't match, this just consumes no events. It never rethrows
-/// errors.
-StreamMatcher mayEmitMultiple(matcher) {
-  var streamMatcher = emits(matcher);
-
-  var description = streamMatcher.description;
-  description += description.contains('\n') ? '\n' : ' ';
-  description += 'zero or more times';
-
-  return StreamMatcher((queue) async {
-    while (await _tryMatch(queue, streamMatcher)) {
-      // Do nothing; the matcher presumably already consumed events.
-    }
-    return null;
-  }, description);
-}
-
-/// Returns a [StreamMatcher] that matches a stream that never matches
-/// [matcher].
-///
-/// This doesn't complete until the stream emits a done event. It never consumes
-/// any events. It never re-throws errors.
-StreamMatcher neverEmits(matcher) {
-  var streamMatcher = emits(matcher);
-  return StreamMatcher((queue) async {
-    var events = 0;
-    var matched = false;
-    await queue.withTransaction((copy) async {
-      while (await copy.hasNext) {
-        matched = await _tryMatch(copy, streamMatcher);
-        if (matched) return false;
-
-        events++;
-
-        try {
-          await copy.next;
-        } catch (_) {
-          // Ignore errors events.
-        }
-      }
-
-      matched = await _tryMatch(copy, streamMatcher);
-      return false;
-    });
-
-    if (!matched) return null;
-    return "after $events ${pluralize('event', events)} did "
-        '${streamMatcher.description}';
-  }, 'never ${streamMatcher.description}');
-}
-
-/// Returns whether [matcher] matches [queue] at its current position.
-///
-/// This treats errors as failures to match.
-Future<bool> _tryMatch(StreamQueue queue, StreamMatcher matcher) {
-  return queue.withTransaction((copy) async {
-    try {
-      return (await matcher.matchQueue(copy)) == null;
-    } catch (_) {
-      return false;
-    }
-  });
-}
-
-/// Returns a [StreamMatcher] that matches the stream if each matcher in
-/// [matchers] matches, in any order.
-///
-/// If any matcher fails to match, this fails and consumes no events. If the
-/// matchers match in multiple different possible orders, this chooses the order
-/// that consumes as many events as possible.
-///
-/// If any sequence of matchers matches the stream, no errors from other
-/// sequences are thrown. If no sequences match and multiple sequences throw
-/// errors, the first error is re-thrown.
-///
-/// Note that checking every ordering of [matchers] is O(n!) in the worst case,
-/// so this should only be called when there are very few [matchers].
-StreamMatcher emitsInAnyOrder(Iterable matchers) {
-  var streamMatchers = matchers.map(emits).toSet();
-  if (streamMatchers.length == 1) return streamMatchers.first;
-  var description = 'do the following in any order:\n'
-      '${bullet(streamMatchers.map((matcher) => matcher.description))}';
-
-  return StreamMatcher(
-      (queue) async => await _tryInAnyOrder(queue, streamMatchers) ? null : '',
-      description);
-}
-
-/// Returns whether [queue] matches [matchers] in any order.
-Future<bool> _tryInAnyOrder(
-    StreamQueue queue, Set<StreamMatcher> matchers) async {
-  if (matchers.length == 1) {
-    return await matchers.first.matchQueue(queue) == null;
-  }
-
-  var transaction = queue.startTransaction();
-  StreamQueue? consumedMost;
-
-  // The first error thrown. If no matchers match and this exists, we rethrow
-  // it.
-  Object? firstError;
-  StackTrace? firstStackTrace;
-
-  await Future.wait(matchers.map((matcher) async {
-    var copy = transaction.newQueue();
-    try {
-      if (await matcher.matchQueue(copy) != null) return;
-    } catch (error, stackTrace) {
-      if (firstError == null) {
-        firstError = error;
-        firstStackTrace = stackTrace;
-      }
-      return;
-    }
-
-    var rest = Set<StreamMatcher>.from(matchers);
-    rest.remove(matcher);
-
-    try {
-      if (!await _tryInAnyOrder(copy, rest)) return;
-    } catch (error, stackTrace) {
-      if (firstError == null) {
-        firstError = error;
-        firstStackTrace = stackTrace;
-      }
-      return;
-    }
-
-    if (consumedMost == null ||
-        consumedMost!.eventsDispatched < copy.eventsDispatched) {
-      consumedMost = copy;
-    }
-  }));
-
-  if (consumedMost == null) {
-    transaction.reject();
-    if (firstError != null) await Future.error(firstError!, firstStackTrace);
-    return false;
-  } else {
-    transaction.commit(consumedMost!);
-    return true;
-  }
-}
diff --git a/pkgs/test_api/lib/src/expect/throws_matcher.dart b/pkgs/test_api/lib/src/expect/throws_matcher.dart
deleted file mode 100644
index b4f081e..0000000
--- a/pkgs/test_api/lib/src/expect/throws_matcher.dart
+++ /dev/null
@@ -1,135 +0,0 @@
-// Copyright (c) 2014, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-import 'package:test_api/hooks.dart';
-
-import 'async_matcher.dart';
-import 'util/pretty_print.dart';
-
-/// This function is deprecated.
-///
-/// Use [throwsA] instead. We strongly recommend that you add assertions about
-/// at least the type of the error, but you can write `throwsA(anything)` to
-/// mimic the behavior of this matcher.
-@Deprecated('Will be removed in 0.13.0')
-const Matcher throws = Throws();
-
-/// This can be used to match three kinds of objects:
-///
-/// * A [Function] that throws an exception when called. The function cannot
-///   take any arguments. If you want to test that a function expecting
-///   arguments throws, wrap it in another zero-argument function that calls
-///   the one you want to test.
-///
-/// * A [Future] that completes with an exception. Note that this creates an
-///   asynchronous expectation. The call to `expect()` that includes this will
-///   return immediately and execution will continue. Later, when the future
-///   completes, the actual expectation will run.
-///
-/// * A [Function] that returns a [Future] that completes with an exception.
-///
-/// In all three cases, when an exception is thrown, this will test that the
-/// exception object matches [matcher]. If [matcher] is not an instance of
-/// [Matcher], it will implicitly be treated as `equals(matcher)`.
-///
-/// Examples:
-/// ```dart
-/// void functionThatThrows() => throw SomeException();
-///
-/// void functionWithArgument(bool shouldThrow) {
-///   if (shouldThrow) {
-///     throw SomeException();
-///   }
-/// }
-///
-/// Future<void> asyncFunctionThatThrows() async => throw SomeException();
-///
-/// expect(functionThatThrows, throwsA(isA<SomeException>()));
-///
-/// expect(() => functionWithArgument(true), throwsA(isA<SomeException>()));
-///
-/// var future = asyncFunctionThatThrows();
-/// await expectLater(future, throwsA(isA<SomeException>()));
-///
-/// await expectLater(
-///     asyncFunctionThatThrows, throwsA(isA<SomeException>()));
-/// ```
-Matcher throwsA(matcher) => Throws(wrapMatcher(matcher));
-
-/// Use the [throwsA] function instead.
-@Deprecated('Will be removed in 0.13.0')
-class Throws extends AsyncMatcher {
-  final Matcher? _matcher;
-
-  const Throws([Matcher? matcher]) : _matcher = matcher;
-
-  // Avoid async/await so we synchronously fail if we match a synchronous
-  // function.
-  @override
-  dynamic /*FutureOr<String>*/ matchAsync(item) {
-    if (item is! Function && item is! Future) {
-      return 'was not a Function or Future';
-    }
-
-    if (item is Future) {
-      return _matchFuture(item, 'emitted ');
-    }
-
-    try {
-      var value = item();
-      if (value is Future) {
-        return _matchFuture(value, 'returned a Future that emitted ');
-      }
-
-      return indent(prettyPrint(value), first: 'returned ');
-    } catch (error, trace) {
-      return _check(error, trace);
-    }
-  }
-
-  /// Matches [future], using try/catch since `onError` doesn't seem to work
-  /// properly in nnbd.
-  Future<String?> _matchFuture(
-      Future<dynamic> future, String messagePrefix) async {
-    try {
-      var value = await future;
-      return indent(prettyPrint(value), first: messagePrefix);
-    } catch (error, trace) {
-      return _check(error, trace);
-    }
-  }
-
-  @override
-  Description describe(Description description) {
-    if (_matcher == null) {
-      return description.add('throws');
-    } else {
-      return description.add('throws ').addDescriptionOf(_matcher);
-    }
-  }
-
-  /// Verifies that [error] matches [_matcher] and returns a [String]
-  /// description of the failure if it doesn't.
-  String? _check(error, StackTrace? trace) {
-    if (_matcher == null) return null;
-
-    var matchState = {};
-    if (_matcher!.matches(error, matchState)) return null;
-
-    var result = _matcher!
-        .describeMismatch(error, StringDescription(), matchState, false)
-        .toString();
-
-    var buffer = StringBuffer();
-    buffer.writeln(indent(prettyPrint(error), first: 'threw '));
-    if (trace != null) {
-      buffer.writeln(indent(
-          TestHandle.current.formatStackTrace(trace).toString(),
-          first: 'stack '));
-    }
-    if (result.isNotEmpty) buffer.writeln(indent(result, first: 'which '));
-    return buffer.toString().trimRight();
-  }
-}
diff --git a/pkgs/test_api/lib/src/expect/throws_matchers.dart b/pkgs/test_api/lib/src/expect/throws_matchers.dart
deleted file mode 100644
index edf777b..0000000
--- a/pkgs/test_api/lib/src/expect/throws_matchers.dart
+++ /dev/null
@@ -1,69 +0,0 @@
-// Copyright (c) 2014, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-
-import 'throws_matcher.dart';
-
-/// A matcher for functions that throw ArgumentError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsArgumentError = Throws(isArgumentError);
-
-/// A matcher for functions that throw ConcurrentModificationError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsConcurrentModificationError =
-    Throws(isConcurrentModificationError);
-
-/// A matcher for functions that throw CyclicInitializationError.
-///
-/// See [throwsA] for objects that this can be matched against.
-@Deprecated('throwsCyclicInitializationError has been deprecated, because '
-    'the type will longer exists in Dart 3.0. It will now catch any kind of '
-    'error, not only CyclicInitializationError.')
-const Matcher throwsCyclicInitializationError = Throws(TypeMatcher<Error>());
-
-/// A matcher for functions that throw Exception.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsException = Throws(isException);
-
-/// A matcher for functions that throw FormatException.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsFormatException = Throws(isFormatException);
-
-/// A matcher for functions that throw NoSuchMethodError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsNoSuchMethodError = Throws(isNoSuchMethodError);
-
-/// A matcher for functions that throw NullThrownError.
-///
-/// See [throwsA] for objects that this can be matched against.
-@Deprecated('throwsNullThrownError has been deprecated, because '
-    'NullThrownError has been replaced with TypeError. '
-    'Use `throwsA(isA<TypeError>())` instead.')
-const Matcher throwsNullThrownError = Throws(TypeMatcher<TypeError>());
-
-/// A matcher for functions that throw RangeError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsRangeError = Throws(isRangeError);
-
-/// A matcher for functions that throw StateError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsStateError = Throws(isStateError);
-
-/// A matcher for functions that throw Exception.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsUnimplementedError = Throws(isUnimplementedError);
-
-/// A matcher for functions that throw UnsupportedError.
-///
-/// See [throwsA] for objects that this can be matched against.
-const Matcher throwsUnsupportedError = Throws(isUnsupportedError);
diff --git a/pkgs/test_api/lib/src/expect/util/placeholder.dart b/pkgs/test_api/lib/src/expect/util/placeholder.dart
deleted file mode 100644
index ee2dc70..0000000
--- a/pkgs/test_api/lib/src/expect/util/placeholder.dart
+++ /dev/null
@@ -1,16 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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.
-
-/// A class that's used as a default argument to detect whether an argument was
-/// passed.
-///
-/// We use a custom class for this rather than just `const Object()` so that
-/// callers can't accidentally pass the placeholder value.
-class _Placeholder {
-  const _Placeholder();
-}
-
-/// A placeholder to use as a default argument value to detect whether an
-/// argument was passed.
-const placeholder = _Placeholder();
diff --git a/pkgs/test_api/lib/src/expect/util/pretty_print.dart b/pkgs/test_api/lib/src/expect/util/pretty_print.dart
deleted file mode 100644
index f21399d..0000000
--- a/pkgs/test_api/lib/src/expect/util/pretty_print.dart
+++ /dev/null
@@ -1,47 +0,0 @@
-// Copyright (c) 2021, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:matcher/matcher.dart';
-import 'package:term_glyph/term_glyph.dart' as glyph;
-
-/// Indent each line in [string] by [first.length] spaces.
-///
-/// [first] is used in place of the first line's indentation.
-String indent(String text, {required String first}) {
-  final prefix = ' ' * first.length;
-  var lines = text.split('\n');
-  if (lines.length == 1) return '$first$text';
-
-  var buffer = StringBuffer('$first${lines.first}\n');
-
-  // Write out all but the first and last lines with [prefix].
-  for (var line in lines.skip(1).take(lines.length - 2)) {
-    buffer.writeln('$prefix$line');
-  }
-  buffer.write('$prefix${lines.last}');
-  return buffer.toString();
-}
-
-/// Returns a pretty-printed representation of [value].
-///
-/// The matcher package doesn't expose its pretty-print function directly, but
-/// we can use it through StringDescription.
-String prettyPrint(value) =>
-    StringDescription().addDescriptionOf(value).toString();
-
-/// Indents [text], and adds a bullet at the beginning.
-String addBullet(String text) => indent(text, first: '${glyph.bullet} ');
-
-/// Converts [strings] to a bulleted list.
-String bullet(Iterable<String> strings) => strings.map(addBullet).join('\n');
-
-/// Returns [name] if [number] is 1, or the plural of [name] otherwise.
-///
-/// By default, this just adds "s" to the end of [name] to get the plural. If
-/// [plural] is passed, that's used instead.
-String pluralize(String name, int number, {String? plural}) {
-  if (number == 1) return name;
-  if (plural != null) return plural;
-  return '${name}s';
-}
diff --git a/pkgs/test_api/lib/src/frontend/async_matcher.dart b/pkgs/test_api/lib/src/frontend/async_matcher.dart
deleted file mode 100644
index a6b800a..0000000
--- a/pkgs/test_api/lib/src/frontend/async_matcher.dart
+++ /dev/null
@@ -1,9 +0,0 @@
-// Copyright (c) 2021, the Dart project authors.  Please see the AUTHORS file
-// 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.
-
-@Deprecated('Moved to src/expect/async_matcher.dart')
-library test_api.src.frontend.async_matcher;
-
-// Temporary re-export to reduce churn in flutter_test.
-export '../expect/async_matcher.dart';
diff --git a/pkgs/test_api/lib/src/frontend/expect.dart b/pkgs/test_api/lib/src/frontend/expect.dart
deleted file mode 100644
index 4354058..0000000
--- a/pkgs/test_api/lib/src/frontend/expect.dart
+++ /dev/null
@@ -1,9 +0,0 @@
-// Copyright (c) 2021, the Dart project authors.  Please see the AUTHORS file
-// 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.
-
-@Deprecated('Moved to src/expect/expect.dart')
-library test_api.src.frontend.expect;
-
-// Temporary re-export to avoid churn in analyzer tests.
-export '../expect/expect.dart';
diff --git a/pkgs/test_api/lib/test_api.dart b/pkgs/test_api/lib/test_api.dart
index 8e037cc..881226e 100644
--- a/pkgs/test_api/lib/test_api.dart
+++ b/pkgs/test_api/lib/test_api.dart
@@ -6,12 +6,9 @@
     'Please use package:test.')
 library test_api;
 
-export 'expect.dart';
+export 'package:matcher/expect.dart';
+
 export 'hooks.dart' show TestFailure;
 export 'scaffolding.dart';
-// Deprecated exports not surfaced through focused libraries.
-export 'src/expect/expect.dart' show ErrorFormatter;
-export 'src/expect/expect_async.dart' show expectAsync;
-export 'src/expect/throws_matcher.dart' show throws, Throws;
 // Not yet deprecated, but not exposed through focused libraries.
 export 'src/scaffolding/utils.dart' show registerException;
diff --git a/pkgs/test_api/pubspec.yaml b/pkgs/test_api/pubspec.yaml
index 124cd69..541ad86 100644
--- a/pkgs/test_api/pubspec.yaml
+++ b/pkgs/test_api/pubspec.yaml
@@ -20,7 +20,7 @@
 
   # Use a tight version constraint to ensure that a constraint on matcher
   # properly constrains all features it provides.
-  matcher: '>=0.12.11 <0.12.15'
+  matcher: '>=0.12.15 <0.12.16'
 
 dev_dependencies:
   analyzer: '>=2.1.0 <6.0.0'
diff --git a/pkgs/test_api/pubspec_overrides.yaml b/pkgs/test_api/pubspec_overrides.yaml
index bdb2cf4..77c296e 100644
--- a/pkgs/test_api/pubspec_overrides.yaml
+++ b/pkgs/test_api/pubspec_overrides.yaml
@@ -3,3 +3,7 @@
     path: ../test
   test_core:
     path: ../test_core
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3b48930a01f678e2921cea16563af67460e6f765
diff --git a/pkgs/test_api/test/backend/invoker_test.dart b/pkgs/test_api/test/backend/invoker_test.dart
index 490bb02..55e697b 100644
--- a/pkgs/test_api/test/backend/invoker_test.dart
+++ b/pkgs/test_api/test/backend/invoker_test.dart
@@ -184,10 +184,9 @@
           expect(lastState, equals(const State(Status.complete, Result.error)));
           expect(
               error,
-              equals(
-                  'This test failed after it had already completed. Make sure to '
-                  'use [expectAsync]\n'
-                  'or the [completes] matcher when testing async code.'));
+              equals('This test failed after it had already completed.\n'
+                  'Make sure to use a matching library which informs the '
+                  'test runner\nof pending async work.'));
         }
       ]);
 
@@ -316,10 +315,9 @@
         (error) {
           expect(
               error,
-              equals(
-                  'This test failed after it had already completed. Make sure to '
-                  'use [expectAsync]\n'
-                  'or the [completes] matcher when testing async code.'));
+              equals('This test failed after it had already completed.\n'
+                  'Make sure to use a matching library which informs the '
+                  'test runner\nof pending async work.'));
         }
       ]);
 
diff --git a/pkgs/test_api/test/frontend/expect_async_test.dart b/pkgs/test_api/test/frontend/expect_async_test.dart
deleted file mode 100644
index 3752b7b..0000000
--- a/pkgs/test_api/test/frontend/expect_async_test.dart
+++ /dev/null
@@ -1,388 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:fake_async/fake_async.dart';
-import 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../utils_new.dart';
-
-void main() {
-  group('supports a function with this many arguments:', () {
-    test('0', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync0(() {
-          callbackRun = true;
-        })();
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('1', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync1((int arg) {
-          expect(arg, equals(1));
-          callbackRun = true;
-        })(1);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('2', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync2((arg1, arg2) {
-          expect(arg1, equals(1));
-          expect(arg2, equals(2));
-          callbackRun = true;
-        })(1, 2);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('3', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync3((arg1, arg2, arg3) {
-          expect(arg1, equals(1));
-          expect(arg2, equals(2));
-          expect(arg3, equals(3));
-          callbackRun = true;
-        })(1, 2, 3);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('4', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync4((arg1, arg2, arg3, arg4) {
-          expect(arg1, equals(1));
-          expect(arg2, equals(2));
-          expect(arg3, equals(3));
-          expect(arg4, equals(4));
-          callbackRun = true;
-        })(1, 2, 3, 4);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('5', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync5((arg1, arg2, arg3, arg4, arg5) {
-          expect(arg1, equals(1));
-          expect(arg2, equals(2));
-          expect(arg3, equals(3));
-          expect(arg4, equals(4));
-          expect(arg5, equals(5));
-          callbackRun = true;
-        })(1, 2, 3, 4, 5);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('6', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync6((arg1, arg2, arg3, arg4, arg5, arg6) {
-          expect(arg1, equals(1));
-          expect(arg2, equals(2));
-          expect(arg3, equals(3));
-          expect(arg4, equals(4));
-          expect(arg5, equals(5));
-          expect(arg6, equals(6));
-          callbackRun = true;
-        })(1, 2, 3, 4, 5, 6);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-  });
-
-  group('with optional arguments', () {
-    test('allows them to be passed', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync1(([arg = 1]) {
-          expect(arg, equals(2));
-          callbackRun = true;
-        })(2);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('allows them not to be passed', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync1(([arg = 1]) {
-          expect(arg, equals(1));
-          callbackRun = true;
-        })();
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-  });
-
-  group('by default', () {
-    test("won't allow the test to complete until it's called", () async {
-      late void Function() callback;
-      final monitor = TestCaseMonitor.start(() {
-        callback = expectAsync0(() {});
-      });
-
-      await pumpEventQueue();
-      expect(monitor.state, equals(State.running));
-      callback();
-      await monitor.onDone;
-
-      expectTestPassed(monitor);
-    });
-
-    test('may only be called once', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var callback = expectAsync0(() {});
-        callback();
-        callback();
-      });
-
-      expectTestFailed(
-          monitor, 'Callback called more times than expected (1).');
-    });
-  });
-
-  group('with count', () {
-    test(
-        "won't allow the test to complete until it's called at least that "
-        'many times', () async {
-      late void Function() callback;
-      final monitor = TestCaseMonitor.start(() {
-        callback = expectAsync0(() {}, count: 3);
-      });
-
-      await pumpEventQueue();
-      expect(monitor.state, equals(State.running));
-      callback();
-
-      await pumpEventQueue();
-      expect(monitor.state, equals(State.running));
-      callback();
-
-      await pumpEventQueue();
-      expect(monitor.state, equals(State.running));
-      callback();
-
-      await monitor.onDone;
-
-      expectTestPassed(monitor);
-    });
-
-    test("will throw an error if it's called more than that many times",
-        () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var callback = expectAsync0(() {}, count: 3);
-        callback();
-        callback();
-        callback();
-        callback();
-      });
-
-      expectTestFailed(
-          monitor, 'Callback called more times than expected (3).');
-    });
-
-    group('0,', () {
-      test("won't block the test's completion", () {
-        expectAsync0(() {}, count: 0);
-      });
-
-      test("will throw an error if it's ever called", () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expectAsync0(() {}, count: 0)();
-        });
-
-        expectTestFailed(
-            monitor, 'Callback called more times than expected (0).');
-      });
-    });
-  });
-
-  group('with max', () {
-    test('will allow the callback to be called that many times', () {
-      var callback = expectAsync0(() {}, max: 3);
-      callback();
-      callback();
-      callback();
-    });
-
-    test('will allow the callback to be called fewer than that many times', () {
-      var callback = expectAsync0(() {}, max: 3);
-      callback();
-    });
-
-    test("will throw an error if it's called more than that many times",
-        () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var callback = expectAsync0(() {}, max: 3);
-        callback();
-        callback();
-        callback();
-        callback();
-      });
-
-      expectTestFailed(
-          monitor, 'Callback called more times than expected (3).');
-    });
-
-    test('-1, will allow the callback to be called any number of times', () {
-      var callback = expectAsync0(() {}, max: -1);
-      for (var i = 0; i < 20; i++) {
-        callback();
-      }
-    });
-  });
-
-  test('will throw an error if max is less than count', () {
-    expect(() => expectAsync0(() {}, max: 1, count: 2), throwsArgumentError);
-  });
-
-  group('expectAsyncUntil()', () {
-    test("won't allow the test to complete until isDone returns true",
-        () async {
-      late TestCaseMonitor monitor;
-      late Future future;
-      monitor = TestCaseMonitor.start(() {
-        var done = false;
-        var callback = expectAsyncUntil0(() {}, () => done);
-
-        future = () async {
-          await pumpEventQueue();
-          expect(monitor.state, equals(State.running));
-          callback();
-          await pumpEventQueue();
-          expect(monitor.state, equals(State.running));
-          done = true;
-          callback();
-        }();
-      });
-      await monitor.onDone;
-
-      expectTestPassed(monitor);
-      // Ensure that the outer test doesn't complete until the inner future
-      // completes.
-      await future;
-    });
-
-    test("doesn't call isDone until after the callback is called", () {
-      var callbackRun = false;
-      expectAsyncUntil0(() => callbackRun = true, () {
-        expect(callbackRun, isTrue);
-        return true;
-      })();
-    });
-  });
-
-  test('allows errors', () async {
-    var monitor = await TestCaseMonitor.run(() {
-      expect(expectAsync0(() => throw 'oh no'), throwsA('oh no'));
-    });
-
-    expectTestPassed(monitor);
-  });
-
-  test('may be called in a non-test zone', () async {
-    var monitor = await TestCaseMonitor.run(() {
-      var callback = expectAsync0(() {});
-      Zone.root.run(callback);
-    });
-    expectTestPassed(monitor);
-  });
-
-  test('may be called in a FakeAsync zone that does not run further', () async {
-    var monitor = await TestCaseMonitor.run(() {
-      FakeAsync().run((_) {
-        var callback = expectAsync0(() {});
-        callback();
-      });
-    });
-    expectTestPassed(monitor);
-  });
-
-  group('old-style expectAsync()', () {
-    test('works with no arguments', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync(() {
-          callbackRun = true;
-        })();
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('works with dynamic arguments', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync((arg1, arg2) {
-          callbackRun = true;
-        })(1, 2);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('works with non-nullable arguments', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync((int arg1, int arg2) {
-          callbackRun = true;
-        })(1, 2);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test('works with 6 arguments', () async {
-      var callbackRun = false;
-      var monitor = await TestCaseMonitor.run(() {
-        expectAsync((arg1, arg2, arg3, arg4, arg5, arg6) {
-          callbackRun = true;
-        })(1, 2, 3, 4, 5, 6);
-      });
-
-      expectTestPassed(monitor);
-      expect(callbackRun, isTrue);
-    });
-
-    test("doesn't support a function with 7 arguments", () {
-      // ignore: no_leading_underscores_for_local_identifiers
-      expect(() => expectAsync((_a, _b, _c, _d, _e, _f, _g) {}),
-          throwsArgumentError);
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/expect_test.dart b/pkgs/test_api/test/frontend/expect_test.dart
deleted file mode 100644
index cae3511..0000000
--- a/pkgs/test_api/test/frontend/expect_test.dart
+++ /dev/null
@@ -1,35 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test/test.dart';
-
-import '../utils_new.dart';
-
-void main() {
-  group('returned Future from expectLater()', () {
-    test('completes immediately for a sync matcher', () {
-      expect(expectLater(true, isTrue), completes);
-    });
-
-    test('contains the expect failure', () {
-      expect(expectLater(Future.value(true), completion(isFalse)),
-          throwsA(isTestFailure(anything)));
-    });
-
-    test('contains an async error', () {
-      expect(expectLater(Future.error('oh no'), completion(isFalse)),
-          throwsA('oh no'));
-    });
-  });
-
-  group('an async matcher that fails synchronously', () {
-    test('throws synchronously', () {
-      expect(() => expect(() {}, throws), throwsA(isTestFailure(anything)));
-    });
-
-    test('can be used with synchronous operators', () {
-      expect(() {}, isNot(throws));
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/matcher/completion_test.dart b/pkgs/test_api/test/frontend/matcher/completion_test.dart
deleted file mode 100644
index 4f114af..0000000
--- a/pkgs/test_api/test/frontend/matcher/completion_test.dart
+++ /dev/null
@@ -1,192 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../../utils_new.dart';
-
-void main() {
-  group('[doesNotComplete]', () {
-    test('fails when provided a non future', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(10, doesNotComplete);
-      });
-
-      expectTestFailed(monitor, contains('10 is not a Future'));
-    });
-
-    test('succeeds when a future does not complete', () {
-      var completer = Completer();
-      expect(completer.future, doesNotComplete);
-    });
-
-    test('fails when a future does complete', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var completer = Completer();
-        completer.complete(null);
-        expect(completer.future, doesNotComplete);
-      });
-
-      expectTestFailed(
-          monitor,
-          'Future was not expected to complete but completed with a value of'
-          ' null');
-    });
-
-    test('fails when a future completes after the expect', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var completer = Completer();
-        expect(completer.future, doesNotComplete);
-        completer.complete(null);
-      });
-
-      expectTestFailed(
-          monitor,
-          'Future was not expected to complete but completed with a value of'
-          ' null');
-    });
-
-    test('fails when a future eventually completes', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        var completer = Completer();
-        expect(completer.future, doesNotComplete);
-        Future(() async {
-          await pumpEventQueue(times: 10);
-        }).then(completer.complete);
-      });
-
-      expectTestFailed(
-          monitor,
-          'Future was not expected to complete but completed with a value of'
-          ' null');
-    });
-  });
-  group('[completes]', () {
-    test('blocks the test until the Future completes', () async {
-      final completer = Completer<void>();
-      final monitor = TestCaseMonitor.start(() {
-        expect(completer.future, completes);
-      });
-      await pumpEventQueue();
-      expect(monitor.state, State.running);
-      completer.complete();
-      await monitor.onDone;
-      expectTestPassed(monitor);
-    });
-
-    test('with an error', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(Future.error('X'), completes);
-      });
-
-      expect(monitor.state, equals(State.failed));
-      expect(monitor.errors, [isAsyncError(equals('X'))]);
-    });
-
-    test('with a failure', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(Future.error(TestFailure('oh no')), completes);
-      });
-
-      expectTestFailed(monitor, 'oh no');
-    });
-
-    test('with a non-future', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(10, completes);
-      });
-
-      expectTestFailed(
-          monitor,
-          'Expected: completes successfully\n'
-          '  Actual: <10>\n'
-          '   Which: was not a Future\n');
-    });
-
-    test('with a successful future', () {
-      expect(Future.value('1'), completes);
-    });
-  });
-
-  group('[completion]', () {
-    test('blocks the test until the Future completes', () async {
-      final completer = Completer<Object?>();
-      final monitor = TestCaseMonitor.start(() {
-        expect(completer.future, completion(isNull));
-      });
-      await pumpEventQueue();
-      expect(monitor.state, State.running);
-      completer.complete(null);
-      await monitor.onDone;
-      expectTestPassed(monitor);
-    });
-
-    test('with an error', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(Future.error('X'), completion(isNull));
-      });
-
-      expect(monitor.state, equals(State.failed));
-      expect(monitor.errors, [isAsyncError(equals('X'))]);
-    });
-
-    test('with a failure', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(Future.error(TestFailure('oh no')), completion(isNull));
-      });
-
-      expectTestFailed(monitor, 'oh no');
-    });
-
-    test('with a non-future', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(10, completion(equals(10)));
-      });
-
-      expectTestFailed(
-          monitor,
-          'Expected: completes to a value that <10>\n'
-          '  Actual: <10>\n'
-          '   Which: was not a Future\n');
-    });
-
-    test('with an incorrect value', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(Future.value('a'), completion(equals('b')));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: completes to a value that 'b'\n"
-                '  Actual: <'),
-            endsWith('>\n'
-                "   Which: emitted 'a'\n"
-                '            which is different.\n'
-                '                  Expected: b\n'
-                '                    Actual: a\n'
-                '                            ^\n'
-                '                   Differ at offset 0\n')
-          ]));
-    });
-
-    test("blocks expectLater's Future", () async {
-      var completer = Completer();
-      var fired = false;
-      unawaited(expectLater(completer.future, completion(equals(1))).then((_) {
-        fired = true;
-      }));
-
-      await pumpEventQueue();
-      expect(fired, isFalse);
-
-      completer.complete(1);
-      await pumpEventQueue();
-      expect(fired, isTrue);
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/matcher/prints_test.dart b/pkgs/test_api/test/frontend/matcher/prints_test.dart
deleted file mode 100644
index 337a812..0000000
--- a/pkgs/test_api/test/frontend/matcher/prints_test.dart
+++ /dev/null
@@ -1,206 +0,0 @@
-// Copyright (c) 2014, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../../utils_new.dart';
-
-void main() {
-  group('synchronous', () {
-    test('passes with an expected print', () {
-      expect(() => print('Hello, world!'), prints('Hello, world!\n'));
-    });
-
-    test('combines multiple prints', () {
-      expect(() {
-        print('Hello');
-        print('World!');
-      }, prints('Hello\nWorld!\n'));
-    });
-
-    test('works with a Matcher', () {
-      expect(() => print('Hello, world!'), prints(contains('Hello')));
-    });
-
-    test('describes a failure nicely', () async {
-      void local() => print('Hello, world!');
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints('Goodbye, world!\n'));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints 'Goodbye, world!\\n'\n"
-                "            ''\n"
-                '  Actual: <'),
-            endsWith('>\n'
-                "   Which: printed 'Hello, world!\\n'\n"
-                "                    ''\n"
-                '            which is different.\n'
-                '                  Expected: Goodbye, w ...\n'
-                '                    Actual: Hello, wor ...\n'
-                '                            ^\n'
-                '                   Differ at offset 0\n')
-          ]));
-    });
-
-    test('describes a failure with a non-descriptive Matcher nicely', () async {
-      void local() => print('Hello, world!');
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints(contains('Goodbye')));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints contains 'Goodbye'\n"
-                '  Actual: <'),
-            endsWith('>\n'
-                "   Which: printed 'Hello, world!\\n'\n"
-                "                    ''\n")
-          ]));
-    });
-
-    test('describes a failure with no text nicely', () async {
-      void local() {}
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints(contains('Goodbye')));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints contains 'Goodbye'\n"
-                '  Actual: <'),
-            endsWith('>\n'
-                '   Which: printed nothing\n')
-          ]));
-    });
-
-    test('with a non-function', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        expect(10, prints(contains('Goodbye')));
-      });
-
-      expectTestFailed(
-          monitor,
-          "Expected: prints contains 'Goodbye'\n"
-          '  Actual: <10>\n'
-          '   Which: was not a unary Function\n');
-    });
-  });
-
-  group('asynchronous', () {
-    test('passes with an expected print', () {
-      expect(() => Future(() => print('Hello, world!')),
-          prints('Hello, world!\n'));
-    });
-
-    test('combines multiple prints', () {
-      expect(
-          () => Future(() {
-                print('Hello');
-                print('World!');
-              }),
-          prints('Hello\nWorld!\n'));
-    });
-
-    test('works with a Matcher', () {
-      expect(() => Future(() => print('Hello, world!')),
-          prints(contains('Hello')));
-    });
-
-    test('describes a failure nicely', () async {
-      void local() => Future(() => print('Hello, world!'));
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints('Goodbye, world!\n'));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints 'Goodbye, world!\\n'\n"
-                "            ''\n"
-                '  Actual: <'),
-            contains('>\n'
-                "   Which: printed 'Hello, world!\\n'\n"
-                "                    ''\n"
-                '            which is different.\n'
-                '                  Expected: Goodbye, w ...\n'
-                '                    Actual: Hello, wor ...\n'
-                '                            ^\n'
-                '                   Differ at offset 0')
-          ]));
-    });
-
-    test('describes a failure with a non-descriptive Matcher nicely', () async {
-      void local() => Future(() => print('Hello, world!'));
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints(contains('Goodbye')));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints contains 'Goodbye'\n"
-                '  Actual: <'),
-            contains('>\n'
-                "   Which: printed 'Hello, world!\\n'\n"
-                "                    ''")
-          ]));
-    });
-
-    test('describes a failure with no text nicely', () async {
-      void local() => Future.value();
-      var monitor = await TestCaseMonitor.run(() {
-        expect(local, prints(contains('Goodbye')));
-      });
-
-      expectTestFailed(
-          monitor,
-          allOf([
-            startsWith("Expected: prints contains 'Goodbye'\n"
-                '  Actual: <'),
-            contains('>\n'
-                '   Which: printed nothing')
-          ]));
-    });
-
-    test("won't let the test end until the Future completes", () async {
-      final completer = Completer<void>();
-      final monitor = TestCaseMonitor.start(() {
-        expect(() => completer.future, prints(isEmpty));
-      });
-      await pumpEventQueue();
-      expect(monitor.state, State.running);
-      completer.complete();
-      await monitor.onDone;
-      expectTestPassed(monitor);
-    });
-
-    test("blocks expectLater's Future", () async {
-      var completer = Completer();
-      var fired = false;
-
-      unawaited(expectLater(() {
-        scheduleMicrotask(() => print('hello!'));
-        return completer.future;
-      }, prints('hello!\n'))
-          .then((_) {
-        fired = true;
-      }));
-
-      await pumpEventQueue();
-      expect(fired, isFalse);
-
-      completer.complete();
-      await pumpEventQueue();
-      expect(fired, isTrue);
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/matcher/throws_test.dart b/pkgs/test_api/test/frontend/matcher/throws_test.dart
deleted file mode 100644
index a9e76af..0000000
--- a/pkgs/test_api/test/frontend/matcher/throws_test.dart
+++ /dev/null
@@ -1,271 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../../utils_new.dart';
-
-void main() {
-  group('synchronous', () {
-    group('[throws]', () {
-      test('with a function that throws an error', () {
-        expect(() => throw 'oh no', throws);
-      });
-
-      test("with a function that doesn't throw", () async {
-        void local() {}
-        var monitor = await TestCaseMonitor.run(() {
-          expect(local, throws);
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith('Expected: throws\n'
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: returned <null>\n')
-            ]));
-      });
-
-      test('with a non-function', () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(10, throws);
-        });
-
-        expectTestFailed(
-            monitor,
-            'Expected: throws\n'
-            '  Actual: <10>\n'
-            '   Which: was not a Function or Future\n');
-      });
-    });
-
-    group('[throwsA]', () {
-      test('with a function that throws an identical error', () {
-        expect(() => throw 'oh no', throwsA('oh no'));
-      });
-
-      test('with a function that throws a matching error', () {
-        expect(() => throw FormatException('bad'), throwsA(isFormatException));
-      });
-
-      test("with a function that doesn't throw", () async {
-        void local() {}
-        var monitor = await TestCaseMonitor.run(() {
-          expect(local, throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: returned <null>\n')
-            ]));
-      });
-
-      test('with a non-function', () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(10, throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            "Expected: throws 'oh no'\n"
-            '  Actual: <10>\n'
-            '   Which: was not a Function or Future\n');
-      });
-
-      test('with a function that throws the wrong error', () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(() => throw 'aw dang', throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              contains('>\n'
-                  "   Which: threw 'aw dang'\n"
-                  '          stack'),
-              endsWith('          which is different.\n'
-                  '                Expected: oh no\n'
-                  '                  Actual: aw dang\n'
-                  '                          ^\n'
-                  '                 Differ at offset 0\n')
-            ]));
-      });
-    });
-  });
-
-  group('asynchronous', () {
-    group('[throws]', () {
-      test('with a Future that throws an error', () {
-        expect(Future.error('oh no'), throws);
-      });
-
-      test("with a Future that doesn't throw", () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(Future.value(), throws);
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith('Expected: throws\n'
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: emitted <null>\n')
-            ]));
-      });
-
-      test('with a closure that returns a Future that throws an error', () {
-        expect(() => Future.error('oh no'), throws);
-      });
-
-      test("with a closure that returns a Future that doesn't throw", () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(() => Future.value(), throws);
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith('Expected: throws\n'
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: returned a Future that emitted <null>\n')
-            ]));
-      });
-
-      test("won't let the test end until the Future completes", () async {
-        late void Function() callback;
-        final monitor = TestCaseMonitor.start(() {
-          final completer = Completer<void>();
-          expect(completer.future, throws);
-          callback = () => completer.completeError('oh no');
-        });
-        await pumpEventQueue();
-        expect(monitor.state, State.running);
-        callback();
-        await monitor.onDone;
-        expectTestPassed(monitor);
-      });
-    });
-
-    group('[throwsA]', () {
-      test('with a Future that throws an identical error', () {
-        expect(Future.error('oh no'), throwsA('oh no'));
-      });
-
-      test('with a Future that throws a matching error', () {
-        expect(
-            Future.error(FormatException('bad')), throwsA(isFormatException));
-      });
-
-      test("with a Future that doesn't throw", () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(Future.value(), throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: emitted <null>\n')
-            ]));
-      });
-
-      test('with a Future that throws the wrong error', () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(Future.error('aw dang'), throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              contains('>\n'
-                  "   Which: threw 'aw dang'\n")
-            ]));
-      });
-
-      test('with a closure that returns a Future that throws a matching error',
-          () {
-        expect(() => Future.error(FormatException('bad')),
-            throwsA(isFormatException));
-      });
-
-      test("with a closure that returns a Future that doesn't throw", () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(() => Future.value(), throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              endsWith('>\n'
-                  '   Which: returned a Future that emitted <null>\n')
-            ]));
-      });
-
-      test('with closure that returns a Future that throws the wrong error',
-          () async {
-        var monitor = await TestCaseMonitor.run(() {
-          expect(() => Future.error('aw dang'), throwsA('oh no'));
-        });
-
-        expectTestFailed(
-            monitor,
-            allOf([
-              startsWith("Expected: throws 'oh no'\n"
-                  '  Actual: <'),
-              contains('>\n'
-                  "   Which: threw 'aw dang'\n")
-            ]));
-      });
-
-      test("won't let the test end until the Future completes", () async {
-        late void Function() callback;
-        final monitor = TestCaseMonitor.start(() {
-          final completer = Completer<void>();
-          expect(completer.future, throwsA('oh no'));
-          callback = () => completer.completeError('oh no');
-        });
-        await pumpEventQueue();
-        expect(monitor.state, State.running);
-        callback();
-        await monitor.onDone;
-
-        expectTestPassed(monitor);
-      });
-
-      test("blocks expectLater's Future", () async {
-        var completer = Completer();
-        var fired = false;
-        unawaited(expectLater(completer.future, throwsArgumentError).then((_) {
-          fired = true;
-        }));
-
-        await pumpEventQueue();
-        expect(fired, isFalse);
-
-        completer.completeError(ArgumentError('oh no'));
-        await pumpEventQueue();
-        expect(fired, isTrue);
-      });
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/matcher/throws_type_test.dart b/pkgs/test_api/test/frontend/matcher/throws_type_test.dart
deleted file mode 100644
index dfad890..0000000
--- a/pkgs/test_api/test/frontend/matcher/throws_type_test.dart
+++ /dev/null
@@ -1,173 +0,0 @@
-// Copyright (c) 2015, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../../utils_new.dart';
-
-void main() {
-  group('[throwsArgumentError]', () {
-    test('passes when a ArgumentError is thrown', () {
-      expect(() => throw ArgumentError(''), throwsArgumentError);
-    });
-
-    test('fails when a non-ArgumentError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsArgumentError);
-      });
-
-      expectTestFailed(liveTest,
-          startsWith("Expected: throws <Instance of 'ArgumentError'>"));
-    });
-  });
-
-  group('[throwsConcurrentModificationError]', () {
-    test('passes when a ConcurrentModificationError is thrown', () {
-      expect(() => throw ConcurrentModificationError(''),
-          throwsConcurrentModificationError);
-    });
-
-    test('fails when a non-ConcurrentModificationError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsConcurrentModificationError);
-      });
-
-      expectTestFailed(
-          liveTest,
-          startsWith(
-              "Expected: throws <Instance of 'ConcurrentModificationError'>"));
-    });
-  });
-
-  group('[throwsCyclicInitializationError]', () {
-    test('passes when a CyclicInitializationError is thrown', () {
-      expect(
-          () => _CyclicInitializationFailure().x,
-          // ignore: deprecated_member_use
-          throwsCyclicInitializationError);
-    });
-
-    test('fails when a non-CyclicInitializationError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsCyclicInitializationError);
-      });
-
-      expectTestFailed(
-          liveTest, startsWith("Expected: throws <Instance of 'Error'>"));
-    });
-  });
-
-  group('[throwsException]', () {
-    test('passes when a Exception is thrown', () {
-      expect(() => throw Exception(''), throwsException);
-    });
-
-    test('fails when a non-Exception is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw 'oh no', throwsException);
-      });
-
-      expectTestFailed(
-          liveTest, startsWith("Expected: throws <Instance of 'Exception'>"));
-    });
-  });
-
-  group('[throwsFormatException]', () {
-    test('passes when a FormatException is thrown', () {
-      expect(() => throw FormatException(''), throwsFormatException);
-    });
-
-    test('fails when a non-FormatException is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsFormatException);
-      });
-
-      expectTestFailed(liveTest,
-          startsWith("Expected: throws <Instance of 'FormatException'>"));
-    });
-  });
-
-  group('[throwsNoSuchMethodError]', () {
-    test('passes when a NoSuchMethodError is thrown', () {
-      expect(() {
-        (1 as dynamic).notAMethodOnInt();
-      }, throwsNoSuchMethodError);
-    });
-
-    test('fails when a non-NoSuchMethodError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsNoSuchMethodError);
-      });
-
-      expectTestFailed(liveTest,
-          startsWith("Expected: throws <Instance of 'NoSuchMethodError'>"));
-    });
-  });
-
-  group('[throwsRangeError]', () {
-    test('passes when a RangeError is thrown', () {
-      expect(() => throw RangeError(''), throwsRangeError);
-    });
-
-    test('fails when a non-RangeError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsRangeError);
-      });
-
-      expectTestFailed(
-          liveTest, startsWith("Expected: throws <Instance of 'RangeError'>"));
-    });
-  });
-
-  group('[throwsStateError]', () {
-    test('passes when a StateError is thrown', () {
-      expect(() => throw StateError(''), throwsStateError);
-    });
-
-    test('fails when a non-StateError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsStateError);
-      });
-
-      expectTestFailed(
-          liveTest, startsWith("Expected: throws <Instance of 'StateError'>"));
-    });
-  });
-
-  group('[throwsUnimplementedError]', () {
-    test('passes when a UnimplementedError is thrown', () {
-      expect(() => throw UnimplementedError(''), throwsUnimplementedError);
-    });
-
-    test('fails when a non-UnimplementedError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsUnimplementedError);
-      });
-
-      expectTestFailed(liveTest,
-          startsWith("Expected: throws <Instance of 'UnimplementedError'>"));
-    });
-  });
-
-  group('[throwsUnsupportedError]', () {
-    test('passes when a UnsupportedError is thrown', () {
-      expect(() => throw UnsupportedError(''), throwsUnsupportedError);
-    });
-
-    test('fails when a non-UnsupportedError is thrown', () async {
-      var liveTest = await TestCaseMonitor.run(() {
-        expect(() => throw Exception(), throwsUnsupportedError);
-      });
-
-      expectTestFailed(liveTest,
-          startsWith("Expected: throws <Instance of 'UnsupportedError'>"));
-    });
-  });
-}
-
-class _CyclicInitializationFailure {
-  late int x = y;
-  late int y = x;
-}
diff --git a/pkgs/test_api/test/frontend/never_called_test.dart b/pkgs/test_api/test/frontend/never_called_test.dart
deleted file mode 100644
index f4160a3..0000000
--- a/pkgs/test_api/test/frontend/never_called_test.dart
+++ /dev/null
@@ -1,75 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:term_glyph/term_glyph.dart' as glyph;
-import 'package:test/test.dart';
-import 'package:test_api/hooks_testing.dart';
-
-import '../utils_new.dart';
-
-void main() {
-  setUpAll(() {
-    glyph.ascii = true;
-  });
-
-  test("doesn't throw if it isn't called", () async {
-    var monitor = await TestCaseMonitor.run(() {
-      const Stream.empty().listen(neverCalled);
-    });
-
-    expectTestPassed(monitor);
-  });
-
-  group("if it's called", () {
-    test('throws', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        neverCalled();
-      });
-
-      expectTestFailed(
-          monitor,
-          'Callback should never have been called, but it was called with no '
-          'arguments.');
-    });
-
-    test('pretty-prints arguments', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        neverCalled(1, 'foo\nbar');
-      });
-
-      expectTestFailed(
-          monitor,
-          'Callback should never have been called, but it was called with:\n'
-          '* <1>\n'
-          "* 'foo\\n'\n"
-          "    'bar'");
-    });
-
-    test('keeps the test alive', () async {
-      var monitor = await TestCaseMonitor.run(() {
-        pumpEventQueue(times: 10).then(neverCalled);
-      });
-
-      expectTestFailed(
-          monitor,
-          'Callback should never have been called, but it was called with:\n'
-          '* <null>');
-    });
-
-    test("can't be caught", () async {
-      var monitor = await TestCaseMonitor.run(() {
-        try {
-          neverCalled();
-        } catch (_) {
-          // Do nothing.
-        }
-      });
-
-      expectTestFailed(
-          monitor,
-          'Callback should never have been called, but it was called with '
-          'no arguments.');
-    });
-  });
-}
diff --git a/pkgs/test_api/test/frontend/stream_matcher_test.dart b/pkgs/test_api/test/frontend/stream_matcher_test.dart
deleted file mode 100644
index 37d37bf..0000000
--- a/pkgs/test_api/test/frontend/stream_matcher_test.dart
+++ /dev/null
@@ -1,358 +0,0 @@
-// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:async/async.dart';
-import 'package:term_glyph/term_glyph.dart' as glyph;
-import 'package:test/test.dart';
-
-import '../utils_new.dart';
-
-void main() {
-  setUpAll(() {
-    glyph.ascii = true;
-  });
-
-  late Stream stream;
-  late StreamQueue queue;
-  late Stream errorStream;
-  late StreamQueue errorQueue;
-  setUp(() {
-    stream = Stream.fromIterable([1, 2, 3, 4, 5]);
-    queue = StreamQueue(Stream.fromIterable([1, 2, 3, 4, 5]));
-    errorStream = Stream.fromFuture(Future.error('oh no!', StackTrace.current));
-    errorQueue = StreamQueue(
-        Stream.fromFuture(Future.error('oh no!', StackTrace.current)));
-  });
-
-  group('emits()', () {
-    test('matches the first event of a Stream', () {
-      expect(stream, emits(1));
-    });
-
-    test('rejects the first event of a Stream', () {
-      expect(
-          expectLater(stream, emits(2)),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should emit an event that <2>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n')
-          ])));
-    });
-
-    test('matches and consumes the next event of a StreamQueue', () {
-      expect(queue, emits(1));
-      expect(queue.next, completion(equals(2)));
-      expect(queue, emits(3));
-      expect(queue.next, completion(equals(4)));
-    });
-
-    test('rejects and does not consume the first event of a StreamQueue', () {
-      expect(
-          expectLater(queue, emits(2)),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should emit an event that <2>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n')
-          ])));
-
-      expect(queue, emits(1));
-    });
-
-    test('rejects an empty stream', () {
-      expect(
-          expectLater(Stream.empty(), emits(1)),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should emit an event that <1>\n'),
-            endsWith('   Which: emitted x Stream closed.\n')
-          ])));
-    });
-
-    test('forwards a stream error', () {
-      expect(expectLater(errorStream, emits(1)), throwsA('oh no!'));
-    });
-
-    test('wraps a normal matcher', () {
-      expect(queue, emits(lessThan(5)));
-      expect(expectLater(queue, emits(greaterThan(5))),
-          throwsTestFailure(anything));
-    });
-
-    test('returns a StreamMatcher as-is', () {
-      expect(queue, emits(emitsThrough(4)));
-      expect(queue, emits(5));
-    });
-  });
-
-  group('emitsDone', () {
-    test('succeeds for an empty stream', () {
-      expect(Stream.empty(), emitsDone);
-    });
-
-    test('fails for a stream with events', () {
-      expect(
-          expectLater(stream, emitsDone),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should be done\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n')
-          ])));
-    });
-  });
-
-  group('emitsError()', () {
-    test('consumes a matching error', () {
-      expect(errorQueue, emitsError('oh no!'));
-      expect(errorQueue.hasNext, completion(isFalse));
-    });
-
-    test('fails for a non-matching error', () {
-      expect(
-          expectLater(errorStream, emitsError('oh heck')),
-          throwsTestFailure(allOf([
-            startsWith("Expected: should emit an error that 'oh heck'\n"),
-            contains('   Which: emitted ! oh no!\n'),
-            contains('                  x Stream closed.\n'
-                "            which threw 'oh no!'\n"
-                '                  stack '),
-            endsWith('                  which is different.\n'
-                '                        Expected: oh heck\n'
-                '                          Actual: oh no!\n'
-                '                                     ^\n'
-                '                         Differ at offset 3\n')
-          ])));
-    });
-
-    test('fails for a stream with events', () {
-      expect(
-          expectLater(stream, emitsDone),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should be done\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n')
-          ])));
-    });
-  });
-
-  group('mayEmit()', () {
-    test('consumes a matching event', () {
-      expect(queue, mayEmit(1));
-      expect(queue, emits(2));
-    });
-
-    test('allows a non-matching event', () {
-      expect(queue, mayEmit('fish'));
-      expect(queue, emits(1));
-    });
-  });
-
-  group('emitsAnyOf()', () {
-    test('consumes an event that matches a matcher', () {
-      expect(queue, emitsAnyOf([2, 1, 3]));
-      expect(queue, emits(2));
-    });
-
-    test('consumes as many events as possible', () {
-      expect(
-          queue,
-          emitsAnyOf([
-            1,
-            emitsInOrder([1, 2]),
-            emitsInOrder([1, 2, 3])
-          ]));
-
-      expect(queue, emits(4));
-    });
-
-    test('fails if no matchers match', () {
-      expect(
-          expectLater(stream, emitsAnyOf([2, 3, 4])),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should do one of the following:\n'
-                '          * emit an event that <2>\n'
-                '          * emit an event that <3>\n'
-                '          * emit an event that <4>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n'
-                '            which failed all options:\n'
-                '                  * failed to emit an event that <2>\n'
-                '                  * failed to emit an event that <3>\n'
-                '                  * failed to emit an event that <4>\n')
-          ])));
-    });
-
-    test('allows an error if any matcher matches', () {
-      expect(errorStream, emitsAnyOf([1, 2, emitsError('oh no!')]));
-    });
-
-    test('rethrows an error if no matcher matches', () {
-      expect(
-          expectLater(errorStream, emitsAnyOf([1, 2, 3])), throwsA('oh no!'));
-    });
-  });
-
-  group('emitsInOrder()', () {
-    test('consumes matching events', () {
-      expect(queue, emitsInOrder([1, 2, emitsThrough(4)]));
-      expect(queue, emits(5));
-    });
-
-    test("fails if the matchers don't match in order", () {
-      expect(
-          expectLater(queue, emitsInOrder([1, 3, 2])),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should do the following in order:\n'
-                '          * emit an event that <1>\n'
-                '          * emit an event that <3>\n'
-                '          * emit an event that <2>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n'
-                "            which didn't emit an event that <3>\n")
-          ])));
-    });
-  });
-
-  group('emitsThrough()', () {
-    test('consumes events including those matching the matcher', () {
-      expect(queue, emitsThrough(emitsInOrder([3, 4])));
-      expect(queue, emits(5));
-    });
-
-    test('consumes the entire queue with emitsDone', () {
-      expect(queue, emitsThrough(emitsDone));
-      expect(queue.hasNext, completion(isFalse));
-    });
-
-    test('fails if the queue never matches the matcher', () {
-      expect(
-          expectLater(queue, emitsThrough(6)),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should eventually emit an event that <6>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n'
-                '            which never did emit an event that <6>\n')
-          ])));
-    });
-  });
-
-  group('mayEmitMultiple()', () {
-    test('consumes multiple instances of the given matcher', () {
-      expect(queue, mayEmitMultiple(lessThan(3)));
-      expect(queue, emits(3));
-    });
-
-    test('consumes zero instances of the given matcher', () {
-      expect(queue, mayEmitMultiple(6));
-      expect(queue, emits(1));
-    });
-
-    test("doesn't rethrow errors", () {
-      expect(errorQueue, mayEmitMultiple(1));
-      expect(errorQueue, emitsError('oh no!'));
-    });
-  });
-
-  group('neverEmits()', () {
-    test('succeeds if the event never matches', () {
-      expect(queue, neverEmits(6));
-      expect(queue, emits(1));
-    });
-
-    test('fails if the event matches', () {
-      expect(
-          expectLater(stream, neverEmits(4)),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should never emit an event that <4>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n'
-                '            which after 3 events did emit an event that <4>\n')
-          ])));
-    });
-
-    test('fails if emitsDone matches', () {
-      expect(expectLater(stream, neverEmits(emitsDone)),
-          throwsTestFailure(anything));
-    });
-
-    test("doesn't rethrow errors", () {
-      expect(errorQueue, neverEmits(6));
-      expect(errorQueue, emitsError('oh no!'));
-    });
-  });
-
-  group('emitsInAnyOrder()', () {
-    test('consumes events that match in any order', () {
-      expect(queue, emitsInAnyOrder([3, 1, 2]));
-      expect(queue, emits(4));
-    });
-
-    test("fails if the events don't match in any order", () {
-      expect(
-          expectLater(stream, emitsInAnyOrder([4, 1, 2])),
-          throwsTestFailure(allOf([
-            startsWith('Expected: should do the following in any order:\n'
-                '          * emit an event that <4>\n'
-                '          * emit an event that <1>\n'
-                '          * emit an event that <2>\n'),
-            endsWith('   Which: emitted * 1\n'
-                '                  * 2\n'
-                '                  * 3\n'
-                '                  * 4\n'
-                '                  * 5\n'
-                '                  x Stream closed.\n')
-          ])));
-    });
-
-    test("doesn't rethrow if some ordering matches", () {
-      expect(errorQueue, emitsInAnyOrder([emitsDone, emitsError('oh no!')]));
-    });
-
-    test('rethrows if no ordering matches', () {
-      expect(
-          expectLater(errorQueue, emitsInAnyOrder([1, emitsError('oh no!')])),
-          throwsA('oh no!'));
-    });
-  });
-
-  test('A custom StreamController doesn\'t hang on close', () async {
-    var controller = StreamController<void>();
-    var done = expectLater(controller.stream, emits(null));
-    controller.add(null);
-    await done;
-    await controller.close();
-  });
-}
diff --git a/pkgs/test_api/test/import_restrictions_test.dart b/pkgs/test_api/test/import_restrictions_test.dart
index f07c4c6..7dfe3d3 100644
--- a/pkgs/test_api/test/import_restrictions_test.dart
+++ b/pkgs/test_api/test/import_restrictions_test.dart
@@ -38,39 +38,6 @@
       }
     });
   });
-
-  group('expect', () {
-    test('must not be imported from any other library', () async {
-      final entryPoints = [
-        _testApiLibrary('hooks.dart'),
-        _testApiLibrary('scaffolding.dart'),
-        _testApiLibrary('fake.dart')
-      ];
-      await for (final source
-          in importCheck.transitiveSamePackageSources(entryPoints)) {
-        for (final import in source.imports) {
-          expect(import.path, isNot(contains('test_api.dart')),
-              reason: 'Invalid import from ${source.uri} : $import.');
-          expect(import.path, isNot(contains('expect')),
-              reason: 'Invalid import from ${source.uri} : $import.');
-        }
-      }
-    });
-
-    test('may only import hooks', () async {
-      final entryPoint = _testApiLibrary('expect.dart');
-      await for (final source
-          in importCheck.transitiveSamePackageSources([entryPoint])) {
-        // Transitive imports through `hooks.dart` don't follow this restriction
-        if (!source.uri.path.contains('expect')) continue;
-        for (final import in source.imports) {
-          expect(import.path,
-              anyOf(['test_api/hooks.dart', startsWith('test_api/src/expect')]),
-              reason: 'Invalid import from ${source.uri} : $import');
-        }
-      }
-    });
-  });
 }
 
 Uri _testApiLibrary(String path) => Uri.parse('package:test_api/$path');
diff --git a/pkgs/test_api/test/utils_new.dart b/pkgs/test_api/test/utils_new.dart
deleted file mode 100644
index 5aa6974..0000000
--- a/pkgs/test_api/test/utils_new.dart
+++ /dev/null
@@ -1,49 +0,0 @@
-// Copyright (c) 2023, the Dart project authors.  Please see the AUTHORS file
-// 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 'package:test_api/expect.dart';
-import 'package:test_api/hooks_testing.dart';
-
-/// Asserts that [liveTest] has completed and passed.
-///
-/// If the test had any errors, they're surfaced nicely into the outer test.
-void expectTestPassed(TestCaseMonitor monitor) {
-  // Since the test is expected to pass, we forward any current or future errors
-  // to the running test, because they're definitely unexpected and it is most
-  // useful for the error to point directly to the throw point.
-  for (var error in monitor.errors) {
-    Zone.current.handleUncaughtError(error.error, error.stackTrace);
-  }
-  monitor.onError.listen((error) {
-    Zone.current.handleUncaughtError(error.error, error.stackTrace);
-  });
-
-  expect(monitor.state, State.passed);
-}
-
-/// Asserts that [liveTest] failed with a single [TestFailure] whose message
-/// matches [message].
-void expectTestFailed(TestCaseMonitor monitor, message) {
-  expect(monitor.state, State.failed);
-  expect(monitor.errors, [isAsyncError(isTestFailure(message))]);
-}
-
-/// Returns a matcher that matches a [AsyncError] with an `error` field matching
-/// [errorMatcher].
-Matcher isAsyncError(Matcher errorMatcher) =>
-    isA<AsyncError>().having((e) => e.error, 'error', errorMatcher);
-
-/// Returns a matcher that matches a [TestFailure] with the given [message].
-///
-/// [message] can be a string or a [Matcher].
-Matcher isTestFailure(message) => const TypeMatcher<TestFailure>()
-    .having((e) => e.message, 'message', message);
-
-/// Returns a matcher that matches a callback or Future that throws a
-/// [TestFailure] with the given [message].
-///
-/// [message] can be a string or a [Matcher].
-Matcher throwsTestFailure(message) => throwsA(isTestFailure(message));
diff --git a/pkgs/test_core/CHANGELOG.md b/pkgs/test_core/CHANGELOG.md
index 376afec..3de4151 100644
--- a/pkgs/test_core/CHANGELOG.md
+++ b/pkgs/test_core/CHANGELOG.md
@@ -27,6 +27,7 @@
   not statically breaking but it will be confusing for users if it isn't
   supported.
 * **BREAKING** Remove `useDataIsolateStrategy` field from `Configuration`.
+* **BREAKING** Stop exporting APIs from `package:matcher/expect.dart`.
 
 ## 0.4.24
 
diff --git a/pkgs/test_core/lib/test_core.dart b/pkgs/test_core/lib/test_core.dart
index c603586..55c7a50 100644
--- a/pkgs/test_core/lib/test_core.dart
+++ b/pkgs/test_core/lib/test_core.dart
@@ -6,12 +6,8 @@
     'Please use package:test.')
 library test_core;
 
-export 'package:test_api/expect.dart';
 export 'package:test_api/hooks.dart' show TestFailure;
 // Not yet deprecated, but not exposed through focused libraries.
 export 'package:test_api/test_api.dart' show registerException;
-// Deprecated exports not surfaced through focused libraries.
-export 'package:test_api/test_api.dart'
-    show ErrorFormatter, expectAsync, throws, Throws;
 
 export 'scaffolding.dart';
diff --git a/pkgs/test_core/pubspec_overrides.yaml b/pkgs/test_core/pubspec_overrides.yaml
index 2a7f631..2cf7e0a 100644
--- a/pkgs/test_core/pubspec_overrides.yaml
+++ b/pkgs/test_core/pubspec_overrides.yaml
@@ -1,3 +1,7 @@
 dependency_overrides:
   test_api:
     path: ../test_api
+  matcher:
+    git:
+      url: https://github.com/dart-lang/matcher.git
+      ref: 3fc9b3c35c3c0465ebef9158971f8203a4fc9416