Given a method that returns a Future
like this...
def myMethod(name: String, count: Int, default: Boolean): Future[Unit] = {
...
}
... I need to invoke it N times, so I've defined a list of tuples containing the parameters to be passed:
val paramList = List(
("text1", 22, true),
("text2", 55, true),
("text3", 77, false)
)
How do I invoke myMethod
with Future.traverse
?
Future.traverse(paramList)(myMethod _).tupled(/* how do I pass the current tuple here? */)
Two possible approaches:
val futuresFromSequence: Future[List[Unit]] = Future.sequence(paramList.map {
case (a,b,c) => myMethod(a,b,c)
})
val futuresFromTraverse: Future[List[Unit]] = Future.traverse(paramList)(x => x match {
case(a,b,c) => myMethod(a,b,c)
})
Note that traverse
takes some collection and a function from an item of that collection to a future, sequence
instead takes a list of futures and folds it to a future of list.
If you want to stick with the tupled
syntax (which I personally dislike):
Future.traverse(paramList)(x => (myMethod _).tupled(x))
As noted in the comments you may want to run them in serial (although it's not 100% clear from the question), in that case you can use foldLeft
and flatMap
to chain future execution:
myList.foldLeft(Future(List.empty[Unit]))((prevFuture, currentTuple) => {
for {
prev <- prevFuture
curr <- (myMethod _).tupled(currentTuple)
} yield prev :+ curr
})
Where basically the first generator waits for the future in the accumulator to complete before launching the new one, this also returns a Future[List[Unit]]
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With