1

私は Scala と Akka を初めて使用しますが、単純なシナリオがあります... URL のリストを取得して、各 URL をメッセージとして新しいアクターに送信し、http GET 要求を作成しようとしています。16 個の URL のリストだけで、約 40 ~ 65% の成功率が得られ、他の URL では「メッセージが配信されませんでした」というデッドレターが返されます。ただし、アクターを作成する前に Thread.sleep(50) を配置すると、デッドレター ミスは発生しません。注: HTTP Get は、要因である場合とそうでない場合がある scala クラスではなく、java クラスを使用しています。以下のコード例を参照してください... Akka がメッセージを保証しないことは知っていますが、この成功率は正しくないように見えます。間違っているに違いありません。ご指摘ありがとうございます。

  def ParallelTest(urls: List[String]): String =   {
     val system = ActorSystem("HelloSystem")

     var cnt: Int = 0
     for (item <- urls){
       Thread.sleep(50)
       createActor(system, "helloactor" + cnt, item)
       cnt += 1
       /*
       historical example
       helloActor ! "hello"
       helloActor ! "hello"
       helloActor ! "Buenos dias"
       */
      }
     system.shutdown

     println("parallel done");
     "done"   
   }

  def createActor(actorSystem: ActorSystem, actorName: String, urlItem: String) = {
    val helloActor = actorSystem.actorOf(Props[HelloActor], name = actorName)
    helloActor ! UrlTransport(urlItem)
  }
4

1 に答える 1

2

アクターがいつ完了したかを知るためのマネージャーを用意して、このようなことを検討することをお勧めします。

class HelloManager(urls: List[String]) extends Actor {

    var completed = 0
    def remaining = urls.size - completed

    def receive: Receive = {
        case StartSystem => startRequests
        case RequestComplete => handleComplete

    }

    def startRequests(): Unit = {
        for ((url, i) <- urls.zipWithIndex) {
            val helloActor = context.actorOf(Props[HelloActor], name = s"helloActor$i")
            helloActor ! UrlTransport(url)
        }
    }  

    def handleComplete(): Unit = {
        completed += 1
        if (remaining == 0) 
            // do something like
            // context.stop(self)
    }
}

sender ! RequestComplete次に、HelloActorがジョブを完了したときにa を実行する必要があります。

于 2014-02-07T00:03:53.240 に答える