我开始使用 Akka Typed 来对我的行为进行详尽的模式匹配,这对于每个参与者的面向外部的契约非常有用。但是,如果参与者是状态机,则不同的状态很可能具有特定于状态的命令。
我可以将特定于状态的命令隐藏为整个命令的私有成员,如下所示:
sealed trait Command
final case class Add(id: Int) extends Command
private final case object AccumulationTimeout extends Command
private final case object Ack extends Command
但是,我的两种状态accumulating
又emitting
不得不处理彼此的命令。我可以使用.receivePartial
或包含一个包罗万象的
case _ => Behaviors.unhandled
在这两种情况下,我都失去了详尽的模式匹配,以确保我正确处理我的状态。
我可以进一步细化命令:
sealed trait Command
sealed trait Accumulating extends Command
private final case object AccumulationTimeout extends Accumulating
sealed trait Emitting extends Command
private final case object Ack extends Emitting
final case class Add(id: Int) extends Accumulating with Emitting
有了这个我可以定义Behavior[Accumulating]
两者Behavior[Emitting]
都是Behavior[Command]
,但问题是任何一种行为都无法转换到另一个,因为两者都必须返回自己的类型。
我尝试了各种排列但无济于事,.widen
并.narrow
意识到我真正需要的是一种将 a 定义Behavior
为的方法
def receiveMessage[T, V <: T](handler: V => Behavior[T]): Behavior[T] = ???
wherehandler
可以让我对窄类型进行详尽的检查,V
并且任何消息T
都V
将返回Behaviors.unhandled
。我似乎无法让这些类型工作以实现这样的功能。