dart-lang / sdk

The Dart SDK, including the VM, JS and Wasm compilers, analysis, core libraries, and more.
https://dart.dev
BSD 3-Clause "New" or "Revised" License
10.31k stars 1.59k forks source link

Provide a canonical base io.HttpClient implementation to use for HttpOverrides #40519

Open davidmorgan opened 4 years ago

davidmorgan commented 4 years ago

Filed on behalf of an internal customer.

dart:io provides a mechanism to swap the implementation of HTTP used by all components in a program with HttpOverrides mechanism.

Real world dart programs resort to this mechanism in several situations:

  1. Fake internet data in tests.
  2. Route HTTP requests through higher level services on platforms with limited networking t
  3. Enforce program-wide policies.

Trying to implement HttpClient from scratch is pretty tricky:

  1. HttpClient has 14 methods, 2 for each HTTP verb. Each of which usually has a one line implementation routing to open(), but this repesents 100 lines of boilerplate in each HttpClient implementation.
  2. HttpClientResponse implements Stream<List>. Stream interface is tricky to implement from scratch, yet (as far as I remember) we can't usefully extend Stream.
  3. HttpHeaders is a class wrapping a simple Map<String, List>, which doesn't bear any dependency on the exact implementation of HTTP, yet needs to be implemented from scratch every time.
  4. All of the above makes users' HttpClient implementation tightly couple to the upstream dart:io interface and make the changes to it burdensome: https://github.com/dart-lang/sdk/issues/39657

Proposal: dart:io should provide some kind of BaseHttpClient implementing HttpClient and allowing users to implement only the transport mechanism. This could be similar to package:http.BaseClient.

@ZichangG

sortie commented 4 years ago

This could potentially be provided in a package.