Scala Akka Actorモデルについて

個人開発したアプリの宣伝
目的地が設定できる手帳のような使い心地のTODOアプリを公開しています。
Todo with Location

Todo with Location

  • Yoshiko Ichikawa
  • Productivity
  • Free

スポンサードリンク

Akka Actorとは?

Akka ActorはActorに対してメッセージを配信する仕組みを提供する。

messageの送信は非同期で送信され、透過的にキューイングされ、Actor側からはキューメッセージを取り出し同期的に処理を行う。


依存ライブラリ
libraryDependencies ++= Seq(
  "com.typesafe.akka" %% "akka-actor" % "2.5.17",
  "com.typesafe.akka" %% "akka-testkit" % "2.5.17" % Test
)


Actorモデルの定義

Actorの定義

Actorを継承して定義する。

import akka.actor.{Actor, ActorSystem, Props}

//Actor(受信側)の定義
class MyActor extends Actor {
  //メッセージ受信時の処理(queue pop)
  def receive = {
    case "test" => println("test")
    case _ => println("unknown")
  }
}


Actorの生成とメッセージの送信
object ActorStudy extends App {
  //Actorの生成 生成はActorSystemから行う
  val system = ActorSystem("actorStudy")
  val myActor = system.actorOf(Props[MyActor], "myActor")
  //メッセージの送信
  myActor ! "test"
  myActor ! "hoge"
  // メインスレッドが終了するまでアプリケーションを終了しない
  //Thread.currentThread().join()
}


ファイルの実行

実行はsbt.buildを配置したディレクトリでbuildする。

$ sbt console
scala> ActorStudy.main(Array[String]())


Actorからの返信を受け取る

Actorの定義。inboxを経由したメッセージはsenderで返信できる

import akka.actor.{Actor, ActorSystem, Inbox, Props}
import scala.concurrent.duration._

class Greeter extends Actor {
  def receive = {
    //inboxへのメッセージ送信 sendは必ずinbox経由のメッセージを受信するようパターンマッチすること
    case _ => sender ! "text"
  }
}


送信側。Actorとやりとりを行うinboxを作成する

object HelloAkkaScala extends App {

  val system = ActorSystem("helloAkka")
  val greeter = system.actorOf(Props[Greeter], "greeter")

  //Actorとの連絡をキューイングするmailboxの作成
  val inbox = Inbox.create(system)

  //greeter ! "message" // Actorからのレスポンスを期待する場合は、inbox経由でのメッセージ送信を行う
  inbox.send(greeter, Greet)
  val data:String = inbox.receive(5.seconds) //inbox内のメッセージを取得 存在しない場合、5秒間待つ
  println(data)
}


Akkaのスケジューラー

Akka ActorはActor間でのメッセージの送信をスケジューリングできる。

以下の例では0秒後に1秒おきにfromActorからtoActorに"test"というメッセージを送信する。

system.scheduler.schedule(0.seconds, 1.second, toActor, "test")(system.dispatcher, fromActor)