我希望能够对“存储”到我的演员的 Receive 函数中的值进行断言。有没有办法用任何 Akka 测试库来做到这一点?
在下面的示例中,我想获取 currentCount
。
import akka.actor.Actor
class CounterActor extends Actor {
import CounterActor._
override def receive: Receive = count(0)
def count(currentCount: Int): Receive = {
case Increment => context.become(count(currentCount + 1))
case Decrement => context.become(count(currentCount - 1))
}
}
object CounterActor {
case object Increment
case object Decrement
}
然后我想用一个 Test 类来反对它:
val counterActorRef = TestActorRef(new CounterActor())
"A counter actor" should {
"have a count of 3" in {
counterActorRef ! CounterActor.Increment
counterActorRef ! CounterActor.Increment
counterActorRef ! CounterActor.Increment
val counterValue = // obtain currentCount from counterActorRef
assert(counterValue == 3)
}
}
我尝试过使用 TestActorRef,但没有成功。我知道有一种方法可以通过添加消息案例来获取它,或者添加一些调试/信息级别的日志消息并使用 EventFilter
来满足这一点。是否有使用我不知道的测试库获取它的简单方法?
我已经在 akka.testkit
库中搜索了一段时间,但找不到我的解决方案。
感谢任何帮助,谢谢。
答案 0 :(得分:0)
您想要做什么 - ask
演员关于他的状态并在测试中 assert
它。
第一步——读取值:
import akka.actor.Actor
class CounterActor extends Actor {
import CounterActor._
override def receive: Receive = count(0)
def count(currentCount: Int): Receive = {
case Increment => context.become(count(currentCount + 1))
case Decrement => context.become(count(currentCount - 1))
case Read => sender() !
}
}
object CounterActor {
case object Increment
case object Decrement
case object Read
case class CurrentValue(currentCount: Int) //for type safety
}
第二步 - 在测试中断言:
val counterActorRef = TestActorRef(new CounterActor())
"A counter actor" should {
"have a count of 3" in {
counterActorRef ! CounterActor.Increment
counterActorRef ! CounterActor.Increment
counterActorRef ! CounterActor.Increment
val counterValue = (counterActorRef ? Read).futureValue
assert(counterValue == CurrentValue(3))
}
}
答案 1 :(得分:0)
演员模型有两个特点:
actor 状态的封装是激进的,并且(在 JVM 上,有效地(因为可能通过反射破坏封装))是完整的。
观察到参与者的状态仅在其行为(它如何响应消息,以及在 Akka(它不是“一直向下的参与者”)的情况下)它执行的副作用方面才重要) 因该状态而变化。
为了验证状态转换是否发生,您只能测试它的行为是否符合预期。公开查询消息是一种方法;诸如点击日志条目流或(如果是事件源,则是持久性事件流)之类的东西。
也就是说,仅出于启用可测试性的目的而公开查询消息通常不是可行的方法(这可能对操作调试有用)。理想的情况是测试参与者响应状态变化的“带内”行为(例如,“在发送 A 为真的消息后,对 B 为真的消息的响应表现出属性 C”)。如果状态变化没有以某种方式表现为行为变化,为什么状态变化会发生?
换句话说,将其他参与者视为黑盒服务通常是好的。如果您正在测试 SO,则无法验证“发布问题后,数据库中的此字段设置为此值”(因为您作为用户无权访问数据库,并且您无法提供您控制的模拟 SO)。您可以验证的是“当我发布问题时,我会返回一个问题 ID,当我请求该 ID 时,我会返回问题的内容”。