Skip to content

Commit

Permalink
ETagManager.httpResultFromCacheOrBackend: return response headers (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
NachoSoto authored Jun 19, 2023
1 parent fdcb64d commit 5c35df2
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 19 deletions.
16 changes: 9 additions & 7 deletions Sources/Networking/HTTPClient/ETagManager.swift
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,8 @@ class ETagManager {
.compactMapValues { $0 }
}

/// - Returns: `response` if a cached response couldn't be fetched,
/// or the cached `HTTPResponse`, always including the headers in `response`.
func httpResultFromCacheOrBackend(with response: HTTPResponse<Data?>,
request: URLRequest,
retried: Bool) -> HTTPResponse<Data>? {
Expand All @@ -99,7 +101,8 @@ class ETagManager {
let newResponse = storedResponse.withUpdatedValidationTime()

self.storeIfPossible(newResponse, for: request)
return newResponse.asResponse(withRequestDate: response.requestDate)
return newResponse.asResponse(withRequestDate: response.requestDate,
headers: response.responseHeaders)
}
if retried {
Logger.warn(
Expand Down Expand Up @@ -148,10 +151,6 @@ private extension ETagManager {
}
}

func storedHTTPResponse(for request: URLRequest, withRequestDate requestDate: Date?) -> HTTPResponse<Data>? {
return self.storedETagAndResponse(for: request)?.asResponse(withRequestDate: requestDate)
}

func storeStatusCodeAndResponseIfNoError(for request: URLRequest,
response: HTTPResponse<Data?>,
eTag: String) {
Expand Down Expand Up @@ -246,10 +245,13 @@ extension ETagManager.Response {
return try? JSONEncoder.default.encode(self)
}

fileprivate func asResponse(withRequestDate requestDate: Date?) -> HTTPResponse<Data> {
fileprivate func asResponse(
withRequestDate requestDate: Date?,
headers: HTTPClient.ResponseHeaders
) -> HTTPResponse<Data> {
return HTTPResponse(
statusCode: self.statusCode,
responseHeaders: [:],
responseHeaders: headers,
body: self.data,
requestDate: requestDate,
verificationResult: self.verificationResult
Expand Down
25 changes: 15 additions & 10 deletions Tests/UnitTests/Networking/ETagManagerTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -45,17 +45,22 @@ class ETagManagerTests: TestCase {
let request = URLRequest(url: Self.testURL)
let cachedResponse = self.mockStoredETagResponse(for: Self.testURL, statusCode: .success, eTag: eTag)

let response = self.eTagManager.httpResultFromCacheOrBackend(
with: self.responseForTest(url: Self.testURL,
body: nil,
eTag: eTag,
statusCode: .notModified),
request: request,
retried: false
let response = try XCTUnwrap(
self.eTagManager.httpResultFromCacheOrBackend(
with: self.responseForTest(url: Self.testURL,
body: nil,
eTag: eTag,
statusCode: .notModified),
request: request,
retried: false
)
)
expect(response).toNot(beNil())
expect(response?.statusCode) == .success
expect(response?.body) == cachedResponse

expect(response.statusCode) == .success
expect(response.body) == cachedResponse
expect(response.responseHeaders).toNot(beEmpty())
expect(Set(response.responseHeaders.keys.compactMap { $0 as? String }))
== Set(self.getHeaders(eTag: eTag).keys)
}

func testValidationTimeIsUpdatedWhenUsingStoredResponse() throws {
Expand Down
10 changes: 8 additions & 2 deletions Tests/UnitTests/Networking/HTTPClientTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -1069,11 +1069,16 @@ final class HTTPClientTests: BaseHTTPClientTests {
let eTag = "tag"
let requestDate = Date().addingTimeInterval(-1000000)

let headers: [String: String] = [
HTTPClient.ResponseHeader.contentType.rawValue: "application/json",
HTTPClient.ResponseHeader.signature.rawValue: UUID().uuidString
]

self.eTagManager.stubResponseEtag(eTag)
self.eTagManager.shouldReturnResultFromBackend = false
self.eTagManager.stubbedHTTPResultFromCacheOrBackendResult = .init(
statusCode: .success,
responseHeaders: [:],
responseHeaders: headers,
body: mockedCachedResponse,
requestDate: requestDate,
verificationResult: .notRequested
Expand All @@ -1084,7 +1089,7 @@ final class HTTPClientTests: BaseHTTPClientTests {

return .init(data: Data(),
statusCode: .notModified,
headers: nil)
headers: headers)
}

let response: HTTPResponse<Data>.Result? = waitUntilValue { completion in
Expand All @@ -1098,6 +1103,7 @@ final class HTTPClientTests: BaseHTTPClientTests {
expect(response?.value?.body) == mockedCachedResponse
expect(response?.value?.requestDate) == requestDate
expect(response?.value?.verificationResult) == .notRequested
expect(response?.value?.responseHeaders).to(haveCount(headers.count))

expect(self.eTagManager.invokedETagHeaderParametersList).to(haveCount(1))
expect(self.eTagManager.invokedETagHeaderParameters?.withSignatureVerification) == false
Expand Down

0 comments on commit 5c35df2

Please sign in to comment.