2016-02-11 67 views
5

如果我因異常創建日誌的演員,像這樣相關Actor是否由主管重新啓動時是否更新了ActorRef?

val logger: ActorRef = 
    actorSystem.actorOf(Props(new Logger())) 

和記錄器重新啓動後,我的記錄器停止寫入磁盤。

,我已發送郵件logger ! msg

我是在假定當管理者重新啓動我的日誌演員ActorRef沒有更新正確?

回答

8

ActorRef應由Akka正確更新以指向演員的新實例。所述docs明確指出:

的引用指向一個終止演員的引用指示不比較等於 到另一個(重新創建)演員具有相同路徑。 請注意,由於故障導致演員重新啓動仍然意味着 它是相同的演員化身,即重新啓動對於 ActorRef的消費者不可見。

另外here

當actorOf()被調用它分配由所傳遞的道具來描述給定的路徑演員 的化身。演員化身 由路徑和UID標識。 重啓只會交換由道具定義的Actor實例 實例,但化身和因此UID 保持不變。

當角色停止時,化身的生命週期結束。在 這一點上,調用適當的生命週期事件並觀察演員被告知終止。 在化身 停止之後,可以通過使用 actorOf()創建演員來再次重用路徑。在這種情況下,新的化身的名稱將是 與前一個相同,但UID將有所不同。 ...

一個ActorRef總是代表一個道具(路徑和UID)而不是 只是一個給定的路徑。因此,如果一個演員停下來,並且一個新演員 創建了同名,那麼舊演員的ActorRef將不會指向 指向新演員。

這是使用ActorRef的主要優勢之一,否則與演員合作會更加不方便。

您需要檢查您的主管策略並確保該參與者實際上已重新啓動。 默認的策略是:

final val defaultStrategy: SupervisorStrategy = { 
    def defaultDecider: Decider = { 
    case _: ActorInitializationException ⇒ Stop 
    case _: ActorKilledException   ⇒ Stop 
    case _: Exception     ⇒ Restart 
    } 
    OneForOneStrategy()(defaultDecider) 
} 

因此,如果你得到一個Exception你的演員將重啓,ActorRef應該是有效的,但如果你得到其他類型的Throwable那麼它會被停止,ActorRef將失效。

+1

謝謝。這解釋得很好。我只是想補充一下,當Actor重啓時,它不會處理導致重啓的消息。就我而言,演員從來沒有給自己發過信息來觸發下一份工作。 – kliew

+0

感謝您關注@kliew。我很好奇它在你的情況下沒有按預期工作的原因。 –

+0

如果您位於Actor系統內,您可以觀看ActorRef。但是如果你想從外面維護一個ActorRef,你會如何保持這個最新? –

相關問題