Skip to content

Instantly share code, notes, and snippets.

@lgiorda
Created June 14, 2012 21:15
Show Gist options
  • Save lgiorda/2933001 to your computer and use it in GitHub Desktop.
Save lgiorda/2933001 to your computer and use it in GitHub Desktop.
Akka Futures, Actors, and timeouts..
object FuturesTimeoutApp extends App {
implicit val timeout = Timeout(10 seconds)
val actorSystem = ActorSystem.create("TimeoutActorSystem")
val actorA = actorSystem.actorOf(Props[ActorA],"actorA")
var responseFuture = actorA ? DoCalculateActorA(6) mapTo manifest[Int]
var response = Await.result(responseFuture, 35 seconds) // yes, blocking is bad...bear with us..
println("Response received finally 1:" + response)
val responseFuture2 = actorA ? DoCalculateActorA(10) mapTo manifest[Int]
val response2 = Await.result(responseFuture2, 60 seconds)
println("Response received finally 2:" + response2)
}
class ActorA extends Actor {
implicit val timeout = Timeout(30 seconds)
import context.dispatcher
def receive = {
case DoCalculateActorA(n) =>
val router = context.actorOf(Props[ActorB].withRouter(RoundRobinRouter(n)))
println("Sending futures to ActorB "+n+" times")
val futures = for (i <- 1 to n) yield {
router ? DoCalculateActorB mapTo manifest[DoneFromActorB]
}
println("Done sending all futures to Actor B")
val returnVal = Future.sequence(futures).map(f => f.foldLeft(0)((r1,r2) => r1 + r2.result))
println("Piping futures back to sender from Actor A")
returnVal pipeTo sender
}
}
class ActorB extends Actor {
import context.dispatcher
def receive = {
case DoCalculateActorB => println("Putting actor ("+self.path.name+","+hashCode+") to sleep for 3500ms")
val future = Future {Thread.sleep(3500)}
Await.result(future, 6 seconds)
println("Future in Actor ("+self.path.name+","+hashCode+")is Done. Returning")
sender ! DoneFromActorB(4)
}
}
case class DoCalculateActorA(numberOfCalcs:Int)
case object DoCalculateActorB
case class DoneFromActorB(result:Int)
case class CalculatedResult(result:Long)
@rkuhn
Copy link

rkuhn commented Jun 15, 2012

lines 46–47 are an anti-pattern: never ever do that! Instead of blocking one thread you simply block two, leading to thread starvation which is the problem in this program. Using Await.result within an actor is in itself something which I cannot find a valid use-case for.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment