2013-12-19 3 views
17

Akakaでは、将来の応答で?で作成されたonCompleteを使用するのではなく、おそらくpreferredパターンであるためpipeToを使用しようとしています。しかし、将来のタイムアウトが発生した場合、ThrowablesやFailuresを受け取っていないようです。 pipeToを使用しているときにタイムアウトが発生した場合、私の俳優で受け取るべきものは何ですか?別の例外がスローされたときはどうですか?コード例:タイムアウトが発生したときに何のメッセージが自動的に送信されていない場合はタイムアウトやその他のエラーでpipeToが送信するメッセージは何ですか?

class Simple(otherActor : ActorRef) extends Actor{ 
    def receive = { 
    case "some_msg" => { 
     val implicit timeout = Timeout(1 seconds) 
     val response = otherActor ? "hello" 
     response pipeTo self 
    } 

    // case ??? // How do I handle timeouts? 
    } 
} 

、どのように私はpipeToとタイムアウトを処理することが出来るのですか?

答えて

23

将来の失敗は、例外を含むakka.actor.Status.Failureメッセージとして送信されます。タイムアウトの例外はakka.pattern.AskTimeoutExceptionです。

+0

タイムアウトメッセージから発信元のメッセージを取得することは可能ですか? – hakunami

11

あなたの事例が実際のコードとよく似ている場合、私はpipeToがあなたが欲しいものと確信していません。私にメッセージを送り返すことはあまり意味がなく、俳優が別の俳優にメッセージを送ってから応答を待つ場合には、より良い解決策があります。まず、pipeToについて話しましょう。 pipeToを使用する良い例は、A、B、Cの3人の俳優がいる場合です。AはBにメッセージを送信し、CはCにメッセージを送信し、Cからの応答はBの後にAに返す必要がありますまず何か他のことをします。その例では、あなたはBのこの内部のような何かができる:ここでは

val fut = actorC ? someMessage 
fut map(someMapFunc) pipeTo sender 

pipeTo機能があなたの代わりにonCompleteようなものを使用してに反応した場合に、誤って変更可能なsender VARの上に閉じてからあなたを防ぐことができますそのコールバックの内側にsenderこの中で

class ActorA extends Actor{ 
    import context._ 
    val myB = context.actorOf(Props[ActorB]) 

    def receive = { 
    case msg => 
     myB ! msg 
     setReceiveTimeout(2 seconds) 
     become(waitingForResponse) 
    } 

    def waitingForResponse:Receive = { 
    case ReceiveTimeout => 
     println("got a receive timeout") 
     cancelReceiveTimeout 

    case response => 
     println("got my response back") 
     cancelReceiveTimeout 
    } 

    def cancelReceiveTimeout = setReceiveTimeout(Duration.Undefined) 
} 

:あなただけのBに話をして、Bからの応答を待つ(および潜在的なタイムアウトを処理)する場合

今、あなたのケースのために、あなたはこのような何かを試みることができますたとえば、Aはデフォルトのreceive部分関数で始まります。メッセージを受信すると、Bに別のメッセージを送り、Bからの応答を受信するための受信タイムアウトを設定し、次にreceiveの機能をBからの応答を待つことに特有のものに切り替えます。その新しい受信機能では、 Bから私の応答を得るか、ReceiveTimeoutを得ることができます。これは、時間内に私の応答を得られなかったことを示しています。どちらの場合でも、繰り返しているので、受信タイムアウトをキャンセルします。

これは非常に簡略化されていますが、私は2つのアクターの間で前後にやりとりする方法を示しています。

+0

この回答は有用で、私が記述した状況ではpipeToが最善ではないかもしれませんが、pipeToを使用したときのエラーの処理方法を知りたいと思っていました。 – mushroom

関連する問題