wbrian
(W. Brian Gourlie)
1
Let's say I have a two types:
struct APIWidget: Codable {
let name: String
let imageUrl: String
}
struct Widget {
let name: String
let image: UIImage
}
And two publishers:
func retrieveWidgets(url: String) -> AnyPublisher<[APIWidget], Never>
func retrieveImage(imageUrl: String) -> AnyPublisher<UIImage, Never>
I'd like to compose these publishers such that I'd map the [APIWidget] returned by retrieveWidgets to [Widget]. I'm having issues conceptualizing this in terms of Combine's operators.
The thing that I'm struggling with is that for each APIWidget, I would need to flatMap onto retrieveImage, but this only seems possible if I were able to convert the AnyPublisher<[APIWidget], Never> into a AnyPublisher<APIWidget, Never>, where the latter publisher would produce a value for every item in the array produced by the first publisher.
Is there a way to do this? Am I going about this the wrong way? One thing I should mention is that the retrieveWidgets publisher necessarily returns an array of APIWidget due to how the backend supplies this data.
Not tested, just from top of my head:
retrieveWidgets(url: myURL)
.flatMap { apiWidgets in
apiWidgets
.publisher
.flatMap { apiWidget in
retrieveImage(imageUrl: apiWidget.imageUrl)
.map { image in
// Build Widget here
}
}
.collect() // collect everything into an array. All publishers must complete first.
}
}
1 Like
wbrian
(W. Brian Gourlie)
3
Thank you! That looks like it should do it.