我需要编写一个具有两个输入端口和两个输出端口的自定义GraphStage
。该GraphStage
将允许两个原本独立的流互相影响。我可以使用什么形状? FanOutShape2
有两个输出,而FanInShape2
有两个输入,但是我如何拥有同时具有这两个形状的形状?以某种方式将两者结合(继承)?使用BidiFlow
?做我自己的吗?
答案 0 :(得分:0)
我自己回答,因为这已经由forum.lightbend.com上的有用人员解决了,请参见https://discuss.lightbend.com/t/graphstage-with-shape-of-2-in-and-2-out/4160/3
这个问题的答案是简单地使用BidiShape
。尽管具有其他名称,但BidiShape
背后的逻辑绝不是双向的(回想起来很明显,但我对此不予理))。
如果有人处于相似的情况下,某些代码可以用作参考,他们必须基于两个输入来做某事,并且有可能推送到两个输出:
class BiNoneCounter[T]() extends GraphStage[BidiShape[Option[T], Option[Int], Option[T], Option[Int]]] {
private val leftIn = Inlet[Option[T]]("BiNoneCounter.in1")
private val rightIn = Inlet[Option[T]]("BiNoneCounter.in2")
private val leftOut = Outlet[Option[Int]]("BiNoneCounter.out1")
private val rightOut = Outlet[Option[Int]]("BiNoneCounter.out2")
override val shape = BidiShape(leftIn, leftOut, rightIn, rightOut)
override def createLogic(inheritedAttributes: Attributes): GraphStageLogic = new GraphStageLogic(shape) {
private var grabNextPush = false
val inHandler = new InHandler {
override def onPush(): Unit = {
if (grabNextPush) {
(grab(leftIn), grab(rightIn)) match {
// do stuff here
}
}
grabNextPush = !grabNextPush
}
}
val outHandler = (inlet: Inlet[Option[T]]) => new OutHandler {
override def onPull(): Unit = {
pull(inlet)
}
}
setHandler(leftOut, outHandler(leftIn))
setHandler(rightOut, outHandler(rightIn))
setHandler(leftIn, inHandler)
setHandler(rightIn, inHandler)
}
}
可以这样使用:
sourceOne ~> bidi.in1
bidi.out1 ~> sinkOne
sourceTwo ~> bidi.in2
bidi.out2 ~> sinkTwo