kotlinforandroid
01/03/2024, 12:55 PM/playlists
to get the list of playlist, and then for each playlist I have to call /playlist/<id>
to get more information about the playlists themselves.
All API calls are suspending. And I always return Either<Error, T>
. Can I somehow leverage Arrow to do n requests in parallel? A higher-level abstraction over parZip
basically. I want to query /playlist/<id>
with 5 simultaneous requests and do it for all playlists returned from /playlists
.dave08
01/03/2024, 12:59 PMsimon.vergauwen
01/03/2024, 1:20 PMparZip
but for Iterable<A>
is parMap
, analogue to map
from Kotlin Std.
data class Playlist(val id: Long, val ids: List<Long>)
object GetPlaylistResult
suspend fun getPlaylists(): List<Playlist> = TODO()
suspend fun getPlaylist(id: Long): GetPlaylistResult = TODO()
fun main(): Unit = runBlocking {
getPlaylists().parMap(concurrency = 5) { playlist ->
getPlaylist(playlist.id)
} // List<GetPlaylistResult>
}
dave08
01/03/2024, 1:47 PMEither
, would parMap short-circuit on error of either getPlaylists or one of the getPlaylist calls?kotlinforandroid
01/03/2024, 1:55 PMinterface API {
fun getPlaylists(): Either<NotAuthenticated, List<Playlist>>
fun getPlaylistDetails(playlistId: PlaylistId): Either<NoPlaylistFound, PlaylistDetails>
}
I think maybe parMapOrAccumulate
might be the function I am looking for.simon.vergauwen
01/03/2024, 2:00 PMsimon.vergauwen
01/03/2024, 2:00 PMfun main(): Unit = runBlocking {
either {
getPlaylists().parMap(concurrency = 5) { playlist ->
getPlaylist(playlist.id).bind()
// GetPlaylistResult
} // List<GetPlaylistResult>
} // Either<E, List<GetPlaylistResult>>
}
simon.vergauwen
01/03/2024, 2:01 PMparMapOrAccumulate
is that parMap
will stop with the first Either.Left
it encounters.
Whilst parMapOrAccumulate
guarantees to finishes all request (unless Throwable
is encountered), and returns all Either.Left
as a NonEmptyList<A> : Iterable<A>
.dave08
01/03/2024, 2:02 PMfun main(): Unit = runBlocking {
either { /// v
getPlaylists().bind().parMap(concurrency = 5) { playlist ->
getPlaylist(playlist.id).bind()
// GetPlaylistResult
} // List<GetPlaylistResult>
} // Either<E, List<GetPlaylistResult>>
}
dave08
01/03/2024, 2:02 PMsimon.vergauwen
01/03/2024, 2:02 PMsimon.vergauwen
01/03/2024, 2:03 PM