Verschmelzen von Conduits mit mehreren Eingängen

Ich versuche, ein Conduit zu erstellen, das mehrere Eingabestreams verarbeiten kann. Ich muss in der Lage sein, auf den einen oder anderen der Eingabestreams in keiner bestimmten Reihenfolge zu warten (z. B. nicht abwechselnd), wodurch zip unbrauchbar wird. Hier passiert nichts Paralleles oder Nicht-Deterministisches: Ich warte auf den einen oder anderen Strom. Ich möchte in der Lage sein, Code ähnlich dem folgenden zu schreiben (woawaitA undawaitB auf den ersten bzw. zweiten Eingabestream warten):

do
  _ <- awaitA
  x <- awaitA
  y <- awaitB
  yield (x,y)
  _ <- awaitB
  _ <- awaitB
  y' <- awaitB
  yield (x,y')

Die beste Lösung, die ich habe, besteht darin, die innere Monade zu einer weiteren Leitung zu machen, z.

foo :: Sink i1 (ConduitM i2 o m) ()

Was dann erlaubt

awaitA = await
awaitB = lift await

Und das funktioniert meistens. Leider scheint es sehr schwierig zu sein, die innere Leitung zu verschmelzen, bevor die äußere Leitung vollständig angeschlossen ist. Das erste was ich versuchte war:

fuseInner :: Monad m =>
                Conduit i2' m i2 -> 
                Sink i1 (ConduitM i2 o m) () -> 
                Sink i1 (ConduitM i2' o m) ()
fuseInner x = transPipe (x =$=)

Aber das funktioniert zumindest dann nichtx ist zustandsbehaftet seit(x =$=) wird mehrmals ausgeführt und neu gestartetx jedes Mal.

Gibt es eine Möglichkeit, fuseInner zu schreiben, ohne in die Interna des Conduits einzubrechen (was so aussieht, als wäre es ziemlich chaotisch)? Gibt es eine bessere Möglichkeit, mit mehreren Eingabestreams umzugehen? Bin ich nur viel zu weit über das hinaus, wofür Conduit entwickelt wurde?

Vielen Dank!

Antworten auf die Frage(2)

Ihre Antwort auf die Frage