Haskell Pipes - get return value of last Proxy in pipeline

跟風遠走 提交于 2019-12-04 09:20:41

Without in-band signaling it will never be possible for the Consumer to have a "return value" if the Producer returns first. If the producer is returning that means the Consumer must be blocked waiting for a requested value. The Consumer will never run again, and thus never have an opportunity to return, until the Consumer gets an in-band signal with the requested value.

Just because signaling is in-band doesn't mean it needs to be "icky". We can convert a Producer that might return into a Producer that we know doesn't return (it's return type is forall r' . r') by capturing the return and forwarding it downstream. We do this forever in case another request comes back upstream.

returnDownstream :: Monad m => Proxy a' a b' b m r -> Proxy a' a b' (Either r b) m r'
returnDownstream = (forever . respond . Left =<<) . (respond . Right <\\)

At the Consumer end you need to explicitly handle what to do when a value is requested but instead of getting the response (in a Right) you get the return value of the upstream producer (in a Left).

Thanks. What I have come up with is something like

produce :: MonadIO m => Producer (Either ExitCode ByteString) m r
consume :: MonadIO m => Consumer (Either ExitCode ByteString) m (Maybe ExitCode, ExitCode)

so that when the Effect runs, I get a (Nothing, code) if the downstream process terminated, or (Just code1, code2) if the upstream process terminated first. (If the downstream terminates first, there's nothing left to do with the upstream process but terminate it, so providing an exit code doesn't make any sense.)

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!