FakeHttpClientResponse improvements (#36289)

Update `FakeHttpClientResponse` to be impervious to Dart SDK
changes to the `HttpClientResponse` stream type (between `List<int>`
and `Uint8List`).
diff --git a/packages/flutter_tools/test/src/testbed.dart b/packages/flutter_tools/test/src/testbed.dart
index 32fff92..d01a0cd 100644
--- a/packages/flutter_tools/test/src/testbed.dart
+++ b/packages/flutter_tools/test/src/testbed.dart
@@ -355,66 +355,271 @@
   void writeln([Object obj = '']) {}
 }
 
-class FakeHttpClientResponse extends Stream<Uint8List>
-    implements HttpClientResponse {
+class FakeHttpClientResponse implements HttpClientResponse {
+  final Stream<Uint8List> _delegate = Stream<Uint8List>.fromIterable(const Iterable<Uint8List>.empty());
 
-  final Stream<List<int>> _content = const Stream<List<int>>.empty();
+  @override
+  final HttpHeaders headers = FakeHttpHeaders();
 
   @override
   X509Certificate get certificate => null;
 
   @override
-  HttpClientResponseCompressionState get compressionState => null;
-
-  @override
   HttpConnectionInfo get connectionInfo => null;
 
   @override
   int get contentLength => 0;
 
   @override
-  List<Cookie> get cookies => <Cookie>[];
-
-  @override
-  Future<Socket> detachSocket() async {
-    return null;
+  HttpClientResponseCompressionState get compressionState {
+    return HttpClientResponseCompressionState.decompressed;
   }
 
   @override
-  HttpHeaders get headers => null;
+  List<Cookie> get cookies => null;
 
   @override
-  bool get isRedirect => null;
-
-  @override
-  StreamSubscription<Uint8List> listen(void Function(Uint8List event) onData,
-      {Function onError, void Function() onDone, bool cancelOnError}) {
-    return _content.listen(
-      onData,
-      onError: onError,
-      onDone: onDone,
-      cancelOnError: cancelOnError
-    );
+  Future<Socket> detachSocket() {
+    return Future<Socket>.error(UnsupportedError('Mocked response'));
   }
 
   @override
-  bool get persistentConnection => false;
+  bool get isRedirect => false;
+
+  @override
+  StreamSubscription<Uint8List> listen(void Function(Uint8List event) onData, { Function onError, void Function() onDone, bool cancelOnError }) {
+    return const Stream<Uint8List>.empty().listen(onData, onError: onError, onDone: onDone, cancelOnError: cancelOnError);
+  }
+
+  @override
+  bool get persistentConnection => null;
 
   @override
   String get reasonPhrase => null;
 
   @override
-  Future<HttpClientResponse> redirect(
-      [String method, Uri url, bool followLoops]) {
-    return null;
+  Future<HttpClientResponse> redirect([ String method, Uri url, bool followLoops ]) {
+    return Future<HttpClientResponse>.error(UnsupportedError('Mocked response'));
   }
 
   @override
-  List<RedirectInfo> get redirects => const <RedirectInfo>[];
+  List<RedirectInfo> get redirects => <RedirectInfo>[];
 
   @override
-  int get statusCode => HttpStatus.badRequest;
-  void sendTiming(String category, String variableName, Duration duration, {String label}) {}
+  int get statusCode => 400;
+
+  @override
+  Future<bool> any(bool Function(Uint8List element) test) {
+    return _delegate.any(test);
+  }
+
+  @override
+  Stream<Uint8List> asBroadcastStream({
+    void Function(StreamSubscription<Uint8List> subscription) onListen,
+    void Function(StreamSubscription<Uint8List> subscription) onCancel,
+  }) {
+    return _delegate.asBroadcastStream(onListen: onListen, onCancel: onCancel);
+  }
+
+  @override
+  Stream<E> asyncExpand<E>(Stream<E> Function(Uint8List event) convert) {
+    return _delegate.asyncExpand<E>(convert);
+  }
+
+  @override
+  Stream<E> asyncMap<E>(FutureOr<E> Function(Uint8List event) convert) {
+    return _delegate.asyncMap<E>(convert);
+  }
+
+  @override
+  Stream<R> cast<R>() {
+    return _delegate.cast<R>();
+  }
+
+  @override
+  Future<bool> contains(Object needle) {
+    return _delegate.contains(needle);
+  }
+
+  @override
+  Stream<Uint8List> distinct([bool Function(Uint8List previous, Uint8List next) equals]) {
+    return _delegate.distinct(equals);
+  }
+
+  @override
+  Future<E> drain<E>([E futureValue]) {
+    return _delegate.drain<E>(futureValue);
+  }
+
+  @override
+  Future<Uint8List> elementAt(int index) {
+    return _delegate.elementAt(index);
+  }
+
+  @override
+  Future<bool> every(bool Function(Uint8List element) test) {
+    return _delegate.every(test);
+  }
+
+  @override
+  Stream<S> expand<S>(Iterable<S> Function(Uint8List element) convert) {
+    return _delegate.expand(convert);
+  }
+
+  @override
+  Future<Uint8List> get first => _delegate.first;
+
+  @override
+  Future<Uint8List> firstWhere(
+    bool Function(Uint8List element) test, {
+    List<int> Function() orElse,
+  }) {
+    return _delegate.firstWhere(test, orElse: orElse);
+  }
+
+  @override
+  Future<S> fold<S>(S initialValue, S Function(S previous, Uint8List element) combine) {
+    return _delegate.fold<S>(initialValue, combine);
+  }
+
+  @override
+  Future<dynamic> forEach(void Function(Uint8List element) action) {
+    return _delegate.forEach(action);
+  }
+
+  @override
+  Stream<Uint8List> handleError(
+    Function onError, {
+    bool Function(dynamic error) test,
+  }) {
+    return _delegate.handleError(onError, test: test);
+  }
+
+  @override
+  bool get isBroadcast => _delegate.isBroadcast;
+
+  @override
+  Future<bool> get isEmpty => _delegate.isEmpty;
+
+  @override
+  Future<String> join([String separator = '']) {
+    return _delegate.join(separator);
+  }
+
+  @override
+  Future<Uint8List> get last => _delegate.last;
+
+  @override
+  Future<Uint8List> lastWhere(
+    bool Function(Uint8List element) test, {
+    List<int> Function() orElse,
+  }) {
+    return _delegate.lastWhere(test, orElse: orElse);
+  }
+
+  @override
+  Future<int> get length => _delegate.length;
+
+  @override
+  Stream<S> map<S>(S Function(Uint8List event) convert) {
+    return _delegate.map<S>(convert);
+  }
+
+  @override
+  Future<dynamic> pipe(StreamConsumer<List<int>> streamConsumer) {
+    return _delegate.pipe(streamConsumer);
+  }
+
+  @override
+  Future<Uint8List> reduce(List<int> Function(Uint8List previous, Uint8List element) combine) {
+    return _delegate.reduce(combine);
+  }
+
+  @override
+  Future<Uint8List> get single => _delegate.single;
+
+  @override
+  Future<Uint8List> singleWhere(bool Function(Uint8List element) test, {List<int> Function() orElse}) {
+    return _delegate.singleWhere(test, orElse: orElse);
+  }
+
+  @override
+  Stream<Uint8List> skip(int count) {
+    return _delegate.skip(count);
+  }
+
+  @override
+  Stream<Uint8List> skipWhile(bool Function(Uint8List element) test) {
+    return _delegate.skipWhile(test);
+  }
+
+  @override
+  Stream<Uint8List> take(int count) {
+    return _delegate.take(count);
+  }
+
+  @override
+  Stream<Uint8List> takeWhile(bool Function(Uint8List element) test) {
+    return _delegate.takeWhile(test);
+  }
+
+  @override
+  Stream<Uint8List> timeout(
+    Duration timeLimit, {
+    void Function(EventSink<Uint8List> sink) onTimeout,
+  }) {
+    return _delegate.timeout(timeLimit, onTimeout: onTimeout);
+  }
+
+  @override
+  Future<List<Uint8List>> toList() {
+    return _delegate.toList();
+  }
+
+  @override
+  Future<Set<Uint8List>> toSet() {
+    return _delegate.toSet();
+  }
+
+  @override
+  Stream<S> transform<S>(StreamTransformer<List<int>, S> streamTransformer) {
+    return _delegate.transform<S>(streamTransformer);
+  }
+
+  @override
+  Stream<Uint8List> where(bool Function(Uint8List event) test) {
+    return _delegate.where(test);
+  }
+}
+
+/// A fake [HttpHeaders] that ignores all writes.
+class FakeHttpHeaders extends HttpHeaders {
+  @override
+  List<String> operator [](String name) => <String>[];
+
+  @override
+  void add(String name, Object value) { }
+
+  @override
+  void clear() { }
+
+  @override
+  void forEach(void Function(String name, List<String> values) f) { }
+
+  @override
+  void noFolding(String name) { }
+
+  @override
+  void remove(String name, Object value) { }
+
+  @override
+  void removeAll(String name) { }
+
+  @override
+  void set(String name, Object value) { }
+
+  @override
+  String value(String name) => null;
 }
 
 class FakeFlutterVersion implements FlutterVersion {