@@ -33,8 +33,11 @@ public protocol HTTPClientProtocol {
3333 ///
3434 /// - Parameters:
3535 /// - request: The `HTTPClientRequest` to perform.
36+ /// - observabilityScope: the observability scope to emit diagnostics on
37+ /// - progress: A closure to handle progress for example for downloads
3638 /// - callback: A closure to be notified of the completion of the request.
3739 func execute( _ request: HTTPClientRequest ,
40+ observabilityScope: ObservabilityScope ? ,
3841 progress: ProgressHandler ? ,
3942 completion: @escaping CompletionHandler )
4043}
@@ -56,21 +59,19 @@ public struct HTTPClient: HTTPClientProtocol {
5659 public typealias Handler = ( Request , ProgressHandler ? , @escaping ( Result < Response , Error > ) -> Void ) -> Void
5760
5861 public var configuration : HTTPClientConfiguration
59- private let observabilityScope : ObservabilityScope
6062 private let underlying : Handler
6163
6264 // static to share across instances of the http client
6365 private static var hostsErrorsLock = Lock ( )
6466 private static var hostsErrors = [ String: [ Date] ] ( )
6567
66- public init ( configuration: HTTPClientConfiguration = . init( ) , handler: Handler ? = nil , observabilityScope : ObservabilityScope = ObservabilitySystem . topScope ) {
68+ public init ( configuration: HTTPClientConfiguration = . init( ) , handler: Handler ? = nil ) {
6769 self . configuration = configuration
68- self . observabilityScope = observabilityScope
6970 // FIXME: inject platform specific implementation here
7071 self . underlying = handler ?? URLSessionHTTPClient ( ) . execute
7172 }
7273
73- public func execute( _ request: Request , progress: ProgressHandler ? = nil , completion: @escaping CompletionHandler ) {
74+ public func execute( _ request: Request , observabilityScope : ObservabilityScope ? = nil , progress: ProgressHandler ? = nil , completion: @escaping CompletionHandler ) {
7475 // merge configuration
7576 var request = request
7677 if request. options. callbackQueue == nil {
@@ -103,7 +104,9 @@ public struct HTTPClient: HTTPClientProtocol {
103104 // execute
104105 let callbackQueue = request. options. callbackQueue ?? self . configuration. callbackQueue
105106 self . _execute (
106- request: request, requestNumber: 0 ,
107+ request: request,
108+ requestNumber: 0 ,
109+ observabilityScope: observabilityScope,
107110 progress: progress. map { handler in
108111 { received, expected in
109112 callbackQueue. async {
@@ -119,9 +122,9 @@ public struct HTTPClient: HTTPClientProtocol {
119122 )
120123 }
121124
122- private func _execute( request: Request , requestNumber: Int , progress: ProgressHandler ? , completion: @escaping CompletionHandler ) {
125+ private func _execute( request: Request , requestNumber: Int , observabilityScope : ObservabilityScope ? , progress: ProgressHandler ? , completion: @escaping CompletionHandler ) {
123126 if self . shouldCircuitBreak ( request: request) {
124- self . observabilityScope. emit ( warning: " Circuit breaker triggered for \( request. url) " )
127+ observabilityScope? . emit ( warning: " Circuit breaker triggered for \( request. url) " )
125128 return completion ( . failure( HTTPClientError . circuitBreakerTriggered) )
126129 }
127130
@@ -145,10 +148,10 @@ public struct HTTPClient: HTTPClientProtocol {
145148 self . recordErrorIfNecessary ( response: response, request: request)
146149 // handle retry strategy
147150 if let retryDelay = self . shouldRetry ( response: response, request: request, requestNumber: requestNumber) {
148- self . observabilityScope. emit ( warning: " \( request. url) failed, retrying in \( retryDelay) " )
151+ observabilityScope? . emit ( warning: " \( request. url) failed, retrying in \( retryDelay) " )
149152 // TODO: dedicated retry queue?
150153 return self . configuration. callbackQueue. asyncAfter ( deadline: . now( ) + retryDelay) {
151- self . _execute ( request: request, requestNumber: requestNumber + 1 , progress: progress, completion: completion)
154+ self . _execute ( request: request, requestNumber: requestNumber + 1 , observabilityScope : observabilityScope , progress: progress, completion: completion)
152155 }
153156 }
154157 // check for valid response codes
@@ -220,24 +223,24 @@ public struct HTTPClient: HTTPClientProtocol {
220223}
221224
222225public extension HTTPClient {
223- func head( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , completion: @escaping ( Result < Response , Error > ) -> Void ) {
224- self . execute ( Request ( method: . head, url: url, headers: headers, body: nil , options: options) , completion: completion)
226+ func head( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , observabilityScope : ObservabilityScope ? = . none , completion: @escaping ( Result < Response , Error > ) -> Void ) {
227+ self . execute ( Request ( method: . head, url: url, headers: headers, body: nil , options: options) , observabilityScope : observabilityScope , completion: completion)
225228 }
226229
227- func get( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , completion: @escaping ( Result < Response , Error > ) -> Void ) {
228- self . execute ( Request ( method: . get, url: url, headers: headers, body: nil , options: options) , completion: completion)
230+ func get( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , observabilityScope : ObservabilityScope ? = . none , completion: @escaping ( Result < Response , Error > ) -> Void ) {
231+ self . execute ( Request ( method: . get, url: url, headers: headers, body: nil , options: options) , observabilityScope : observabilityScope , completion: completion)
229232 }
230233
231- func put( _ url: URL , body: Data ? , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , completion: @escaping ( Result < Response , Error > ) -> Void ) {
232- self . execute ( Request ( method: . put, url: url, headers: headers, body: body, options: options) , completion: completion)
234+ func put( _ url: URL , body: Data ? , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , observabilityScope : ObservabilityScope ? = . none , completion: @escaping ( Result < Response , Error > ) -> Void ) {
235+ self . execute ( Request ( method: . put, url: url, headers: headers, body: body, options: options) , observabilityScope : observabilityScope , completion: completion)
233236 }
234237
235- func post( _ url: URL , body: Data ? , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , completion: @escaping ( Result < Response , Error > ) -> Void ) {
236- self . execute ( Request ( method: . post, url: url, headers: headers, body: body, options: options) , completion: completion)
238+ func post( _ url: URL , body: Data ? , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , observabilityScope : ObservabilityScope ? = . none , completion: @escaping ( Result < Response , Error > ) -> Void ) {
239+ self . execute ( Request ( method: . post, url: url, headers: headers, body: body, options: options) , observabilityScope : observabilityScope , completion: completion)
237240 }
238241
239- func delete( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , completion: @escaping ( Result < Response , Error > ) -> Void ) {
240- self . execute ( Request ( method: . delete, url: url, headers: headers, body: nil , options: options) , completion: completion)
242+ func delete( _ url: URL , headers: HTTPClientHeaders = . init( ) , options: Request . Options = . init( ) , observabilityScope : ObservabilityScope ? = . none , completion: @escaping ( Result < Response , Error > ) -> Void ) {
243+ self . execute ( Request ( method: . delete, url: url, headers: headers, body: nil , options: options) , observabilityScope : observabilityScope , completion: completion)
241244 }
242245}
243246
0 commit comments