From e99fb0c93842d517b8a185458f405bace2bbb46b Mon Sep 17 00:00:00 2001 From: Vojin Jovanovic Date: Fri, 18 May 2012 17:53:05 +0200 Subject: Adding the Actor Migration Kit. Kit consists of: 1) The StashingActor which adopts an interface similar to Akka. 2) Props mockup for creating Akka like code 3) Pattern mockup 4) Test cases for every step in the migration. 5) MigrationSystem which will paired on the Akka side. Review of the code : @phaller Review of the build: @jsuereth --- test/files/jvm/actmig-loop-react.scala | 170 +++++++++++++++++++++++++++++++++ 1 file changed, 170 insertions(+) create mode 100644 test/files/jvm/actmig-loop-react.scala (limited to 'test/files/jvm/actmig-loop-react.scala') diff --git a/test/files/jvm/actmig-loop-react.scala b/test/files/jvm/actmig-loop-react.scala new file mode 100644 index 0000000000..8452f9766a --- /dev/null +++ b/test/files/jvm/actmig-loop-react.scala @@ -0,0 +1,170 @@ +import scala.actors.MigrationSystem._ +import scala.actors.Actor._ +import scala.actors.{ Actor, StashingActor, ActorRef, Props, MigrationSystem, PoisonPill } +import java.util.concurrent.{ TimeUnit, CountDownLatch } +import scala.collection.mutable.ArrayBuffer + +object Test { + + def testLoopWithConditionReact() = { + // Snippet showing composition of receives + // Loop with Condition Snippet - before + val myActor = actor { + var c = true + loopWhile(c) { + react { + case x: Int => + // do task + println("do task") + if (x == 42) c = false + } + } + } + + myActor.start() + myActor ! 1 + myActor ! 42 + + // Loop with Condition Snippet - migrated + val myAkkaActor = MigrationSystem.actorOf(Props(() => new StashingActor { + + def receive = { + case x: Int => + // do task + println("do task") + if (x == 42) context.stop(self) + } + }, "default-stashing-dispatcher")) + myAkkaActor ! 1 + myAkkaActor ! 42 + } + + def testNestedReact() = { + // Snippet showing composition of receives + // Loop with Condition Snippet - before + val myActor = actor { + var c = true + loopWhile(c) { + react { + case x: Int => + // do task + println("do task " + x) + if (x == 42) c = false + else + react { + case y: String => + println("do string " + y) + } + println("after react") + } + } + } + myActor.start() + + myActor ! 1 + myActor ! "I am a String" + myActor ! 42 + + Thread.sleep(100) + println(myActor.getState) + + // Loop with Condition Snippet - migrated + val myAkkaActor = MigrationSystem.actorOf(Props(() => new StashingActor { + + def receive = { + case x: Int => + // do task + println("do task " + x) + if (x == 42) + context.stop(self) + else + context.become(({ + case y: String => + println("do string " + y) + }: Receive).andThen(x => { + unstashAll() + context.unbecome() + }).orElse { case x => stash() }) + } + }, "default-stashing-dispatcher")) + + myAkkaActor ! 1 + myAkkaActor ! "I am a String" + myAkkaActor ! 42 + + } + + def exceptionHandling() = { + // Stashing actor with act and exception handler + val myActor = MigrationSystem.actorOf(Props(() => new StashingActor { + + def receive = { case _ => println("Dummy method.") } + override def act() = { + loop { + react { + case "fail" => + throw new Exception("failed") + case "work" => + println("working") + case "die" => + exit() + } + } + } + + override def exceptionHandler = { + case x: Exception => println("scala got exception") + } + + }, "default-stashing-dispatcher")) + + myActor ! "work" + myActor ! "fail" + myActor ! "die" + + Thread.sleep(100) + // Stashing actor in Akka style + val myAkkaActor = MigrationSystem.actorOf(Props(() => new StashingActor { + def receive = PFCatch({ + case "fail" => + throw new Exception("failed") + case "work" => + println("working") + case "die" => + context.stop(self) + }, { case x: Exception => println("akka got exception") }) + }, "default-stashing-dispatcher")) + + myAkkaActor ! "work" + myAkkaActor ! "fail" + myAkkaActor ! "die" + } + + def main(args: Array[String]) = { + testLoopWithConditionReact() + Thread.sleep(100) + exceptionHandling() + Thread.sleep(100) + testNestedReact() + } + +} + +// As per Jim Mcbeath blog (http://jim-mcbeath.blogspot.com/2008/07/actor-exceptions.html) +class PFCatch(f: PartialFunction[Any, Unit], handler: PartialFunction[Exception, Unit]) + extends PartialFunction[Any, Unit] { + + def apply(x: Any) = { + try { + f(x) + } catch { + case e: Exception if handler.isDefinedAt(e) => handler(e) + } + } + + def isDefinedAt(x: Any) = f.isDefinedAt(x) +} + +object PFCatch { + def apply(f: PartialFunction[Any, Unit], handler: PartialFunction[Exception, Unit]) = new PFCatch(f, handler) +} -- cgit v1.2.3