The pattern I keep using for handling Future
completions inside of Akka looks something like this:
val caller = sender()
doSomethingAsync().onComplete {
case Success(arg) => caller ! SuccessMsg(arg)
case Failure(e:Exception) => caller ! FailureMsg()
case Failure(e) => throw e // so as to not catch a non-exception Throwable
}
I know i'd much rather map
the future and not use onComplete
, but mixing Future
and Message passing semantics kind of leads you to a place where you end up at a side-effecting operation.
If i leave the Failure(e)
case out, I get a warning that my pattern matching will fail, but it's tedious to have to match for the thing I know i shouldn't be catching. Is there a better way to handle success and appropriate failure?
You can use pipeTo
to send a message from a Future
to an Actor. You can combine it with Future.recover
to handle the Failure
case.
import akka.pattern.pipe
doSomethingAsync()
.map(SuccessMsg)
.recover{ case e: Exception => FailureMsg() }
.pipeTo(caller)