0
votes

Within a test-program, I want to check that an Actor (child) remains terminated and is not created again after some computation. My test looks like (it is part of a TestKit subclass):

val childSelection = system.actorSelection(parent.path / "*")
childSelection ! Identify(0)
val child = expectMsgPF {
  case ActorIdentity(0, Some(ref)) => ref
}
watch(child)
// some computation that should end in stopping child
expectTermiated(child)
// some computation that should not create a new child
childSelection ! Identify(1)
expectMsg(ActorIdentity(1, None))

The last line sometimes unexpectedly fails, stating that the message ActorIdentity(1, Some(parent.path/child-name)) was received instead of the expected one. This means that, even after receiving the Terminated message (resulting from the expectTerminated(...) test), sending the Identify message to an actor selection does not necessarily result in the ActorIdentity(..., None) response.

Does anybody know what the akka framework actually does and how it works in this case? Thanks in advance for your help!

Meanwhile, I replaced the last line of my test with:

val identities = receiveWhile() {
  case ActorIdentity(1, Some(ref)) => ref == child
}
if (identities.isEmpty) {
  expectMsg(ActorIdentity(1, None))
} else {
  expectNoMsg
}

which seems to work fine but is quite more complex to read (and write)...

1
did you try graceful shutdown of the actor as in docs doc.akka.io/docs/akka/current/scala/actors.html#Graceful_StopLaksitha Ranasingha
no, the child stops itself using context.stop(self). The Terminated message sent to my test-program should attest that the child is actually stopped. However, it seems that the child, even stopped, remains "visible" on the akka platform for a short time...Vincent

1 Answers

0
votes

Since you selection is on parent.path / "*", your parent actor probably have another child that is responding to the Identity message. Check what identity your receive after stopping the child, to figure out what other child is responding.