Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Kill or timeout a Future in Scala 2.10

Hi,

I'm using Scala 2.10 with the new futures library and I'm trying to write some code to test an infinite loop. I use a scala.concurrent.Future to run the code with the loop in a separate thread. I would then like to wait a little while to do some testing and then kill off the separate thread/future. I have looked at Await.result but that doesn't actually kill the future. Is there any way to timeout or kill the new Scala 2.10 futures?

I would prefer not having to add external dependencies such as Akka just for this simple part.

like image 839
Stephan Avatar asked Jan 22 '13 00:01

Stephan


2 Answers

Do not try it at home.

import scala.concurrent._
import scala.concurrent.duration._

class MyCustomExecutionContext extends AnyRef with ExecutionContext {
  import ExecutionContext.Implicits.global
  @volatile var lastThread: Option[Thread] = None
  override def execute(runnable: Runnable): Unit = {
    ExecutionContext.Implicits.global.execute(new Runnable() {
      override def run() {
        lastThread = Some(Thread.currentThread)
        runnable.run()
      }
    })
  }
  override def reportFailure(t: Throwable): Unit = ???
}    

implicit val exec = new MyCustomExecutionContext()
val f = future[Int]{ do{}while(true); 1 }
try {
  Await.result(f, 10 seconds) // 100% cpu here
} catch {
  case e: TimeoutException => 
    println("Stopping...")
    exec.lastThread.getOrElse(throw new RuntimeException("Not started"))
      .stop() // 0% cpu here
}
like image 148
idonnie Avatar answered Sep 17 '22 06:09

idonnie


No - you will have to add a flag that your loop checks. If the flag is set, stop the loop. Make sure the flag is at least volatile.

See Java Concurrency in Practice, p 135-137.

like image 29
sourcedelica Avatar answered Sep 21 '22 06:09

sourcedelica