Skip to content

Commit d8983fa

Browse files
authored
Add support for setting headers for all requests (#1060)
1 parent c90496e commit d8983fa

File tree

5 files changed

+80
-3
lines changed

5 files changed

+80
-3
lines changed

pkgs/cupertino_http/CHANGELOG.md

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,7 @@
1-
## 1.1.1-wip
1+
## 1.2.0-wip
2+
3+
* Add support for setting additional http headers in
4+
`URLSessionConfiguration`.
25

36
## 1.1.0
47

pkgs/cupertino_http/example/integration_test/url_session_configuration_test.dart

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,38 @@
22
// for details. All rights reserved. Use of this source code is governed by a
33
// BSD-style license that can be found in the LICENSE file.
44

5+
import 'dart:io';
6+
57
import 'package:cupertino_http/cupertino_http.dart';
68
import 'package:integration_test/integration_test.dart';
79
import 'package:test/test.dart';
810

11+
/// Make a HTTP request using the given configuration and return the headers
12+
/// received by the server.
13+
Future<Map<String, List<String>>> sentHeaders(
14+
URLSessionConfiguration config) async {
15+
final session = URLSession.sessionWithConfiguration(config);
16+
final headers = <String, List<String>>{};
17+
final server = (await HttpServer.bind('localhost', 0))
18+
..listen((request) async {
19+
request.headers.forEach((k, v) => headers[k] = v);
20+
await request.drain<void>();
21+
request.response.headers.set('Content-Type', 'text/plain');
22+
request.response.write('Hello World');
23+
await request.response.close();
24+
});
25+
26+
final task = session.dataTaskWithRequest(URLRequest.fromUrl(
27+
Uri(scheme: 'http', host: 'localhost', port: server.port)))
28+
..resume();
29+
while (task.state != URLSessionTaskState.urlSessionTaskStateCompleted) {
30+
await pumpEventQueue();
31+
}
32+
33+
await server.close();
34+
return headers;
35+
}
36+
937
void testProperties(URLSessionConfiguration config) {
1038
group('properties', () {
1139
test('allowsCellularAccess', () {
@@ -32,6 +60,22 @@ void testProperties(URLSessionConfiguration config) {
3260
config.discretionary = false;
3361
expect(config.discretionary, false);
3462
});
63+
test('httpAdditionalHeaders', () async {
64+
expect(config.httpAdditionalHeaders, isNull);
65+
66+
config.httpAdditionalHeaders = {
67+
'User-Agent': 'My Client',
68+
'MyHeader': 'myvalue'
69+
};
70+
expect(config.httpAdditionalHeaders,
71+
{'User-Agent': 'My Client', 'MyHeader': 'myvalue'});
72+
final headers = await sentHeaders(config);
73+
expect(headers, containsPair('user-agent', ['My Client']));
74+
expect(headers, containsPair('myheader', ['myvalue']));
75+
76+
config.httpAdditionalHeaders = null;
77+
expect(config.httpAdditionalHeaders, isNull);
78+
});
3579
test('httpCookieAcceptPolicy', () {
3680
config.httpCookieAcceptPolicy =
3781
HTTPCookieAcceptPolicy.httpCookieAcceptPolicyAlways;

pkgs/cupertino_http/example/lib/main.dart

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,10 @@ import 'book.dart';
1515
void main() {
1616
var clientFactory = Client.new; // The default Client.
1717
if (Platform.isIOS || Platform.isMacOS) {
18-
clientFactory = CupertinoClient.defaultSessionConfiguration.call;
18+
final config = URLSessionConfiguration.ephemeralSessionConfiguration()
19+
..cache = URLCache.withCapacity(memoryCapacity: 2 * 1024 * 1024)
20+
..httpAdditionalHeaders = {'User-Agent': 'Book Agent'};
21+
clientFactory = () => CupertinoClient.fromSessionConfiguration(config);
1922
}
2023
runWithClient(() => runApp(const BookSearchApp()), clientFactory);
2124
}

pkgs/cupertino_http/lib/src/cupertino_api.dart

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -344,6 +344,32 @@ class URLSessionConfiguration
344344
bool get discretionary => _nsObject.discretionary;
345345
set discretionary(bool value) => _nsObject.discretionary = value;
346346

347+
/// Additional headers to send with each request.
348+
///
349+
/// Note that the getter for this field returns a **copy** of the headers.
350+
///
351+
/// See [NSURLSessionConfiguration.HTTPAdditionalHeaders](https://developer.apple.com/documentation/foundation/nsurlsessionconfiguration/1411532-httpadditionalheaders)
352+
Map<String, String>? get httpAdditionalHeaders {
353+
if (_nsObject.HTTPAdditionalHeaders case var additionalHeaders?) {
354+
final headers = ncb.NSDictionary.castFrom(additionalHeaders);
355+
return stringDictToMap(headers);
356+
}
357+
return null;
358+
}
359+
360+
set httpAdditionalHeaders(Map<String, String>? headers) {
361+
if (headers == null) {
362+
_nsObject.HTTPAdditionalHeaders = null;
363+
return;
364+
}
365+
final d = ncb.NSMutableDictionary.alloc(linkedLibs).init();
366+
headers.forEach((key, value) {
367+
d.setObject_forKey_(
368+
value.toNSString(linkedLibs), key.toNSString(linkedLibs));
369+
});
370+
_nsObject.HTTPAdditionalHeaders = d;
371+
}
372+
347373
/// What policy to use when deciding whether to accept cookies.
348374
///
349375
/// See [NSURLSessionConfiguration.HTTPCookieAcceptPolicy](https://developer.apple.com/documentation/foundation/nsurlsessionconfiguration/1408933-httpcookieacceptpolicy).
@@ -441,6 +467,7 @@ class URLSessionConfiguration
441467
'allowsConstrainedNetworkAccess=$allowsConstrainedNetworkAccess '
442468
'allowsExpensiveNetworkAccess=$allowsExpensiveNetworkAccess '
443469
'discretionary=$discretionary '
470+
'httpAdditionalHeaders=$httpAdditionalHeaders '
444471
'httpCookieAcceptPolicy=$httpCookieAcceptPolicy '
445472
'httpShouldSetCookies=$httpShouldSetCookies '
446473
'httpMaximumConnectionsPerHost=$httpMaximumConnectionsPerHost '

pkgs/cupertino_http/pubspec.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
name: cupertino_http
2-
version: 1.1.1-wip
2+
version: 1.2.0-wip
33
description: >-
44
A macOS/iOS Flutter plugin that provides access to the Foundation URL
55
Loading System.

0 commit comments

Comments
 (0)