|
2 | 2 | // for details. All rights reserved. Use of this source code is governed by a
|
3 | 3 | // BSD-style license that can be found in the LICENSE file.
|
4 | 4 |
|
5 |
| -import 'dart:async'; |
6 |
| -import 'dart:io'; |
7 |
| - |
| 5 | +import 'package:async/async.dart'; |
8 | 6 | import 'package:http/http.dart';
|
| 7 | +import 'package:stream_channel/stream_channel.dart'; |
9 | 8 | import 'package:test/test.dart';
|
10 | 9 |
|
| 10 | +import 'utils.dart'; |
| 11 | + |
11 | 12 | /// Tests that the [Client] correctly sends headers in the request.
|
12 | 13 | void testRequestHeaders(Client client) async {
|
13 | 14 | group('client headers', () {
|
| 15 | + late final String host; |
| 16 | + late final StreamChannel<Object?> httpServerChannel; |
| 17 | + late final StreamQueue<Object?> httpServerQueue; |
| 18 | + |
| 19 | + setUpAll(() async { |
| 20 | + httpServerChannel = await startServer('request_headers_server.dart'); |
| 21 | + httpServerQueue = StreamQueue(httpServerChannel.stream); |
| 22 | + host = 'localhost:${await httpServerQueue.next}'; |
| 23 | + }); |
| 24 | + tearDownAll(() => httpServerChannel.sink.add(null)); |
| 25 | + |
14 | 26 | test('single header', () async {
|
15 |
| - late HttpHeaders requestHeaders; |
16 |
| - final server = (await HttpServer.bind('localhost', 0)) |
17 |
| - ..listen((request) async { |
18 |
| - await request.drain<void>(); |
19 |
| - requestHeaders = request.headers; |
20 |
| - unawaited(request.response.close()); |
21 |
| - }); |
22 |
| - await client.get(Uri.http('localhost:${server.port}', ''), |
23 |
| - headers: {'foo': 'bar'}); |
24 |
| - expect(requestHeaders['foo'], ['bar']); |
25 |
| - await server.close(); |
| 27 | + await client.get(Uri.http(host, ''), headers: {'foo': 'bar'}); |
| 28 | + |
| 29 | + final headers = await httpServerQueue.next as Map; |
| 30 | + expect(headers['foo'], ['bar']); |
26 | 31 | });
|
27 | 32 |
|
28 | 33 | test('UPPER case header', () async {
|
29 |
| - late HttpHeaders requestHeaders; |
30 |
| - final server = (await HttpServer.bind('localhost', 0)) |
31 |
| - ..listen((request) async { |
32 |
| - await request.drain<void>(); |
33 |
| - requestHeaders = request.headers; |
34 |
| - unawaited(request.response.close()); |
35 |
| - }); |
36 |
| - await client.get(Uri.http('localhost:${server.port}', ''), |
37 |
| - headers: {'FOO': 'BAR'}); |
| 34 | + await client.get(Uri.http(host, ''), headers: {'FOO': 'BAR'}); |
| 35 | + |
| 36 | + final headers = await httpServerQueue.next as Map; |
38 | 37 | // RFC 2616 14.44 states that header field names are case-insensive.
|
39 | 38 | // http.Client canonicalizes field names into lower case.
|
40 |
| - expect(requestHeaders['foo'], ['BAR']); |
41 |
| - await server.close(); |
| 39 | + expect(headers['foo'], ['BAR']); |
42 | 40 | });
|
43 | 41 |
|
44 | 42 | test('test headers different only in case', () async {
|
45 |
| - // RFC 2616 14.44 states that header field names are case-insensive. |
46 |
| - late HttpHeaders requestHeaders; |
47 |
| - final server = (await HttpServer.bind('localhost', 0)) |
48 |
| - ..listen((request) async { |
49 |
| - await request.drain<void>(); |
50 |
| - requestHeaders = request.headers; |
51 |
| - unawaited(request.response.close()); |
52 |
| - }); |
53 |
| - await client.get(Uri.http('localhost:${server.port}', ''), |
54 |
| - headers: {'foo': 'bar', 'Foo': 'Bar'}); |
55 |
| - expect(requestHeaders['foo']!.single, isIn(['bar', 'Bar'])); |
56 |
| - await server.close(); |
| 43 | + await client |
| 44 | + .get(Uri.http(host, ''), headers: {'foo': 'bar', 'Foo': 'Bar'}); |
| 45 | + |
| 46 | + final headers = await httpServerQueue.next as Map; |
| 47 | + // ignore: avoid_dynamic_calls |
| 48 | + expect(headers['foo']!.single, isIn(['bar', 'Bar'])); |
57 | 49 | });
|
58 | 50 |
|
59 | 51 | test('multiple headers', () async {
|
60 |
| - late HttpHeaders requestHeaders; |
61 |
| - final server = (await HttpServer.bind('localhost', 0)) |
62 |
| - ..listen((request) async { |
63 |
| - await request.drain<void>(); |
64 |
| - requestHeaders = request.headers; |
65 |
| - unawaited(request.response.close()); |
66 |
| - }); |
67 | 52 | // The `http.Client` API does not offer a way of sending the name field
|
68 | 53 | // more than once.
|
69 |
| - await client.get(Uri.http('localhost:${server.port}', ''), |
70 |
| - headers: {'fruit': 'apple', 'color': 'red'}); |
71 |
| - expect(requestHeaders['fruit'], ['apple']); |
72 |
| - expect(requestHeaders['color'], ['red']); |
73 |
| - await server.close(); |
| 54 | + await client |
| 55 | + .get(Uri.http(host, ''), headers: {'fruit': 'apple', 'color': 'red'}); |
| 56 | + |
| 57 | + final headers = await httpServerQueue.next as Map; |
| 58 | + expect(headers['fruit'], ['apple']); |
| 59 | + expect(headers['color'], ['red']); |
74 | 60 | });
|
75 | 61 |
|
76 | 62 | test('multiple values per header', () async {
|
77 |
| - late HttpHeaders requestHeaders; |
78 |
| - final server = (await HttpServer.bind('localhost', 0)) |
79 |
| - ..listen((request) async { |
80 |
| - await request.drain<void>(); |
81 |
| - requestHeaders = request.headers; |
82 |
| - unawaited(request.response.close()); |
83 |
| - }); |
84 | 63 | // The `http.Client` API does not offer a way of sending the same field
|
85 | 64 | // more than once.
|
86 |
| - await client.get(Uri.http('localhost:${server.port}', ''), |
87 |
| - headers: {'list': 'apple, orange'}); |
| 65 | + await client.get(Uri.http(host, ''), headers: {'list': 'apple, orange'}); |
88 | 66 |
|
89 |
| - expect(requestHeaders['list'], ['apple, orange']); |
90 |
| - await server.close(); |
| 67 | + final headers = await httpServerQueue.next as Map; |
| 68 | + expect(headers['list'], ['apple, orange']); |
91 | 69 | });
|
92 | 70 | });
|
93 | 71 | }
|
0 commit comments