Reputation:
I'm trying to wait for a function to finish or timeout after 5 seconds, but whatever I do, I can't prevent the following exception. Interestingly it is caught by the parent actor:
java.util.concurrent.TimeoutException: Futures timed out after [5 seconds]
One of the solutions that I tried (from this question):
val f = Future { dockerClient.execStartCmd(execCreateCmdResponse.getId()).exec() }
val result: Try[InputStream] = Await.ready(f, 5.seconds).value.get
val resultEither = result match {
case Success(t) => log.info("right")
case Failure(e) => log.info("left")
}
Upvotes: 1
Views: 2596
Reputation: 7275
Indeed it's possible to achieve this with akka ask pattern. But there is a different solution that can be used without akka.
Wrap your blocking Await
code into another Future
and register onComplete
function
import concurrent.ExecutionContext.Implicits.global
import scala.concurrent.duration._
import scala.concurrent.{Await, Future}
import scala.util.{Failure, Success, Try}
val sleepTimeout = 1*1000
val f = Future( Thread.sleep(sleepTimeout); Try(10))
val timeoutFuture = Future(Await.result(f, 5.seconds))
timeoutFuture.onComplete {
case Success(Success(t)) => println(t)
case Success(Failure(ex)) => println("error on Try" + ex.getMessage)
case Failure(e) => println("timeout " + e.getMessage)
}
Explaining match cases
Success(Success(t))
First Success
is for the timeoutFuture
, it means it did not timeout. Second Success
is for Try
- means no exception were thrown.Success(Failure(ex))
same as first but there is exception within Try
Failure(e)
this is where timeout is handled. Upvotes: 3