| Index: pkg/http/lib/src/client.dart
|
| diff --git a/pkg/http/lib/src/client.dart b/pkg/http/lib/src/client.dart
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..bbee58d2744fa5b7e7bd67b716d4745163160291
|
| --- /dev/null
|
| +++ b/pkg/http/lib/src/client.dart
|
| @@ -0,0 +1,82 @@
|
| +// 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.
|
| +
|
| +library client;
|
| +
|
| +import 'dart:io';
|
| +
|
| +import 'base_client.dart';
|
| +import 'base_request.dart';
|
| +import 'streamed_response.dart';
|
| +import 'utils.dart';
|
| +
|
| +/// An HTTP client which takes care of maintaining persistent connections across
|
| +/// multiple requests to the same server. If you only need to send a single
|
| +/// request, it's usually easier to use [head], [get], [post],
|
| +/// [put], or [delete] instead.
|
| +///
|
| +/// When creating an HTTP client class with additional functionality, it's
|
| +/// recommended that you subclass [BaseClient] and wrap another instance of
|
| +/// [BaseClient] rather than subclassing [Client] directly. This allows all
|
| +/// subclasses of [BaseClient] to be mutually composable.
|
| +class Client extends BaseClient {
|
| + /// The underlying `dart:io` HTTP client.
|
| + HttpClient _inner;
|
| +
|
| + /// Creates a new HTTP client.
|
| + Client() : _inner = new HttpClient();
|
| +
|
| + /// Sends an HTTP request and asynchronously returns the response.
|
| + Future<StreamedResponse> send(BaseRequest request) {
|
| + var stream = request.finalize();
|
| +
|
| + var completer = new Completer<StreamedResponse>();
|
| + var connection = _inner.openUrl(request.method, request.url);
|
| + connection.onError = (e) {
|
| + async.then((_) {
|
| + // TODO(nweiz): remove this when issue 4974 is fixed
|
| + if (completer.future.isComplete) throw e;
|
| +
|
| + completer.completeException(e);
|
| + });
|
| + };
|
| +
|
| + connection.onRequest = (underlyingRequest) {
|
| + underlyingRequest.contentLength = request.contentLength;
|
| + underlyingRequest.persistentConnection = request.persistentConnection;
|
| + request.headers.forEach((name, value) {
|
| + underlyingRequest.headers.set(name, value);
|
| + });
|
| +
|
| + if (stream.closed) {
|
| + underlyingRequest.outputStream.close();
|
| + } else {
|
| + stream.pipe(underlyingRequest.outputStream);
|
| + }
|
| + };
|
| +
|
| + connection.onResponse = (response) {
|
| + var headers = <String>{};
|
| + response.headers.forEach((key, value) => headers[key] = value);
|
| +
|
| + completer.complete(new StreamedResponse(
|
| + response.inputStream,
|
| + response.statusCode,
|
| + response.contentLength,
|
| + headers: headers,
|
| + isRedirect: response.isRedirect,
|
| + persistentConnection: response.persistentConnection,
|
| + reasonPhrase: response.reasonPhrase));
|
| + };
|
| +
|
| + return completer.future;
|
| + }
|
| +
|
| + /// Closes the client. This terminates all active connections. If a client
|
| + /// remains unclosed, the Dart process may not terminate.
|
| + void close() {
|
| + if (_inner != null) _inner.shutdown();
|
| + _inner = null;
|
| + }
|
| +}
|
|
|