From 40a5589e317810230a64e5ced427b76f32ca65b6 Mon Sep 17 00:00:00 2001 From: NachoSoto Date: Thu, 3 Sep 2026 09:22:06 -0700 Subject: [PATCH] Share remote image download pipeline Add a generic raw-data decoder renderer and make RemoteImageRenderer delegate to it. Clients that need custom image decoding or encoded cache payloads can now reuse the established HTTP status and error behavior. --- .../Renderers/RemoteImageRenderer.swift | 32 +++++++++++++++---- 1 file changed, 26 insertions(+), 6 deletions(-) diff --git a/AsyncImageView/Renderers/RemoteImageRenderer.swift b/AsyncImageView/Renderers/RemoteImageRenderer.swift index fed3acd6..34e1ba37 100644 --- a/AsyncImageView/Renderers/RemoteImageRenderer.swift +++ b/AsyncImageView/Renderers/RemoteImageRenderer.swift @@ -20,17 +20,37 @@ public protocol RemoteRenderDataType: RenderDataType { /// download the original image. /// Consider chaining this with `ImageInflaterRenderer`. public final class RemoteImageRenderer: RendererType { - private let session: URLSession + private let renderer: RemoteImageDataRenderer public init(session: URLSession = URLSession.shared) { - self.session = session + self.renderer = RemoteImageDataRenderer(session: session) { UIImage(data: $0) } } public func renderImageWithData(_ data: T) -> SignalProducer { + return self.renderer.renderImageWithData(data) + } +} + +/// `RendererType` which downloads encoded image data and decodes it into a custom render result. +public final class RemoteImageDataRenderer: RendererType { + public typealias Decoder = (Data) -> Result? + + private let session: URLSession + private let decoder: Decoder + + public init( + session: URLSession = URLSession.shared, + decoder: @escaping Decoder + ) { + self.session = session + self.decoder = decoder + } + + public func renderImageWithData(_ data: T) -> SignalProducer { return self.session.reactive.data(with: URLRequest(url: data.imageURL)) .mapError(RemoteImageRendererError.loadingError) .attemptMap { (data, response) in - Result( + Swift.Result( (response as? HTTPURLResponse).map { (data, $0) }, failWith: .invalidResponse ) @@ -47,10 +67,10 @@ public final class RemoteImageRenderer: RendererType { } } .observe(on: QueueScheduler()) - .flatMap(.merge) { data in + .flatMap(.merge) { [decoder = self.decoder] data in return SignalProducer { - Result( - UIImage(data: data), + Swift.Result( + decoder(data), failWith: RemoteImageRendererError.decodingError ) }