Skip to content

Commit 56b2c36

Browse files
authored
fix(auth): disable URL caching in FoundationClientEngine (#4238)
The FoundationClientEngine is the base HTTP client used by the AWS SDK service clients (Cognito Identity / Identity Provider, etc.) for credential and token exchange. It previously used URLSession.shared, whose default configuration includes an on-disk URLCache. As a result, responses carrying Cognito tokens and AWS credentials were persisted to the app container's Cache.db, where they could be recovered by inspecting the device. Use a dedicated URLSession with urlCache = nil and a reloadIgnoringLocalCacheData policy so these responses are never written to disk. This mirrors the cache-disabling behavior already applied to the Hosted UI URLSession in AWSCognitoAuthPlugin+Configure.
1 parent 9db19e5 commit 56b2c36

2 files changed

Lines changed: 45 additions & 2 deletions

File tree

AmplifyPlugins/Core/AmplifyCredentials/CustomHttpClientEngine/FoundationClientEngine.swift

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,12 @@ import SmithyHTTPAPI
1111

1212
@_spi(FoundationClientEngine)
1313
public struct FoundationClientEngine: HTTPClient {
14+
let urlSession: URLSession
15+
1416
public func send(request: SmithyHTTPAPI.HTTPRequest) async throws -> SmithyHTTPAPI.HTTPResponse {
1517
let urlRequest = try await URLRequest(from: request)
1618

17-
let (data, response) = try await URLSession.shared.data(for: urlRequest)
19+
let (data, response) = try await urlSession.data(for: urlRequest)
1820
guard let httpURLResponse = response as? HTTPURLResponse else {
1921
// This shouldn't be necessary because we're only making HTTP requests.
2022
// `URLResponse` should always be a `HTTPURLResponse`.
@@ -30,7 +32,16 @@ public struct FoundationClientEngine: HTTPClient {
3032
return httpResponse
3133
}
3234

33-
public init() {}
35+
public init() {
36+
// These requests carry Cognito tokens and AWS credentials. Disable URL
37+
// caching so that responses are never persisted to disk (e.g. Cache.db),
38+
// where they could be recovered by inspecting the app container. This
39+
// mirrors the cache-disabling behavior used for the Hosted UI session.
40+
let configuration = URLSessionConfiguration.default
41+
configuration.urlCache = nil
42+
configuration.requestCachePolicy = .reloadIgnoringLocalCacheData
43+
self.urlSession = URLSession(configuration: configuration)
44+
}
3445

3546
/// no-op
3647
func close() async {}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
//
2+
// Copyright Amazon.com Inc. or its affiliates.
3+
// All Rights Reserved.
4+
//
5+
// SPDX-License-Identifier: Apache-2.0
6+
//
7+
8+
@_spi(FoundationClientEngine)
9+
@testable import InternalAmplifyCredentials
10+
import XCTest
11+
12+
class FoundationClientEngineTests: XCTestCase {
13+
14+
/// Given: A `FoundationClientEngine`.
15+
/// When: The engine is initialized.
16+
/// Then: Its `URLSession` has URL caching disabled so that responses
17+
/// carrying Cognito tokens / AWS credentials are never persisted
18+
/// to disk (e.g. Cache.db).
19+
func test_urlSession_disablesCaching() {
20+
let engine = FoundationClientEngine()
21+
let configuration = engine.urlSession.configuration
22+
23+
XCTAssertNil(
24+
configuration.urlCache,
25+
"URLSession must not have a URLCache, otherwise credential responses are persisted to disk."
26+
)
27+
XCTAssertEqual(
28+
configuration.requestCachePolicy,
29+
.reloadIgnoringLocalCacheData
30+
)
31+
}
32+
}

0 commit comments

Comments
 (0)