Akka笔记–儿童演员和ActorPath – 6

角色是完全分层的。 无论演员,你创建必须一些其他演员的孩子。

让我们分析一下:

路径

假设我们使用ActorSystem.actorOf创建一个ActorRef,然后尝试打印它的path

val actorSystem=ActorSystem("SupervisionActorSystem")  
val actorRef=actorSystem.actorOf(Props[BasicLifecycleLoggingTeacherActor])  
println (actorRef.path) // (prints) akka://SupervisionActorSystem/user/$a

如您所见,路径看起来与文件系统中的文件路径非常相似。

  1. 这里的akka是固定的,因为所有这些都是Akka Actor的地址–更像是file://http://前缀(尽管与协议无关)。
  2. SupervisionActorSystem只是您创建的ActorSystem的名称。
  3. 我们将在下一节中讨论user
  4. $a是系统为您生成的Actor的名称。 如果您的操作系统为文件生成了随机文件名,您希望如何? 您显然会讨厌它,因为您将来想引用该名称。 因此,我们给它起一个适当的有意义的名称:
val actorRef=actorSystem.actorOf(Props[BasicLifecycleLoggingTeacherActor], "teacherActor")  
println (actorRef.path)     // (prints) akka://SupervisionActorSystem/user/teacherActor

而已。 现在,该路径实际上是有意义的。

Akka笔记–儿童演员和ActorPath – 6_第1张图片

儿童演员

与我们在ActorSystem中创建的顶级actor相似,我们也可以在ActorContext创建子actor。 实际上,Actor的容错能力主要在于利用Actor的层次结构和父母管理孩子Actor的能力。

假设您有一个TeacherSupervisor并且您想创建一个TeacherActor作为Supervisor的子代,则执行ActorContext.actorOf而不是ActorSystem.actorOf

class TeacherSupervisor extends Actor with ActorLogging {  
  val teacherActor=context.actorOf(Props[TeacherActor], "teacherActor")
...
...

坦率地说,在任何应用中,您将创建一大堆儿童演员比顶级的演员-这意味着你将调用了很多actorContext.actorOfactorSystem.actorOf

Akka笔记–儿童演员和ActorPath – 6_第2张图片

您会注意到子actor的路径是akka://SupervisionActorSystem/user/teacherSupervisor/teacherActor ,与在父文件夹中创建子文件夹时获得的路径非常相似。

您何时创建儿童演员?

通常,当特定任务由一个子任务或多个子任务组成时,您将创建子参与者。 当要由父级执行的特定任务容易出错并且您希望隔离它时,您还将创建一个子actor(这样,如果失败,则可以恢复)。 如果任务之间没有父子关系,则不要创建子actor。

而且,没有什么可以阻止子角色创建子任务来委派子任务。 演员及其创造物确实很便宜,但是其带来的力量却是惊人的(我们在谈论监督时会看到这一点)。

现在,该路径中的那个

由于缺乏创造力,让我将ActorSystem与Unix文件系统进行比较-带有/根文件夹以及所有/etc/usr/bin和其他各种文件夹。

ActorSystem很像那样。 它创建了几个顶级演员-最重要的是根演员与路径/ ,与路径的用户演员/user以及与路径的系统演员/system (也有一个/deadLetters代表DeadLetterActorRef 。我们在上 /deadLetters中看到了这一点)

在代码方面,ActorSystem在其中组成了三个Actor(通过ActorRefProvider )。 这些是在ActorSystem下创建的所有Actor的根。

  1. systemGuardian actor – /system下所有actor的根
  2. guardian –在/user
  3. rootGuardian Actor – systemGuardianuserGuardian actor的根。
/**
   * Reference to the supervisor of guardian and systemGuardian; ....
   */
  def rootGuardian: InternalActorRef

  /**
   * Reference to the supervisor used for all top-level user actors.
   */
  def guardian: LocalActorRef

  /**
   * Reference to the supervisor used for all top-level system actors.
   */
  def systemGuardian: LocalActorRef

Akka笔记–儿童演员和ActorPath – 6_第3张图片

/ user(又名)用户监护人

您在程序中使用ActorSystemactorOf方法创建的任何Actor(例如StudentActorTeacherActor都将直接位于/user之下。 这就是在本文第一部分中您的teacherActor具有路径slug /user/teacherActor

/ system(aka)系统守护者

当发现userGuardian已死时,系统守护程序会自行关闭。 考虑到userGuardian是否已关闭,则其下的所有业务角色也都关闭了,因此所有管理角色也都必须关闭。

我们可以看到创建系统参与者的两个不同的地方–我的意思是/system层次结构下的参与者。

  1. 就像我们前面看到的 ,发送给终止的Actor的任何消息都会转发到内部Actor的名为DeadLetterActor的邮箱。 DeadLetter Actor将每个消息包装为DeadLetter并将其发布到EventStream。 另一个名为DeadLetterListener Actor会使用所有DeadLetter,并将其作为日志消息发布。 现在,DeadLetterListener是具有路径/system/deadLetterListener
  2. 还记得我们在上一篇 TestEventListener中创建的TestEventListener ,用于订阅EventStream中的日志消息吗? 他们也是系统参与者。 实际上,所有akka.loggers都是作为系统参与者创建的。
class TeacherTest extends TestKit(ActorSystem("UniversityMessageSystem", ConfigFactory.parseString("""akka.loggers = ["akka.testkit.TestEventListener"]""")))  
...
...

此处的文档说,在配置文件中配置并在启动时创建并部署到ActorSystem中的任何Actor都位于/system伞下。 当我发现与此有关的有趣内容时,请让我更新此帖子

/(aka)根监护人

如前所述, / Actor是用户和系统监护人的父级。

琐事

从技术上讲,根演员也有多余的父母。 该Actor的唯一工作是在根actor发生故障时关闭整个ActorSystem。 由于严格不在Actor层次结构内,因此Akka团队将其称为:

private[akka] val theOneWhoWalksTheBubblesOfSpaceTime: InternalActorRef = new MinimalActorRef {
...

翻译自: https://www.javacodegeeks.com/2014/10/akka-notes-child-actors-and-actorpath-6.html

你可能感兴趣的:(Akka笔记–儿童演员和ActorPath – 6)