[
  {
    "path": ".github/workflows/haskell.yml",
    "content": "name: Haskell CI\n\non:\n  push:\n    branches: [ main ]\n  pull_request:\n    branches: [ main ]\n\njobs:\n  build:\n\n    runs-on: ubuntu-latest\n\n    steps:\n    - uses: actions/checkout@v2\n    - uses: haskell/actions/setup@v1.2\n    - name: Cache\n      uses: actions/cache@v1\n      env:\n        cache-name: cache-cabal\n      with:\n        path: ~/.cabal\n        key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ hashFiles('**/*.cabal') }}-${{ hashFiles('**/cabal.project') }}\n        restore-keys: |\n          ${{ runner.os }}-build-${{ env.cache-name }}-\n          ${{ runner.os }}-build-\n          ${{ runner.os }}-\n\n    - name: Install dependencies\n      run: |\n        cabal update\n        cabal build --only-dependencies --enable-tests --enable-benchmarks\n    - name: Build\n      run: cabal build --enable-tests --enable-benchmarks all\n    - name: Run tests\n      run: cabal test all\n"
  },
  {
    "path": ".gitignore",
    "content": "cabal-dev\n.cabal-sandbox\ncabal.sandbox.config\ndist\n.stack-work\n"
  },
  {
    "path": "CHANGELOG.md",
    "content": "4.3.16\n\n* Fix example code for `every`\n* Improved documentation for `ListT`\n\n4.3.15\n\n* Build against `ghc-9.0`\n\n4.3.14\n\n* Add `mapMaybe` and `wither`, and more laws for `filter` and `filterM`.\n\n4.3.13\n\n* Add `MonadFail` instance for `Proxy`\n\n4.3.12\n\n* Fix space leak introduced in version 4.3.10\n    * This leak primarily affects the use of `forever`\n\n4.3.11\n\n* Fix documentation for `scanM`\n\n4.3.10\n\n* Relax `Monad` constraints to `Functor`\n* Support GHC 8.8\n\n4.3.9\n\n* Increase upper bound on `exceptions`\n\n4.3.8\n\n* Increase upper bound on `exceptions`\n\n4.3.7\n\n* Documentation fix\n\n4.3.6\n\n* Fix implementation of `pass` in `MonadWriter` instance for `Proxy`\n\n4.3.5\n\n* Support `Semigroup` being a super-class of `Monoid`\n\n4.3.4\n\n* Increase upper bound on `mmorph`\n\n4.3.3\n\n* Make `X` a synonym for `Data.Void.Void`\n\n4.3.2\n\n* BUG FIX: Fix `MMonad` instance for `ListT`\n    * The old instance was an infinite loop\n\n4.3.1\n\n* Support building against `ghc-7.4`\n\n4.3.0\n\n* BREAKING CHANGE: Remove `Alternative`/`MonadPlus` instances for `Proxy`\n    * See commit 08e7302f43dbf2a40bd367c5ee73ee3367e17768 which explains why\n* Add `Traversable` instance for `ListT`\n* New `MonadThrow`/`MonadCatch`/`MMonad`/`Semigroup`/`MonadZip` instances for\n  `ListT`\n* New `MonadThrow`/`MonadCatch` instances for `Proxy`\n* Fix lower bound on `mtl`\n* Increase upper bound on `optparse-applicative`\n\n4.2.0\n\n* BREAKING CHANGE: Switch from `ErrorT` to `ExceptT`\n* Add `Foldable` instance for `ListT`\n* Fix all warnings\n* Enable foldr/build fusion for `toList`\n\n4.1.9\n\n* Increase lower bound on `criterion`\n* Increase upper bound on `transformers` for tests/benchmarks\n* Optimize code by delaying `INLINABLE` annotations\n\n4.1.8\n\n* Increase upper bound on `transformers`\n* Prepare for MRP (Monad of no Return Proposal)\n\n4.1.7\n\n* Increase lower bound on `deepseq`\n* Add `unfoldr`\n* Add `loop`\n* Add `toListM'`\n* Improve efficiency of `drop`\n* License tutorial under Creative Commons license\n\n4.1.6\n\n* Increase lower bound on `base`\n* Add diagrams to `Pipes.Core` documentation\n* Add `mapM_`\n* Add `takeWhile'`\n* Add `seq`\n* Improve efficiency of `toListM`\n\n4.1.5\n\n* Increase upper bound on `criterion`\n\n4.1.4\n\n* Increase upper bound on `criterion`\n* Add `Monoid` instance for `Proxy`\n\n4.1.3\n\n* Increase lower bound on `mtl`\n* Re-export `void`\n* Add `fold'`\n* Add `foldM'`\n\n4.1.2\n\n* Increase upper bounds on `transformers` and `mtl`\n\n4.1.1\n\n* Add `runListT`\n* Add `MMonad` instance for `Proxy`\n* Add `repeatM`\n* Add laws to documentation of `Pipes.Prelude` utilities\n\n4.1.0\n\n* Remove Haskell98 support\n* Use internal `X` type instead of `Data.Void`\n* Document `Pipes.Lift` module:w\n* Add `drain`\n* Add `sequence`\n\n4.0.2\n\n* Improve performance of `each`\n* Add tutorial appendix explaining how to work around quadratic time complexity\n\n4.0.1\n\n* Remove `WriterT` and `RWST` benchmarks\n* Add `Enumerable` instance for `ErrorT`\n* Add cabal flag for Haskell98 compilation\n* Add several rewrite rules\n* Add `mtl` instances for `ListT`\n* Fix implementation of `pass`, which did not satisfy `Writer` laws\n* Implement `fail` for `ListT`\n* Add type synonym table to tutorial appendix\n* Add QuickCheck tests for `pipes` laws\n* Add `mapFoldable`\n* Add `Monoid` instance for `ListT`\n* Add manual proofs of `pipes` laws in `laws.md`\n\n4.0.0\n\nMajor upgrade of `pipes` to no longer use `Proxy` type class\n"
  },
  {
    "path": "LICENSE",
    "content": "Copyright (c) 2012-2016 Gabriella Gonzalez\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without modification,\nare permitted provided that the following conditions are met:\n    * Redistributions of source code must retain the above copyright notice,\n      this list of conditions and the following disclaimer.\n    * Redistributions in binary form must reproduce the above copyright notice,\n      this list of conditions and the following disclaimer in the documentation\n      and/or other materials provided with the distribution.\n    * Neither the name of Gabriella Gonzalez nor the names of other contributors\n      may be used to endorse or promote products derived from this software\n      without specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\nANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\nANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "README.md",
    "content": "# `pipes`\n\n`pipes` is a clean and powerful stream processing library that lets you build\nand connect reusable streaming components.\n\n## Quick start\n\n* Install the [Haskell Platform](http://www.haskell.org/platform/)\n* `cabal install pipes`\n\nThen fire up `ghci`:\n\n    $ ghci\n    Prelude> import Pipes\n    Prelude Pipes> import qualified Pipes.Prelude as P\n\n... and echo standard input to standard output until you enter `quit`.\n\n    Prelude Pipes P> runEffect $ P.stdinLn >-> P.takeWhile (/= \"quit\") >-> P.stdoutLn\n    Test[Enter]\n    Test\n    Apple[Enter]\n    Apple\n    quit[Enter]\n    Prelude P> -- Done!\n\nTo learn more, read the\n[pipes tutorial](http://hackage.haskell.org/package/pipes/docs/Pipes-Tutorial.html).\n\n## Features\n\n* *Concise API*: Use simple commands like `for`, `(>->)`, `await`, and `yield`\n\n* *Blazing fast*: Implementation tuned for speed, including shortcut fusion\n\n* *Lightweight Dependency*: `pipes` is small and compiles very rapidly,\n  including dependencies\n\n* *Elegant semantics*: Use practical category theory\n\n* *ListT*: Correct implementation of `ListT` that interconverts with pipes\n\n* *Bidirectionality*: Implement duplex channels\n\n* *Extensive Documentation*: Second to none!\n\n## Philosophy\n\nThe `pipes` library emphasizes the following three design precepts:\n\n* Emphasize elegance - Elegant libraries replace inelegant libraries\n\n* Theory everywhere - Principled design promotes intuitive behavior\n\n* Minimize dependencies - Small dependency profiles maximize portability\n\n## Outline\n\nThe core `pipes` ecosystem consists of the following four libraries:\n\n* `pipes`: The elegant, theoretically-principled core.\n\n* `pipes-concurrency`: Message passing and reactive programming\n\n* `pipes-parse`: Utilities for parsing streams\n\n* `pipes-safe`: Resource management and exception safety\n\nThese represent the core areas that I envision for `pipes`.  The latter three\nlibraries represent the more pragmatic face of the ecosystem and make design\ntradeoffs where there is no known elegant solution.\n\nDerived libraries that build on top of these include:\n\n* `pipes-network` and `pipes-network-tls`: Networking support\n\n* `pipes-attoparsec`: High-efficiency streaming parsing\n\n* `pipes-zlib`: Compression and decompression\n\n* `pipes-binary`: Streaming serialization and deserialization\n\n* `pipes-aeson`: Streaming JSON encoding and decoding\n\n## Development Status\n\n[![Build Status](https://travis-ci.org/Gabriella439/Haskell-Pipes-Library.png)](https://travis-ci.org/Gabriella439/Haskell-Pipes-Library)\n\n`pipes` is stable, and current work focuses on packaging `pipes` for various\npackage managers.  The long term goal is to get `pipes` into the Haskell\nplatform and become the basic building block for streaming APIs.\n\n## Community Resources\n\n* [Haskell wiki page](http://www.haskell.org/haskellwiki/Pipes)\n\n* [Mailing list](mailto:haskell-pipes@googlegroups.com) ([Google Group](https://groups.google.com/forum/?fromgroups#!forum/haskell-pipes))\n\n## How to contribute\n\n* Contribute code\n\n* Build derived libraries\n\n* Write `pipes` tutorials\n\n## License (BSD 3-clause)\n\nCopyright (c) 2012-2014 Gabriella Gonzalez\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without modification,\nare permitted provided that the following conditions are met:\n\n* Redistributions of source code must retain the above copyright notice, this\n  list of conditions and the following disclaimer.\n\n* Redistributions in binary form must reproduce the above copyright notice, this\n  list of conditions and the following disclaimer in the documentation and/or\n  other materials provided with the distribution.\n\n* Neither the name of Gabriella Gonzalez nor the names of other contributors may\n  be used to endorse or promote products derived from this software without\n  specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\nANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\nANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "Setup.hs",
    "content": "import Distribution.Simple\nmain = defaultMain\n"
  },
  {
    "path": "benchmarks/Common.hs",
    "content": "module Common (commonMain) where\n\nimport Criterion.Main (Benchmark, runMode)\nimport Criterion.Main.Options as Criterion\nimport Data.Maybe (fromMaybe)\nimport Data.Monoid\nimport Options.Applicative\n\ncommonMain :: Int                    -- ^ default maximum data size\n           -> (Int -> [Benchmark])   -- ^ the benchmarks to run\n           -> IO ()\ncommonMain mdMax bench = do\n    (maybeNewMax, critMode) <- execParser $ info (helper <*> options) mempty\n    runMode critMode $ bench (fromMaybe mdMax maybeNewMax)\n\noptions :: Parser (Maybe Int, Criterion.Mode)\noptions =\n    (,) <$> optional (option auto (help \"benchmark maximum data size\"\n                                   <> metavar \"N\" <> short 'i'  <> long \"imax\"))\n        <*> Criterion.parseWith Criterion.defaultConfig\n"
  },
  {
    "path": "benchmarks/LiftBench.hs",
    "content": "{-# LANGUAGE RankNTypes #-}\nmodule Main (main) where\n\nimport Common (commonMain)\nimport Control.Monad.Identity\nimport qualified Control.Monad.Trans.Reader as R\nimport qualified Control.Monad.Trans.State.Strict as S\nimport Criterion.Main\nimport Data.Monoid\nimport Pipes\nimport Pipes.Lift\n\ndefaultMax :: Int\ndefaultMax = 10000\n\nmain :: IO ()\nmain = commonMain defaultMax liftBenchmarks\n\niter :: forall m a . (Monad m , Ord a, Num a) => (a -> m a) -> a -> Effect m a\niter a vmax = loop 0\n    where\n        loop n\n            | n > vmax  = return vmax\n            | otherwise = do\n                x <- lift $ a n\n                loop $! x\n\ns_bench :: Int -> Effect (S.StateT Int Identity) Int\ns_bench = iter (\\n -> S.get >>= (\\a -> S.put $! a + n) >> return (n + 1))\n\nr_bench :: Int -> Effect (R.ReaderT Int Identity) Int\nr_bench = iter (\\n -> R.ask >>= (\\a -> return $ n + a))\n\n-- Run before Proxy\nrunB :: (a -> Effect Identity r) -> a -> r\nrunB f a = runIdentity $ runEffect $ f a\n\n-- Run after Proxy\nrunA :: (Monad m) => (m r -> Identity a) -> Effect m r -> a\nrunA f a = runIdentity $ f (runEffect a)\n\nliftBenchmarks :: Int -> [Benchmark]\nliftBenchmarks vmax =\n    let applyBench = map ($ vmax)\n    in\n    [\n      bgroup \"ReaderT\" $\n        let defT f = (\\d -> f d 1)\n        in applyBench\n        [\n          bench \"runReaderP_B\" . whnf (runB (runReaderP 1) . r_bench)\n        , bench \"runReaderP_A\" . whnf (runA (defT R.runReaderT) . r_bench)\n        ]\n    , bgroup \"StateT\" $\n        let defT f = (\\s -> f s 0)\n        in applyBench\n        [\n          bench \"runStateP_B\"  . nf (runB (runStateP 0) . s_bench)\n        , bench \"runStateP_A\"  . nf (runA (defT S.runStateT) . s_bench)\n        , bench \"evalStateP_B\" . whnf (runB (evalStateP 0) . s_bench)\n        , bench \"evalStateP_A\" . whnf (runA (defT S.evalStateT) . s_bench)\n        , bench \"execStateP_B\" . whnf (runB (execStateP 0) . s_bench)\n        , bench \"execStateP_A\" . whnf (runA (defT S.execStateT) . s_bench)\n        ]\n    ]\n"
  },
  {
    "path": "benchmarks/PreludeBench.hs",
    "content": "{-# LANGUAGE RankNTypes #-}\nmodule Main (main) where\n\nimport Criterion.Main\nimport Common (commonMain)\nimport Control.Monad.Identity (Identity, runIdentity)\nimport Pipes\nimport qualified Pipes.Prelude as P\nimport Prelude hiding (enumFromTo)\n\ndefaultMax :: Int\ndefaultMax = 10000\n\nmain :: IO ()\nmain = commonMain defaultMax preludeBenchmarks\n\nenumFromTo :: (Int -> a) -> Int -> Int -> Producer a Identity ()\nenumFromTo f n1 n2 = loop n1\n    where\n        loop n =\n            if n <= n2\n            then do\n                yield $! f n\n                loop $! n + 1\n            else return ()\n{-# INLINABLE enumFromTo #-}\n\ndrain :: Producer b Identity r -> r\ndrain p = runIdentity $ runEffect $ for p discard\n\nmsum :: (Monad m) => Producer Int m () -> m Int\nmsum = P.foldM (\\a b -> return $ a + b) (return 0) return\n\nscanMSum :: (Monad m) => Pipe Int Int m r\nscanMSum = P.scanM (\\x y -> return (x + y)) (return 0) return\n\n-- Using runIdentity seems to reduce outlier counts.\npreludeBenchmarks :: Int -> [Benchmark]\npreludeBenchmarks vmax =\n    let applyBench b = b benchEnum_p\n        benchEnum_p  = enumFromTo id 1 vmax\n    in\n    [\n      bgroup \"Folds\" $ map applyBench\n        [\n          bench \"all\"       . whnf (runIdentity . P.all (<= vmax))\n        , bench \"any\"       . whnf (runIdentity . P.any (> vmax))\n        , bench \"find\"      . whnf (runIdentity . P.find (== vmax))\n        , bench \"findIndex\" . whnf (runIdentity . P.findIndex (== vmax))\n        , bench \"fold\"      . whnf (runIdentity . P.fold (+) 0 id)\n        , bench \"foldM\"     . whnf (runIdentity . msum)\n        , bench \"head\"      . nf (runIdentity . P.head)\n        , bench \"index\"     . nf (runIdentity . P.index (vmax-1))\n        , bench \"last\"      . nf (runIdentity . P.last)\n        , bench \"length\"    . whnf (runIdentity . P.length)\n        , bench \"null\"      . whnf (runIdentity  . P.null)\n        , bench \"toList\"    . nf P.toList\n        ]\n    , bgroup \"Pipes\" $ map applyBench\n        [\n          bench \"chain\"       . whnf (drain . (>-> P.chain (\\_ -> return ())))\n        , bench \"drop\"        . whnf (drain . (>-> P.drop vmax))\n        , bench \"dropWhile\"   . whnf (drain . (>-> P.dropWhile (<= vmax)))\n        , bench \"filter\"      . whnf (drain . (>-> P.filter even))\n        , bench \"findIndices\" . whnf (drain . (>-> P.findIndices (<= vmax)))\n        , bench \"map\"         . whnf (drain . (>-> P.map id))\n        , bench \"mapM\"        . whnf (drain . (>-> P.mapM return))\n        , bench \"take\"        . whnf (drain . (>-> P.take vmax))\n        , bench \"takeWhile\"   . whnf (drain . (>-> P.takeWhile (<= vmax)))\n        , bench \"scan\"        . whnf (drain . (>-> P.scan (+) 0 id))\n        , bench \"scanM\"       . whnf (drain . (>-> scanMSum))\n        ] ++ [\n          bench \"concat\" $ whnf (drain . (>-> P.concat)) $ enumFromTo Just 1 vmax\n        ]\n    , bgroup \"Zips\" $ map applyBench\n        [\n          bench \"zip\"     . whnf (drain . P.zip benchEnum_p)\n        , bench \"zipWith\" . whnf (drain . P.zipWith (+) benchEnum_p)\n        ]\n    , bgroup \"enumFromTo.vs.each\"\n        [\n          bench \"enumFromTo\" $ whnf (drain . enumFromTo id 1) vmax\n        , bench \"each\"       $ whnf (drain . each) [1..vmax]\n        ]\n    ]\n"
  },
  {
    "path": "laws.md",
    "content": "# Kleisli Category\n\n    Define:\n    \n    return\n        :: (Monad m)\n        =>  r -> Proxy a' a b' b m r\n    return = Pure\n    \n    (>=>)\n        :: (Monad m)\n        => (r -> Proxy a' a b' b m s)\n        -> (s -> Proxy a' a b' b m t)\n        -> (r -> Proxy a' a b' b m t)\n    (f >=> g) x = f x >>= g\n    \n    (>>=)\n        :: (Monad m)\n        =>       Proxy a' a b' b m s\n        -> (s -> Proxy a' a b' b m t)\n        ->       Proxy a' a b' b m t\n    p >>= f = case p of\n        Request a' fa  -> Request a' (\\a  -> fa  a  >>= f)\n        Respond b  fb' -> Respond b  (\\b' -> fb' b' >>= f)\n        M          m   -> M (m >>= \\p' -> return (p' >>= f))\n        Pure    r      -> f r\n    \n## Left Identity Law\n\n    Goal: return >=> f = f\n    \n    return >=> f\n    \n    -- Definition of `(>=>)`\n    = \\x -> return x >>= f\n    \n    -- [Kleisli Category - Left Identity Law - Pointful]\n    = \\x -> f x\n    \n    -- Eta reduce\n    = f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: return r >>= f = f r\n    \n    return r >>= f\n    \n    -- Definition of `return`\n    = Pure r >>= f\n    \n    -- Definition of `(>>=)`\n    = f r\n    \n    -- Goal complete\n    \n## Right Identity Law\n\n    Goal: f >=> return = f\n    \n    f >=> return\n    \n    -- Definition of `(>=>)`\n    = \\x -> f x >>= return\n    \n    -- [Kleisli Category - Right Identity Law - Pointful]\n    = \\x -> f x\n    \n    -- Eta reduce\n    = f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: p >>= return = p\n    \n    p >>= return\n    \n    -- Definition of `(>>=)`\n    = case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>= return)\n        \n                        -- Coinduction: Reuse the premise\n                        = Request a' (\\a -> fa a)\n                        \n                        -- Eta reduce\n                        = Request a' fa\n                        \n        Respond b  fb' -> Respond b (\\b' -> fb' b' >>= return)\n        \n                        -- Coinduction: Reuse the premise\n                        = Respond b (\\b' -> fb' b')\n                        \n                        -- Eta reduce\n                        = Respond b fb'\n                        \n        M          m   -> M (m >>= \\p' -> return (p' >>= return))\n        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p')\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful] (NOTE: for base monad, so no coinduction necessary)\n                        = M m\n                        \n        Pure    r      -> return r\n        \n                        -- Definition of `return`\n                        = Pure r\n                        \n    -- Clean up\n    = case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r\n        \n    -- case statement = id\n    = p\n    \n    -- Goal complete\n    \n## Associativity Law\n\n    Goal: (f >=> g) >=> h = f >=> (g >=> h)\n    \n    (f >=> g) >=> h\n    \n    -- Definition of `(>=>)`\n    = \\x -> (f >=> g) x >>= h\n    \n    -- Definition of `(>=>)`\n    = \\x -> (f x >>= g) >>= h\n    \n    -- [Kleisli Category - Associativity Law - Pointful]\n    = \\x -> f x >>= \\y -> g y >>= h\n    \n    -- Definition of `(>=>)`, in reverse\n    = \\x -> f x >>= (g >=> h)\n    \n    -- Definition of `(>=>)`, in reverse\n    = f >=> (g >=> h)\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: (p >>= f) >>= g) = p >>= \\x -> f x >>= g\n    \n    (p >>= f) >>= g\n    \n    -- Definition of `(>>=)`\n    (case p of\n        Request a' fa  -> Request a' (\\a  -> fa  a  >>= f)\n        Respond b  fb' -> Respond b  (\\b' -> fb' b' >>= f)\n        M          m   -> M (m >>= \\p' -> return (p' >>= f))\n        Pure    r      -> f r ) >>= g\n        \n    -- Distribute over case statement\n    = case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>= f) >>= g\n        \n                        -- Definition of `(>>=)`\n                        = Request a' (\\a -> (fa a >>= f) >>= g)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request a' (\\a -> fa a >>= \\x -> f x >>= g)\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Request a' fa >>= \\x -> f x >>= g\n                        \n        Respond b  fb' -> Respond b (\\b' -> fb' b' >>= f) >>= g\n        \n                        -- Definition of `(>>=)`\n                        = Respond b (\\b' -> (fb' b' >>= f) >>= g)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Respond b (\\b' -> fb' b' >>= \\x -> f x >>= g)\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Respond b fb' >>= \\x -> f x >>= g\n                        \n        M          m   -> M (m >>= \\p' -> return (p' >>= f)) >>= g\n        \n                        -- Definition of `(>>=)`\n                        = M (m >>= \\p' -> return ((p' >>= f) >>= g))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (p' >>= \\x -> f x >>= g))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = M m >>= \\x -> f x >>= g\n                        \n        Pure    r      -> f r >>= g\n\n                        -- Definition of `(>>=)`, in reverse\n                        = Pure r >>= \\x -> f x >>= g\n                        \n    -- Clean up\n    = case p of\n        Request a' fa  -> Request a' fa  >>= \\x -> f x >>= g\n        Respond b  fb' -> Respond b  fb' >>= \\x -> f x >>= g\n        M          m   -> M          m   >>= \\x -> f x >>= g\n        Pure    r      -> Pure    r      >>= \\x -> f x >>= g\n        \n    -- Factor from case statement\n    = (case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r ) >>= \\x -> f x >>= g\n        \n    -- case statement = id\n    = p >>= \\x -> f x >>= g\n    \n    -- Goal complete\n\n# Respond Category\n\n    Define:\n    \n    respond\n        :: (Monad m)\n        =>  a -> Proxy x' x a' a m a'\n    respond a = Respond a Pure\n    \n    (/>/)\n        :: (Monad m)\n        => (a -> Proxy x' x b' b m a')\n        -> (b -> Proxy x' x c' c m b')\n        -> (a -> Proxy x' x c' c m a')\n    (fa />/ fb) a = fa a //> fb\n    \n    (//>)\n        :: (Monad m)\n        =>       Proxy x' x b' b m a'\n        -> (b -> Proxy x' x c' c m b')\n        ->       Proxy x' x c' c m a'\n    p //> fb = case p of\n        Request x' fx  -> Request x' (\\x -> fx x //> fb)\n        Respond b  fb' -> fb b >>= \\b' -> fb' b' //> fb\n        M          m   -> M (m >>= \\p' -> return (p' //> fb)\n        Pure    a      -> Pure a\n\n## Right Identity Law\n\n    Goal: respond />/ fb = fb\n    \n    respond />/ fb\n    \n    -- Definition of `(/>/)`\n    = \\b -> respond b //> fb\n    \n    -- [Respond Category - Left Identity Law - Pointful]\n    = \\b -> fb b\n    \n    -- Eta reduce\n    = fb\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: respond b //> fb = fb b\n    \n    -- Definition of `respond`\n    = Respond b Pure //> fb\n    \n    -- Definition of `(//>)`\n    = fb b >>= \\b' -> Pure b' //> fb\n    \n    -- Definition of `(//>)`\n    = fb b >>= \\b' -> Pure b'\n    \n    -- Eta reduce\n    = fb b >>= Pure\n    \n    -- Definition of `return` (in reverse)\n    = fb b >>= return\n    \n    -- [Kleisli Category - Right Identity Law - Pointful]\n    = fb b\n    \n    -- Goal complete\n\n## Left Identity Law\n\n    Goal: fa />/ respond = fa\n        \n    fa />/ respond\n    \n    -- Definition of '(/>/)'\n    = \\a -> fa a //> respond\n    \n    -- [Respond Category - Left Identity Law - Pointful]\n    = \\a -> fa a\n    \n    -- Eta reduce\n    = fa\n    \n    -- Goal complete\n\n### Pointful\n    \n    Goal: \"Pointful\": p //> respond = p\n    \n    p //> respond\n    -- Definition of `(//>)`\n    = case p of\n        Request x' fx  -> Request x' (\\x -> fx x //> respond)\n        \n                        -- Coinduction: Reuse the premise\n                        = Request x' (\\x -> fx x)\n                        \n                        -- Eta reduce\n                        = Request x' fx\n                        \n        Respond b  fb' -> respond b >>= \\b' -> fb' b' //> respond\n        \n                        -- Coinduction: Reuse the premise\n                        = respond b >>= \\b' -> fb' b'\n                        \n                        -- Eta reduce\n                        = respond b >>= fb'\n                        \n                        -- Definition of `respond`\n                        = Respond b Pure >>= fb'\n                        \n                        -- Definition of `(>>=)`\n                        = Respond b (\\b' -> Pure b' >>= fb')\n                        \n                        -- Definition of `return`, backwards\n                        = Respond b (\\b' -> return b' >>= fb')\n                        \n                        -- [Kleisli Category - Left Identity Law - Pointful]\n                        = Respond b (\\b' -> fb' b')\n                        \n                        -- Eta reduce\n                        = Respond b fb'\n                        \n        M          m   -> M (m >>= \\p' -> return (p' //> respond))\n        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p')\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful]\n                        = M m\n                        \n        Pure    a'      -> Pure a'\n    \n    -- Clean up\n    = case p of\n        Request x' fx  -> Request x' fx\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M           m\n        Pure    a'     -> Pure    a'\n        \n    -- case statement = id\n    = p\n    \n    -- Goal complete\n\n## Associativity Law\n\n    Goal: (fa />/ fb) />/ fc = fa />/ (fb />/ fc)\n\n    (fa />/ fb) />/ fc\n    \n    -- Definition of `(/>/)`\n    \\a -> ((fa />/ fb) a) //> fc\n    \n    -- Definition of `(/>/)`\n    \\a -> (fa a //> fb) //> fc\n    \n    -- [Respond Category - Associativity Law - Pointful]\n    \\a -> fa a //> \\b -> fb b //> fc\n    \n    -- Definition of `(/>/)`, in reverse\n    \\a -> fa a //> (fb />/ fc)\n    \n    -- Definition of `(/>/)`, in reverse\n    fa />/ (fb />/ fc)\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: (p //> fb) //> fc = p //> \\b -> fb b //> fc\n    \n    (p //> fb) //> fc\n    \n    -- Definition of `(//>)`\n    = (case p of\n        Request x' fx  -> Request x' (\\x -> fx x //> fb)\n        Respond b  fb' -> fb b >>= \\b' -> fb' b' //> fb\n        M          m   -> M (m >>= \\p' -> return (p' //> fb))\n        Pure    a'     -> Pure a' ) //> fc\n        \n    -- Distribute over case statement\n    = case p of\n        Request x' fx  -> Request x' (\\x -> fx x //> fb) //> fc\n        \n                        -- Definition of `(//>)`\n                        = Request x' (\\x -> (fx x //> fb) //> fc)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request x' (\\x -> fx x //> \\b -> fb b //> fc)\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = Request x' fx //> \\b -> fb //> fc\n                        \n        Respond b  fb' -> (fb b >>= \\b' -> fb' b' //> fb) //> fc\n        \n                        -- [Respond Category - Distributivity Law - Pointful]\n                        = (fb b //> fc) >>= \\b' -> (fb' b' //> fb) //> fc\n                        \n                        -- Coinduction: Reuse the premise\n                        = (fb b //> fc) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful], in reverse\n                        = ((fb b //> fc) >>= return) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- Definition of `return`\n                        = ((fb b //> fc) >>= Pure) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- Eta expand\n                        = ((fb b //> fc) >>= \\r -> Pure r) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- Definition of `(//>)` in reverse\n                        = ((fb b //> fc) >>= \\r -> Pure r //> \\b -> fb b //> fc) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- Definition of `(//>)` in reverse\n                        = (Respond b Pure //> \\b -> fb b //> fc) >>= \\b' -> fb' b' //> \\b -> fb b //> fc\n                        \n                        -- [Respond Category - Distributivity Law - Pointful], in reverse\n                        = (Respond b Pure >>= \\b' -> fb' b') //> \\b -> fb b //> fc\n                        \n                        -- Eta reduce\n                        = (Respond b Pure >>= fb') //> \\b -> fb b //> fc\n                        \n                        -- Definition of `(>>=)`\n                        = Respond b (\\b' -> Pure b' >>= fb') //> \\b -> fb b //> fc\n                        \n                        -- Definition of `(>>=)`\n                        = Respond b (\\b' -> fb' b') //> \\b -> fb b //> fc\n                        \n                        -- Eta reduce\n                        = Respond b fb' //> \\b -> fb b //> fc\n                        \n        M          m   -> M (m >>= \\p' -> return (p' //> fb)) //> fc\n        \n                        -- Definition of `(//>)`\n                        = M (m >>= \\p' -> return ((p' //> fb) //> fc))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (p' //> \\b -> fb b //> fc))\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = M m //> \\b -> fb b //> fc\n                        \n        Pure    a'      = Pure a' //> fc\n        \n                        -- Definition of `(//>)`\n                        = Pure a'\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = Pure a' //> \\b -> fb b //> fc\n                        \n    -- Clean up\n    = case p of\n        Request x' fx  -> Request x' fx  //> \\b -> fb b //> fc\n        Respond b  fb' -> Respond b  fb' //> \\b -> fb b //> fc\n        M          m   -> M          m   //> \\b -> fb b //> fc\n        Pure       a'  -> Pure    a'     //> \\b -> fb b //> fc\n        \n    -- Factor from case statement\n    = (case p of\n        Request x' fx  -> Request x' fx\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure       a'  -> Pure    a' ) //> \\b -> fb b //> fc\n        \n    -- case statement = id\n    = p //> \\b -> fb b //> fc\n    \n    -- Goal complete\n\n## Distributivity Law\n\n    Goal: (k1 >=> k2) />/ fb = (k1 />/ fb) >=> (k2 />/ fb)\n    \n    (k1 >=> k2) />/ fb\n    \n    -- Definition of `(/>/)`\n    = \\a -> ((k1 >=> k2) a) //> fb\n    \n    -- Definition of `(>=>)`\n    = \\a -> (k1 a >>= k2) //> fb\n    \n    -- [Respond Category - Distributivity Law - Pointful]\n    = \\a -> (k1 a //> fb) >>= \\r -> k2 r //> fb\n    \n    -- Definition of `(/>/)`, in reverse\n    = \\a -> (k1 />/ fb) a >>= \\r -> k2 r //> fb\n    \n    -- Definition of `(/>/)`, in reverse\n    = \\a -> (k1 />/ fb) a >>= (k2 />/ fb)\n    \n    -- Definition of `(>=>)`, in reverse\n    = (k1 />/ fb) >=> (k2 />/ fb)\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: (p >>= k) //> fb = (p //> fb) >>= \\r -> k r //> fb\n    \n    (p >>= k) //> fb\n    \n    -- Definition of `(>>=)`\n    = (case p of\n        Request x' fx  -> Request x' (\\x  -> fx  x  >>= k)\n        Respond b  fb' -> Respond b  (\\b' -> fb' b' >>= k)\n        M          m   -> M (m >>= \\p' -> return (p' >>= k))\n        Pure    r      -> k r ) //> fb\n        \n    -- Distribute over case statement\n    = case p of\n        Request x' fx  -> Request x' (\\x -> fx x >>= k) //> fb\n        \n                        -- Definition of `(//>)`\n                        = Request x' (\\x -> (fx x >>= k) //> fb)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request x' (\\x -> (fx x //> fb) >>= \\r -> k r //> fb)\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Request x' (\\x -> (fx x //> fb)) >>= \\r -> k r //> fb\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = (Request x' fx //> fb) >>= \\r -> k r //> fb\n                        \n        Respond b  fb' -> Respond b (\\b' -> fb' b' >>= k) //> fb\n        \n                        -- Definition of `(//>)`\n                        = fb b (\\b' -> (fb' b' >>= k) //> fb)\n                        \n                        -- Coinduction: Reuse the premise\n                        = fb b >>= \\b' -> (fb' b' //> fb) >>= \\r -> k r //> fb\n                        \n                        -- [Kleisli Category - Associativity Law - Pointful]\n                        = (fb b >>= \\b' -> fb' b' //> fb) >>= \\r -> k r //> fb\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = (Respond b fb' //> fb) >>= \\r -> k r //> fb\n                        \n        M          m   -> M (m >>= \\p' -> return (p >>= k)) //> fb\n        \n                        -- Definition of `(//>)`\n                        = M (m >>= \\p' -> return ((p >>= k) //> fb))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return ((p //> fb) >>= \\r -> k r //> fb))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = M (m >>= \\p' -> return (p //> fb)) >>= \\r -> k r //> fb\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = (M m //> fb) >>= \\r -> k r //> fb\n                        \n        Pure    r      -> k r //> fb\n        \n                        -- Definition of `(>>=)`, in reverse\n                        = Pure r >>= \\r -> k r //> fb\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = (Pure r //> fb) >>= \\r -> k r //> fb\n                        \n    -- Clean up\n    = case p of\n        Request x' fx  -> (Request x' fx  //> fb) >>= \\r -> k r //> fb\n        Respond b  fb' -> (Respond b  fb' //> fb) >>= \\r -> k r //> fb\n        M          m   -> (M          m   //> fb) >>= \\r -> k r //> fb\n        Pure    r      -> (Pure    r      //> fb) >>= \\r -> k r //> fb\n        \n    -- Factor from case statement\n    = ((case p of\n        Request x' fx  -> Request x' fx\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r ) //> fb) >>= \\r -> k r //> fb\n        \n    -- case statement = id\n    = (p //> fb) >>= \\r -> k r //> fb\n    \n    -- Goal complete\n\n## Zero Law\n\n    Goal: return />/ f = return\n    \n    return />/ f\n    \n    -- Definition of `(/>/)`\n    = \\r -> return r //> f\n    \n    -- [Respond Category - Zero Law - Pointful]\n    = \\r -> return r\n    \n    -- Eta reduce\n    = return\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: return r //> f = return r\n    \n    return r //> f\n    \n    -- Definition of `return`\n    = Pure r //> f\n    \n    -- Definition of `(//>)`\n    = Pure r\n    \n    -- Definition of `return`, in reverse\n    = return r\n    \n    -- Goal complete\n\n# Request Category\n\n    Define:\n    \n    request\n        :: (Monad m)\n        =>  a' -> Proxy a' a y' y m a\n    request a' = Request a' Pure\n    \n    (\\>\\)\n        :: (Monad m)\n        => (b' -> Proxy a' a y' y m b)\n        -> (c' -> Proxy b' b y' y m c)\n        -> (c' -> Proxy a' a y' y m c)\n    (fb' \\>\\ fc') c' = fb' >\\\\ fc' c'\n    \n    (>\\\\)\n        :: (Monad m)\n        => (b' -> Proxy a' a y' y m b)\n        ->        Proxy b' b y' y m c\n        ->        Proxy a' a y' y m c\n    fb' >\\\\ p = case p of\n        Request b' fb  -> fb' b' >>= \\b -> fb' >\\\\ fb b\n        Respond y  fy' -> Respond y (\\y' -> fb' >\\\\ fy' y')\n        M          m   -> M (m >>= \\p' -> return (fb' >\\\\ p'))\n        Pure       c   -> Pure c\n\n## Left Identity Law\n\n    Goal: request \\>\\ fc' = fc'\n\n    request \\>\\ fc' = fc'\n    \n    -- Definition of `(\\>\\)`\n    = \\c' -> request >\\\\ fc' c'\n    \n    -- [Request Category - Left Identity Law - Pointful]\n    = \\c' -> fc' c'\n    \n    -- Eta reduce\n    = fc'\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: request >\\\\ p = p\n    \n    -- Definition of `(>\\\\)`\n    case p of\n        Request b' fb  -> request b' >>= \\b -> request >\\\\ fb b\n        \n                        -- Coinduction: Reuse the premise\n                        = request b' >>= \\b -> fb b\n                        \n                        -- Eta reduce\n                        = request b' >>= fb\n                        \n                        -- Definition of `request`\n                        = Request b' Pure >>= fb\n                        \n                        -- Definition of `(>>=)`\n                        = Request b' (\\b -> Pure b >>= fb)\n                        \n                        -- Definition of `(>>=)`\n                        = Request b' (\\b -> fb b)\n                        \n                        -- Eta reduce\n                        = Request b' fb\n                        \n        Respond y  fy' -> Respond y (\\y' -> request >\\\\ fy' y')\n        \n                        -- Coinduction: Reuse the premise\n                        = Respond y (\\y' -> fy' y')\n                        \n                        -- Eta reduce\n                        = Respond y fy'\n                        \n        M          m   -> M (m >>= \\p' -> return (request >\\\\ p'))\n        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p')\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful]\n                        = M m\n                        \n        Pure    c       = Pure c\n    \n    -- Clean up\n    = case p of\n        Request b' fb  -> Request b' fb\n        Respond y  fy' -> Respond y  fy'\n        M          m   -> M          m\n        Pure    c      -> Pure    c\n    \n    -- case statement = if\n    = p\n    \n    -- Goal complete\n\n## Right Identity Law\n\n    Goal: fb' \\>\\ request = fb'\n    \n    fb' \\>\\ request\n    \n    -- Definition of `(\\>\\)`\n    = \\b' -> fb' >\\\\ request b'\n    \n    -- [Request Category - Right Identity Law - Pointful]\n    = \\b' -> fb' b'\n    \n    -- Eta reduce\n    = fb'\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: fb' >\\\\ request b' = fb' b'\n    \n    fb' >\\\\ request b'\n    \n    -- Definition of `request`\n    = fb' >\\\\ Request b' Pure\n    \n    -- Definitoin of `(>\\\\)`\n    = fb' b' >>= \\b -> fb' >\\\\ Pure b\n    \n    -- Definition of `(>\\\\)`\n    = fb' b' >>= \\b -> Pure b\n    \n    -- Eta reduce\n    = fb' b' >>= Pure\n    \n    -- Definition of `return`, in reverse\n    = fb' b' >>= return\n    \n    -- [Kleisli Category - Right Identity Law - Pointful]\n    = fb' b'\n    \n    -- Goal complete\n\n## Associativity Law\n\n    Goal: (f \\>\\ g) \\>\\ h = f \\>\\ (g \\>\\ h)\n    \n    (f \\>\\ g) \\>\\ h\n    \n    -- Definition of `(\\>\\)`\n    = \\x -> (f \\>\\ g) >\\\\ h x\n    \n    -- Definition of `(\\>\\)`\n    = \\x -> (\\y -> f >\\\\ g y) >\\\\ h x\n    \n    -- [Request Category - Composition - Pointful]\n    = \\x -> f >\\\\ (g >\\\\ h x)\n    \n    -- Definition of `(\\>\\)`, in reverse\n    = \\x -> f >\\\\ (g \\>\\ h) x\n    \n    -- Definition of `(\\>\\)`, in reverse\n    = f \\>\\ (g \\>\\ h)\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: fa' >\\\\ (fb' >\\\\ p) = (\\b' -> fa' >\\\\ fb' b') >\\\\ p\n    \n    fa' >\\\\ (fb' >\\\\ p)\n    \n    -- Definition of `(>\\\\)`\n    = fa' >\\\\ (case p of\n        Request b' fb  -> fb' b' >>= \\b -> fb' >\\\\ fb b\n        Respond y  fy' -> Respond y (\\y' -> fb' >\\\\ fy' y')\n        M          m   -> M (m >>= \\p' -> return (fb' >\\\\ p'))\n        Pure    c      -> Pure c\n        \n    -- Distribute over case statement\n    = case p of\n        Request b' fb  -> fa' >\\\\ (fb' b' >>= \\b -> fb' >\\\\ fb b)\n        \n                        -- [Request Category - Distributivity Law]\n                        = (fa' >\\\\ fb' b') >>= \\b -> fa' >\\\\ (fb' >\\\\ fb b)\n                        \n                        -- Coinduction : Reuse the premise\n                        = (fa' >\\\\ fb' b') >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful], in reverse\n                        = ((fa' >\\\\ fb' b') >>= return) >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- Definition of `return`\n                        = ((fa' >\\\\ fb' b') >>= Pure) >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- Eta expand\n                        = ((fa' >\\\\ fb' b') >>= \\r -> Pure r) >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = ((fa' >\\\\ fb' b') >>= \\r -> (\\b' -> fa' >\\\\ fb' b') >\\\\ Pure r) >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = ((\\b' -> fa' >\\\\ fb' b') >\\\\ Request b' Pure) >>= \\b -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fb b\n                        \n                        -- [Request Category - Distributivity Law - Pointful], in reverse\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ (Request b' Pure >>= fb)\n                        \n                        -- Definition of `(>>=)`\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ Request b' (\\b -> Pure b >>= fb)\n                        \n                        -- Definition of `(>>=)`\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ Request b' (\\b -> fb b)\n                        \n                        -- Eta reduce\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ Request b' fb\n                        \n        Respond y  fy' -> fa' >\\\\ Respond y (\\y' -> fb' >\\\\ fy' y')\n        \n                        -- Definition of `(>\\\\)`\n                        = Respond y (\\y' -> fa' >\\\\ (fb' >\\\\ fy' y'))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Respond y (\\y' -> (\\b' -> fa' >\\\\ fb' b') >\\\\ fy' y')\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ Respond y fy'\n                        \n        M          m   -> fa' >\\\\ M (m >>= \\p' -> return (fb' >\\\\ p'))\n        \n                        -- Definition of `(>\\\\)`\n                        = M (m >>= \\p' -> return (fa' >\\\\ (fb' >\\\\ p')))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return ((\\b' -> fa' >\\\\ fb' b') >\\\\ p'))\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ M m\n                        \n        Pure    c       = fa' >\\\\ Pure c\n        \n                        -- Definition of `(>\\\\)`\n                        = Pure c\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (\\b' -> fa' >\\\\ fb' b') >\\\\ Pure c\n    \n    -- Clean up\n    = case p of\n        Request b' fb  -> (\\b' -> fa' >\\\\ fb' b') >\\\\ Request b' fb\n        Request y  fy' -> (\\b' -> fa' >\\\\ fb' b') >\\\\ Respond y  fy'\n        M          m   -> (\\b' -> fa' >\\\\ fb' b') >\\\\ M          m\n        Pure    c      -> (\\b' -> fa' >\\\\ fb' b') >\\\\ Pure    c\n    \n    -- Factor from case statement\n    = (\\b' -> fa' >\\\\ fb' b') >\\\\ (case p of\n        Request b' fb  -> Request b' fb\n        Respond y  fy' -> Respond y  fy'\n        M          m   -> M          m\n        Pure    c      -> Pure    c )\n    \n    -- case statement = id\n    = (\\b' -> fa' >\\\\ fb' b') >\\\\ p\n    \n    -- Goal complete\n    \n## Distributivity Law\n\n    Goal: fb' \\>\\ (k1 >=> k2) = (fb' \\>\\ k1) >=> (fb' \\>\\ k2)\n    \n    fb' \\>\\ (k1 >=> k2)\n    \n    -- Definition of `(\\>\\)`\n    = \\x -> fb' >\\\\ ((k1 >=> k2) x)\n    \n    -- Definition of `(>=>)`\n    = \\x -> fb' >\\\\ (k1 x >>= k2)\n    \n    -- [Request Category - Distributivity Law - Pointful]\n    = \\x -> (fb' >\\\\ k1 x) >>= \\y -> fb' >\\\\ k2 y\n    \n    -- Definition of `(\\>\\)`, in reverse\n    = \\x -> (fb' >\\\\ k1 x) >>= (fb' \\>\\ k2)\n    \n    -- Definition of `(\\>\\)`, in reverse\n    = \\x -> (fb' \\>\\ k1) x >>= (fb' \\>\\ k2)\n    \n    -- Definition of `(>=>)`, in reverse\n    = (fb' \\>\\ k1) >=> (fb' \\>\\ k2)\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: fb' >\\\\ (p >>= k) = (fb' >\\\\ p) >>= \\r -> fb' >\\\\ k r\n    \n    fb' >\\\\ (p >>= k)\n    \n    -- Definition of `(>>=)`\n    = fb' >\\\\ (case p of\n        Request b' fb  -> Request b' (\\b  -> fb  b  >>= k)\n        Respond y  fy' -> Respond y  (\\y' -> fy' y' >>= k)\n        M          m   -> M (m >>= \\p' -> return (p' >>= k))\n        Pure    c      -> k c )\n    \n    -- Distribute over case statement\n    = case p of\n        Request b' fb  -> fb' >\\\\ Request b' (\\b -> fb b >>= k)\n        \n                        -- Definition of `(>\\\\)`\n                        = fb' b' >>= \\b -> fb' >\\\\ (fb b >>= k)\n                        \n                        -- Coinduction: Reuse the premise\n                        = fb' b' >>= \\b -> (fb' >\\\\ fb b) >>= \\r -> fb' >\\\\ k r\n                        \n                        -- [Kleisli Category -- Associativity Law - Pointful]\n                        = (fb' b' >>= \\b -> fb' >\\\\ fb b) >>= \\r -> fb' >\\\\ k r\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (fb' >\\\\ Request b' fb) >>= \\r -> fb' >\\\\ k r\n        \n        Respond y  fy' -> fb' >\\\\ Respond y (\\y' -> fy' y' >>= k)\n                        \n                        -- Definition of `(>\\\\)`\n                        = Respond y (\\y' -> fb' >\\\\ (fy' y' >>= k))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Respond y (\\y' -> (fb' >\\\\ fy' y') >>= \\r -> fb' >\\\\ k r)\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Respond y (\\y' -> (fb' >\\\\ fy' y')) >>= \\r -> fb' >\\\\ k r\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (fb' >\\\\ Respond y fy') >>= \\r -> fb' >\\\\ k r\n                        \n        M          m   -> fb' >\\\\ M (m >>= \\p' -> return (p' >>= k))\n                        \n                        -- Definition of `(>\\\\)`\n                        = M (m >>= \\p' -> return (fb' >\\\\ (p' >>= k)))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return ((fb' >\\\\ p') >>= \\r -> fb' >\\\\ k r))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = M (m >>= \\p' -> return (fb' >\\\\ p')) >>= \\r -> fb' >\\\\ k r\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (fb' >\\\\ M m) >>= \\r -> fb' >\\\\ k r\n                        \n        Pure    c       = fb' >\\\\ k c\n        \n                        -- [Kleisli Category - Left Identity Law - Pointful], in reverse\n                        = return c >>= \\r -> fb' >\\\\ k r\n                        \n                        -- Definition of `return`\n                        = Pure c >>= \\r -> fb' >\\\\ k r\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = (fb' >\\\\ Pure c) >>= \\r -> fb' >\\\\ k r\n\n    -- Clean up\n    = case p of\n        Request b' fb  -> (fb' >\\\\ Request b' fb ) >>= \\r -> fb' >\\\\ k r\n        Respond y  fy' -> (fb' >\\\\ Respond y  fy') >>= \\r -> fb' >\\\\ k r\n        M          m   -> (fb' >\\\\ M          m  ) >>= \\r -> fb' >\\\\ k r\n        Pure    c      -> (fb' >\\\\ Pure    c     ) >>= \\r -> fb' >\\\\ k r\n    \n    -- Factor from case statement\n    = (fb' >\\\\ case p of\n        Request b' fb  -> Request b' fb\n        Respond y  fy' -> Respond y  fy'\n        M          m   -> M          m\n        Pure    c      -> Pure    c ) >>= \\r -> fb' >\\\\ k r\n    \n    -- case statement = id\n    = (fb' >\\\\ p) >>= \\r -> fb' >\\\\ k r\n    \n    -- Goal complete\n\n## Zero Law\n\n    Goal: f \\>\\ return = return\n    \n    f \\>\\ return\n    \n    -- Definition of `(\\>\\)`\n    = \\r -> f >\\\\ return r\n    \n    -- [Request Category - Zero Law - Pointful]\n    = \\r -> return r\n    \n    -- Eta reduce\n    = return\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: f >\\\\ return r = return r\n    \n    f >\\\\ return r\n    \n    -- Definition of `return`\n    = f >\\\\ Pure r\n    \n    -- Definition of `(>\\\\)`\n    = Pure r\n    \n    -- Definition of `return`, in reverse\n    = return r\n    \n    -- Goal complete\n\n# Pull Category\n\n    Define:\n    \n    pull\n        :: (Monad m)\n        =>   a' -> Proxy a' a a' a m r\n    pull a' = Request a' push\n    \n    (>+>)\n        :: (Monad m)\n        => ( b' -> Proxy a' a b' b m r)\n        -> (_c' -> Proxy b' b c' c m r)\n        -> (_c' -> Proxy a' a c' c m r)\n    (fb' >+> fc') c' = fb' +>> fc' c'\n    \n    (+>>)\n        :: (Monad m)\n        => ( b' -> Proxy a' a b' b m r)\n        ->         Proxy b' b c' c m r\n        ->         Proxy a' a c' c m r\n    fb' +>> p = case p of\n        Request b' fb  -> fb' b' >>~ fb\n        Respond c  fc' -> Respond c (\\c' -> fb' +>> fc' c')\n        M          m   -> M (m >>= \\p' -> return (fb' +>> p'))\n        Pure       r   -> Pure r\n        \n## Left Identity Law\n\n    Goal: pull >+> f = f\n    \n    pull >+> f\n    \n    -- Definition of `(>+>)`\n    = \\c' -> pull +>> f c'\n    \n    -- [Pull Category - Left Identity Law - Pointful]\n    = \\c' -> f c'\n    \n    -- Eta reduce\n    = f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: pull +>> p = p\n    \n    pull +>> p\n    \n    -- Definition of `(+>>)`\n    = case p of\n        Request b' fb  -> pull b' >>~ fb\n                        \n                        -- Definition of `pull`\n                        = Request b' (\\b -> Respond b pull) >>~ fb\n                        \n                        -- Definition of `(>>~)`\n                        = Request b' (\\b -> Respond b pull >>~ fb)\n                        \n                        -- Definition of `(>>~)`\n                        = Request b' (\\b -> pull +>> fb b)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request b' (\\b -> fb b)\n                        \n                        -- Eta reduce\n                        = Request b' fb\n                        \n        Respond c  fc' -> Respond c (\\c' -> pull +>> fc' c')\n        \n                        -- Coinduction: Reuse the premise\n                        = Respond c (\\c' -> fc' c')\n                        \n                        -- Eta reduce\n                        = Respond c fc'\n                        \n        M          m   -> M (m >>= \\p' -> return (pull +>> p'))\n        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p')\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful]\n                        = M m\n                        \n        Pure    r      -> Pure r\n    \n    -- Clean up\n    = case p of\n        Request b' fb  -> Request b' fb\n        Respond c  fc' -> Respond c  fc'\n        M          m   -> M          m\n        Pure    r      -> Pure r\n    \n    -- case statement = id\n    = p\n    \n    -- Goal complete\n    \n## Right Identity Law\n\n    Goal: fb' >+> pull = fb'\n    \n    fb' >+> pull\n    \n    -- Definition of `(>+>)`\n    = \\b' -> fb' +>> pull b'\n    \n    -- [Pull Category - Right Identity Law - Pointful]\n    = \\b' -> fb' b'\n    \n    -- Eta reduce\n    = fb'\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: fb' +>> pull b' = fb' b'\n    \n    fb' +>> pull b'\n    \n    -- Definition of `push`\n    = fb' +>> Request b' (\\b -> Respond b pull)\n    \n    -- Definition of `(+>>)`\n    = fb' b' >>~ \\b -> Respond b pull\n    \n    -- Definition of `push`, in reverse\n    = fb' b' >>~ push\n    \n    -- Coinduction: [Push Category - Right Identity Law - Pointful]\n    = fb' b'\n    \n    -- Goal complete\n\n## Associativity Law\n\n    Goal: fb' >+> (fc' >+> fd') = (fb' >+> fc') >+> fd'\n    \n    fb' >+> (fc' >+> fd')\n    \n    -- Definition of `(>+>)`\n    = \\d' -> fb' +>> (fc' >+> fd') d'\n    \n    -- Definition of `(>+>)`\n    = \\d' -> fb' +>> (fc' +>> fd' d')\n    \n    -- [Pull Category - Associativity Law - Pointful]\n    = \\d' -> (\\c' -> fb' +>> fc' c') +>> fd' d'\n    \n    -- Definition of `(>+>)`, in reverse\n    = \\d' -> (fb' >+> fc') +>> fd' d'\n    \n    -- Definition of `(>+>)`, in reverse\n    = (fb' >+> fc') >+> fd'\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: fb' +>> (fc' +>> p) = (\\c' -> fb' +>> fc' c') +>> p\n    \n    fb' +>> (fc' +>> p)\n    \n    -- Definition of `(+>>)`\n    = fb' +>> (case p of\n        Request c' fc  -> fc' c' >>~ fc\n        Respond d  fd' -> Respond d (\\d' -> fc' +>> fd' d')\n        M          m   -> M (m >>= \\p' -> return (fc' +>> p'))\n        Pure    r      -> Pure r )\n        \n    -- Distribute over case statement\n    = case p of\n        Request c' fc  -> fb' +>> (fc' c' >>~ fc)\n        \n                        -- Coinduction: [Push/Pull - Associativity - Pointful]\n                        = (fb' +>> fc' c') >>~ fc\n                       \n                        -- Definition of `(+>>), in reverse\n                        = (\\c' -> fb' +>> fc' c') +>> Request c' fc\n                       \n        Respond d  fd' -> fb' +>> Respond d (\\d' -> fc' +>> fd' d')\n        \n                        -- Definition of `(+>>)`\n                        = Respond d (\\d' -> fb' +>> (fc' +>> fd' d'))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Respond d (\\d' -> (\\c' -> fb' +>> fc' c') +>> fd' d')\n                        \n                        -- Definition of `(+>>)`, in reverse\n                        = (\\c' -> fb' +>> fc' c') +>> Respond d fd'\n        \n        M          m   -> fb' +>> M (m >>= \\p' -> return (fc' +>> p'))\n        \n                        -- Definition of `(+>>)`\n                        = M (m >>= \\p' -> return (fb' +>> (fc' +>> p')))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return ((\\c' -> fb' +>> fc' c') +>> p'))\n                        \n                        -- Definition of `(+>>)`, in reverse\n                        = (\\c' -> fb' +>> fc' c') +>> M m\n                        \n        Pure    r      -> fb' +>> Pure r\n        \n                       -- Definition of `(+>>)`\n                       = Pure r\n                       \n                       -- Definition of `(+>>)`, in reverse\n                       = (\\c' -> fb' +>> fc' c') +>> Pure r\n                       \n    -- Clean up\n    = case p of\n        Request c' fc  -> (\\c' -> fb' +>> fc' c') +>> Request c' fc\n        Respond d  fd' -> (\\c' -> fb' +>> fc' c') +>> Respond d  fd'\n        M          m   -> (\\c' -> fb' +>> fc' c') +>> M          m\n        Pure       r   -> (\\c' -> fb' +>> fc' c') +>> Pure    r\n    \n    -- Factor from case statement\n    = (\\c' -> fb' +>> fc' c') +>> (case p of\n        Request c' fc  -> Request c' fc\n        Respond d  fd' -> Respond d  fd'\n        M          m   -> M          m\n        Pure    r      -> Pure    r )\n    \n    -- case statement = id\n    = (\\c' -> fb' +>> fc' c') +>> p\n    \n    -- Goal complete\n\n# Push Category\n\n    Define:\n\n    push\n        :: (Monad m)\n        =>   a -> Proxy a' a a' a m r\n    push a = Respond a pull\n\n    (>~>)\n        :: (Monad m)\n        => (_a -> Proxy a' a b' b m r)\n        -> ( b -> Proxy b' b c' c m r)\n        -> (_a -> Proxy a' a c' c m r)\n    (f >~> g) x = f x >>~ g\n\n    (>>~)\n        :: (Monad m)\n        =>        Proxy a' a b' b m r\n        -> ( b -> Proxy b' b c' c m r)\n        ->        Proxy a' a c' c m r\n    p >>~ fb = case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>~ fb)\n        Respond b  fb' -> fb' +>> fb b\n        M          m   -> M (m >>= \\p' -> return (p' >>~ fb))\n        Pure    r      -> Pure r\n\n## Left Identity Law\n\n    Goal: push >~> f = f\n    \n    push >~> f\n    \n    -- Definition of `(>~>)`\n    = \\a -> push a >>~ f\n    \n    -- [Push Category - Left Identity Law - Pointful]\n    = \\a -> f a\n    \n    -- Eta reduce\n    = f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: push a >>~ f = f a\n    \n    push a >>~ f\n    \n    -- Definition of `push`\n    = Respond a pull >>~ f\n    \n    -- Definition of `(>>~)`\n    = pull +>> f a\n    \n    -- Coinduction: [Pull Category - Left Identity Law - Pointful]\n    = f a\n    \n    -- Goal complete\n\n## Right Identity Law\n\n    Goal: f >~> push = f\n    \n    f >~> push\n    \n    -- Definition of `(>~>)`\n    = \\a -> f a >>~ push\n    \n    -- [Push Category - Right Identity Law - Pointful]\n    = \\a -> f a\n    \n    -- Eta reduce\n    = f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: p >>~ push = p\n    \n    p >>~ push\n    \n    -- Definition of `(>>~)`\n    = case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>~ push)\n         \n                        -- Coinduction: Reuse the premise\n                        = Request a' (\\a -> fa a)\n                        \n                        -- Eta reduce\n                        = Request a' fa\n                       \n        Respond b  fb' -> fb' +>> push b\n        \n                        -- Definition of `push`\n                        = fb' +>> Respond b pull\n                        \n                        -- Definition of `(+>>)`\n                        = Respond b (fb' +>> pull)\n                        \n                        -- [Pull Category - Right Identity Law - Pointful]\n                        = Respond b fb'\n                        \n        M          m   -> M (m >>= \\p' -> return (p >>~ push))\n        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p)\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful]\n                        = M m\n                        \n        Pure    r      -> Pure r\n    \n    -- Clean up\n    = case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r\n    \n    -- case statement = id\n    = p\n    \n    -- Goal complete\n    \n## Associativity Law\n\n    Goal: (fa >~> fb) >~> fc = fa >~> (fb >~> fc)\n    \n    (fa >~> fb) >~> fc\n    \n    -- Definition of `(>~>)`\n    = \\a -> (fa >~> fb) a >>~ fc\n    \n    -- Definition of `(>~>)`\n    = \\a -> (fa a >>~ fb) >>~ fc\n    \n    -- [Push Category - Associativity Law - Pointful]\n    = \\a -> fa a >>~ \\b -> fb b >>~ fc\n    \n    -- Definition of `(>~>)`, in reverse\n    = \\a -> fa a >>~ (fb >~> fc)\n    \n    -- Definition of `(>~>)`, in reverse\n    = fa >~> (fb >~> fc)`\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: (p >>~ fb) >>~ fc = p >>~ \\b -> fb b >>~ fc\n    \n    (p >>~ fb) >>~ fc\n    \n    -- Definition of `(>>~)`\n    = (case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>~ fb)\n        Respond b  fb' -> fb' +>> fb b\n        M          m   -> M (m >>= \\p' -> return (p' >>~ fb))\n        Pure    r      -> Pure r ) >>~ fc\n        \n    -- Distribute over case statement\n    = case p of\n        Request a' fa  -> Request a' (\\a -> fa a >>~ fb) >>~ fc\n        \n                        -- Definition of `(>>~)`\n                        = Request a' (\\a -> (fa a >>~ fb) >>~ fc)\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request a' (\\a -> fa a >>~ \\b -> fb b >>~ fc)\n                        \n                        -- Definition of `(>>~), in reverse\n                        = Request a' fa >>~ \\b -> fb b >>~ fc\n                       \n        Respond b  fb' -> (fb' +>> fb b) >>~ fc\n        \n                        -- Coinduction: [Push/Pull - Associativity - Pointful]\n                        = fb' +>> (fb b >>~ fc)\n                        \n                        -- Definition of `(>>~)`, in reverse\n                        = Respond b fb' >>~ \\b -> fb b >>~ fc\n                        \n        M          m   -> M (m >>= \\p' -> return (p' >>~ fb)) >>~ fc\n        \n                        -- Definition of `(>>~)`\n                        = M (m >>= \\p' -> return ((p >>~ fb) >>~ fc))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (p >>~ \\b -> fb b >>~ fc))\n                        \n                        -- Definition of `(>>~), in reverse\n                        = M m >>~ \\b -> fb b >>~ fc\n                        \n        Pure    r      -> Pure r >>~ fc\n        \n                        -- Definition of `(>>~)`\n                        = Pure r\n                        \n                        -- Definition of `(>>~)`, in reverse\n                        = Pure r >>~ \\b -> fb b >>~ fc\n                        \n    -- Clean up\n    = case p of\n        Request a' fa  -> Request a' fa  >>~ \\b -> fb b >>~ fc\n        Respond b  fb' -> Respond b  fb' >>~ \\b -> fb b >>~ fc\n        M          m   -> M          m   >>~ \\b -> fb b >>~ fc\n        Pure    r      -> Pure    r      >>~ \\b -> fb b >>~ fc\n        \n    -- Factor from case statement\n    = (case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r ) >>~ \\b -> fb b >>~ fc\n        \n    -- case statement = id\n    = p >>~ \\b -> fb b >>~ fc\n    \n    -- Goal complete\n        \n# Push/Pull\n\n## Associativity\n\n    Goal: (f >+> g) >~> h = f >+> (g >~> h)\n    \n    (f >+> g) >~> h\n    \n    -- Definition of `(>~>)`\n    = \\x -> (f >+> g) x >>~ h\n    \n    -- Definition of `(>+>)`\n    = \\x -> (f +>> g x) >>~ h\n    \n    -- [Push/Pull - Associativity - Pointful]\n    = \\x -> f +>> (g x >>~ h)\n    \n    -- Definition of `(>~>)`, in reverse\n    = \\x -> f +>> (g >~> h)x\n    \n    -- Definition of `(>+>)`, in reverse\n    = f >+> (g >~> h)\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: (fb' +>> p) >>~ fc = fb' +>> (p >>~ fc)\n    \n    (fb' +>> p) >>~ fc\n    \n    -- Definition of `(+>>)`\n    = (case p of\n        Request b' fb  -> fb' b' >>~ fb\n        Respond c  fc' -> Respond c (\\c' -> fb' +>> fc' c')\n        M          m   -> M (m >>= \\p' -> return (fb' +>> p'))\n        Pure    r      -> Pure r ) >>~ fc\n        \n    -- Distribute over case statement\n    = case p of\n        Request b' fb  -> (fb' b' >>~ fb) >>~ fc\n        \n                        -- Coinduction: [Push Category - Associativity Law - Pointful]\n                        = fb' b' >>~ \\b -> fb b >>~ fc\n                        \n                        -- Definition of `(+>>)`, in reverse\n                        = fb' +>> Request b' (\\b -> fb b >>~ fc)\n                       \n                        -- Definition of `(>>~)`, in reverse\n                        = fb' +>> (Request b' fb >>~ fc)\n                       \n        Respond c  fc' -> Respond c (\\c' -> fb' +>> fc' c') >>~ fc\n        \n                        -- Definition of `(>>~)`\n                        = (\\c' -> fb' +>> fc' c') +>> fc c\n                        \n                        -- Coinduction: [Pull Category - Associativity Law - Pointful]\n                        = fb' +>> (fc' +>> fc c)\n                        \n                        -- Definition of `(>>~)`, in reverse\n                        = fb' +>> (Respond c fc' >>~ fc)\n                        \n        M          m   -> M (m >>= \\p' -> return (fb' +>> p')) >>~ fc\n        \n                        -- Definition of `(>>~)`\n                        = M (m >>= \\p' -> return ((fb' +>> p') >>~ fc))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (fb' +>> (p' >>~ fc))\n                        \n                        -- Definition of `(+>>)`, in reverse\n                        = fb' +>> M (m >>= \\p' -> return (p' >>~ fc))\n                        \n                        -- Definition of `(>>~)`, in reverse\n                        = fb' +>> (M m >>~ fc)\n                        \n        Pure    r      -> Pure r >>~ fc\n         \n                        -- Definition of `(+>>)`, in reverse\n                        = fb' +>> (Pure r >>~ fc)\n                        \n    -- Clean up\n    = case p of\n        Request b' fb  -> fb' +>> (Request b' fb  >>~ fc)\n        Respond c  fc' -> fb' +>> (Respond c  fc' >>~ fc)\n        M          m   -> fb' +>> (M          m   >>~ fc)\n        Pure    r      -> fb' +>> (Pure    r      >>~ fc)\n        \n    -- Factor from case statement\n    = fb' +>> ((case p of\n        Request b' fb  -> Request b' fb\n        Respond c  fc' -> Respond c  fc'\n        M          m   -> M          m\n        Pure    r      -> Pure    r ) >>~ fc)\n        \n    -- case statement = id\n    = fb' +>> (p >>~ fc)\n    \n    -- Goal complete\n    \n# Duals\n\n    Define:\n    \n    reflect\n        :: (Monad m)\n        => Proxy a' a b' b m r\n        -> Proxy b b' a a' m r\n    reflect p = case p of\n        Request a' fa  -> Respond a' (\\a  -> go (fa  a ))\n        Respond b  fb' -> Request b  (\\b' -> go (fb' b'))\n        M          m   -> M (m >>= \\p' -> return (go p'))\n        Pure    r      -> Pure r\n\n## Request Identity\n\n    Goal: reflect . request = respond\n    \n    reflect . request\n    \n    -- Definition of `(.)`\n    = \\a' -> reflect (request a')\n    \n    -- [Dual - Request Identity - Pointful]\n    = \\a' -> respond a'\n    \n    -- Eta reduce\n    = respond\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: reflect (request x) = respond x\n    \n    reflect (request x)\n    \n    -- Definition of `request`\n    = reflect (Request x Pure)\n    \n    -- Definition of `reflect`\n    = Respond x (\\r -> reflect (Pure r))\n    \n    -- Definition of `reflect`\n    = Respond x (\\r -> Pure r)\n    \n    -- Eta reduce\n    = Respond x Pure\n    \n    -- Definition of `respond`, in reverse\n    = respond\n    \n    -- Goal complete\n\n## Request Composition\n\n    Goal: reflect . (f \\>\\ g) = reflect . g />/ reflect . f\n    \n    reflect . (f \\>\\ g)\n    \n    -- Definition of `(.)`\n    = \\a -> reflect ((f \\>\\ g) a)\n    \n    -- Definition of `(\\>\\)`\n    = \\a -> reflect (f >\\\\ g a)\n    \n    -- [Dual - Request Composition - Pointful]\n    = \\a -> reflect (g a) //> reflect . f\n    \n    -- Definition of `(.)`, in reverse\n    = \\a -> (reflect . g) a //> reflect . f\n    \n    -- Definition of `(/>/)`, in reverse\n    = reflect . g />/ reflect . f\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: reflect (f >\\\\ p) = reflect p //> reflect . f\n    \n    reflect (f >\\\\ p)\n    \n    -- Definition of `(>\\\\)`\n    = reflect (case p of\n        Request b' fb  -> f b' >>= \\b -> f >\\\\ f b\n        Respond x  fx' -> Respond x (\\x' -> f >\\\\ fx' x')\n        M          m   -> M (m >>= \\p' -> return (f >\\\\ p'))\n        Pure       c   -> Pure c )\n        \n    -- Distribute over case statement\n    = case p of\n        Request b' fb  -> reflect (f b' >>= \\b -> f >\\\\ fb b)\n        \n                        -- [Dual - Distributivity Law - Pointful]\n                        = reflect (f b') >>= \\b -> reflect (f >\\\\ fb b)\n                        \n                        -- Coinduction: Reuse the premise\n                        = reflect (f b') >>= \\b -> reflect (fb b) //> reflect . f\n                        \n                        -- Definition of `(.)`, in reverse\n                        = (reflect . f) b' >>= \\b -> reflect (fb b) //> reflect . f\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = Respond b' (\\b -> reflect (fb b)) //> reflect . f\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect (Request b' fb) //> reflect . f\n                        \n        Respond x  fx' -> reflect (Respond x (\\x' -> f >\\\\ fx' x'))\n        \n                        -- Definition of `reflect`\n                        = Request x (\\x' -> reflect (f >\\\\ fx' x'))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request x (\\x' -> reflect (fx' x') //> reflect . f)\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = Request x (\\x' -> reflect (fx' x')) //> reflect . f\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect (Respond x fx') //> reflect . f\n                        \n        M          m   -> reflect (M (m >>= \\p' -> return (f >\\\\ p')))\n        \n                        -- Definition of `reflect`\n                        = M (m >>= \\p' -> return (reflect (f >\\\\ p')))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (reflect p' //> reflect . f))\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = M (m >>= \\p' -> return (reflect p')) //> reflect . f\n                        \n                        -- Definition of `reflect, in reverse\n                        = reflect (M m) //> reflect . f\n                        \n        Pure    c       = reflect (Pure c)\n        \n                        -- Definition of `reflect\n                        = Pure c\n                        \n                        -- Definition of `(//>)`, in reverse\n                        = Pure c //> reflect . f\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect (Pure c) //> reflect .f\n                        \n    -- Clean up\n    = case p of\n        Request b' fb  -> reflect (Request b' fb ) //> reflect . f\n        Respond x  fx' -> reflect (Respond x  fx') //> reflect . f\n        M          m   -> reflect (M          m  ) //> reflect . f\n        Pure       c   -> reflect (Pure    c     ) //> reflect . f\n        \n    -- Factor from case statement\n    = reflect (case p of\n        Request b' fb  -> Request b' fb\n        Respond x  fx' -> Respond x  fx'\n        M          m   -> M          m\n        Pure       c   -> Pure     c ) //> reflect . f\n        \n    -- case statement = id\n    = reflect p //> reflect . f\n    \n    -- Goal complete\n\n## Respond Identity\n\n    Goal: reflect . respond = request\n    \n    reflect . respond\n    \n    -- Definition of `(.)`\n    = \\a -> reflect (respond a)\n    \n    -- [Dual - Respond Identity - Pointful]\n    = \\a -> request a\n    \n    -- Eta reduce\n    = request\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: reflect (respond x) = request x\n    \n    reflect (respond x)\n    \n    -- Definition of `respond`\n    = reflect (Respond x Pure)\n    \n    -- Definition of `reflect`\n    = Request x (\\r -> reflect (Pure r))\n    \n    -- Definition of `reflect`\n    = Request x (\\r -> Pure r)\n    \n    -- Eta reduce\n    = Request x Pure\n    \n    -- Definition of `request`, in reverse\n    = request\n     \n    -- Goal complete\n\n## Respond Composition\n\n    Goal: reflect . (f />/ g) = reflect . g \\>\\ reflect . f\n    \n    reflect . (f />/ g)\n    \n    -- Definition of `(.)`\n    = \\x -> reflect ((f />/ g) x)\n    \n    -- Definition of `(/>/)`\n    = \\x -> reflect (f x //> g)\n    \n    -- [Dual - Respond Composition - Pointful]\n    = \\x -> reflect . g >\\\\ reflect (f x)\n    \n    -- Definition of `(.)`, in reverse\n    = \\x -> reflect . g >\\\\ (reflect . f) x\n    \n    -- Definition of `(\\>\\)`, in reverse\n    = reflect . g \\>\\ reflect . f\n    \n    -- Goal complete\n\n### Pointful\n\n    Goal: reflect (p //> f) = reflect . f >\\\\ reflect p\n    \n    reflect (p //> f)\n    \n    -- Definition of `(//>)`\n    = reflect (case p of\n        Request x' fx  -> Request x' (\\x -> fx x //> f)\n        Respond b  fb' -> f b >>= \\b' -> fb' b' //> f\n        M          m   -> M (m >>= \\p' -> return (p' //> f))\n        Pure    a'     -> Pure a' )\n        \n    -- Distribute over case statement\n    = case p of\n        Request x' fx  -> reflect (Request x' (\\x -> fx x //> f))\n        \n                         -- Definition of `reflect`\n                         = Respond x' (\\x -> reflect (fx x //> f))\n                         \n                         -- Coinduction: Reuse the premise\n                         = Respond x' (\\x -> reflect . f >\\\\ reflect (fx x))\n                         \n                         -- Definition of `(>\\\\)`, in reverse\n                         = reflect . f >\\\\ Respond x' (\\x -> reflect (fx x))\n                         \n                         -- Definition of `reflect`, in reverse\n                         = reflect . f >\\\\ reflect (Request x' fx)\n                         \n        Respond b  fb' -> reflect (f b >>= \\b' -> fb' b' //> f)\n        \n                        -- [Dual - Distributivity Law - Pointful]\n                        = reflect (f b) >>= \\b' -> reflect (fb' b' //> f)\n                        \n                        -- Coinduction: Reuse the premise\n                        = reflect (f b) >>= \\b' -> reflect . f >\\\\ reflect (fb' b')\n                        \n                        -- Definition of `(.)`\n                        = (reflect . f) b >>= \\b' -> reflect . f >\\\\ reflect (fb' b')\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = reflect . f >\\\\ (Request b (\\b' -> reflect (fb' b')))\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect . f >\\\\ reflect (Respond b fb')\n                        \n        M          m    = reflect (M (m >>= \\p' -> return (p' //> f)))\n        \n                        -- Definition of `reflect`\n                        = M (m >>= \\p' -> return (reflect (p' //> f)))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (reflect . f >\\\\ reflect p'))\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = reflect . f >\\\\ M (m >>= \\p' -> return (reflect p'))\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect . f >\\\\ reflect (M m)\n                        \n        Pure    a'      = reflect (Pure a')\n        \n                        -- Definition of `reflect`\n                        = Pure a'\n                        \n                        -- Definition of `(>\\\\)`, in reverse\n                        = reflect . f >\\\\ Pure a'\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect . f >\\\\ reflect (Pure a')\n                        \n    -- Clean up\n    = case p of\n        Request x' fx  -> reflect . f >\\\\ reflect (Request x' fx )\n        Respond b  fb' -> reflect . f >\\\\ reflect (Respond b  fb')\n        M          m   -> reflect . f >\\\\ reflect (M          m  )\n        Pure    a'     -> reflect . f >\\\\ reflect (Pure    a'    )\n    \n    -- Factor from case statement\n    = reflect . f >\\\\ reflect (case p of\n        Request x' fx  -> Request x' fx\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    a'     -> Pure    a' )\n    \n    -- case statement = id\n    = reflect . f >\\\\ reflect p\n    \n    -- Goal complete\n    \n## Distributivity Law\n\n    Goal: reflect . (f >=> g) = reflect . f >=> reflect . g\n    \n    reflect . (f >=> g)\n    \n    -- Definition of `(.)`\n    = \\x -> reflect ((f >=> g) x)\n    \n    -- Definition of `(>=>)`\n    = \\x -> reflect (f x >>= g)\n    \n    -- [Dual - Distributive Law - Pointful]\n    = \\x -> reflect (f x) >>= \\y -> reflect (g y)\n    \n    -- Definition of `(.)`, in reverse\n    = \\x -> reflect (f x) >>= reflect . g\n    \n    -- Definition of `(.)`, in reverse\n    = \\x -> ((reflect . f) x >>= reflect . g)\n    \n    -- Definition of `(>=>)`, in reverse\n    = reflect . f >=> reflect . g\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: reflect (p >>= f) = reflect p >>= \\x -> reflect (f x)\n    \n    reflect (p >>= f)\n    \n    -- Definition of `(>>=)`\n    = reflect (case p of\n        Request a' fa  -> Request a' (\\a  -> fa  a  >>= f)\n        Respond b  fb' -> Respond b  (\\b' -> fb' b' >>= f)\n        M          m   -> M (m >>= \\p' -> return (p' >>= f))\n        Pure    r      -> f r )\n        \n    -- Distribute over case statement\n    = case p of\n        Request a' fa  -> reflect (Request a' (\\a -> fa a >>= f))\n        \n                        -- Definition of `reflect`\n                        = Respond a' (\\a -> reflect (fa a >>= f))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Respond a' (\\a -> reflect (fa a) >>= \\x -> reflect (f x))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Respond a' (\\a -> reflect (fa a)) >>= \\x -> reflect (f x)\n                        \n                        -- Definition of `reflect`, in revrse\n                        = reflect (Request a' (\\a -> fa a)) >>= \\x -> reflect (f x)\n                        \n                        -- Eta reduce\n                        = reflect (Request a' fa) >>= \\x -> reflect (f x)\n                        \n        Respond b  fb' -> reflect (Respond b (\\b' -> fb' b' >>= f))\n        \n                        -- Definition of `reflect`\n                        = Request b (\\b' -> reflect (fb' b' >>= f))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request b (\\b' -> reflect (fb' b') >>= \\x -> reflect (f x))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = Request b (\\b' -> reflect (fb' b')) >>= \\x -> reflect (f x)\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect (Respond b (\\b' -> fb' b')) >>= \\x -> reflect (f x)\n                        \n                        -- Eta reduce\n                        = reflect (Respond b fb') >>= \\x -> reflect (f x)\n                        \n        M          m   -> reflect (M (m >>= \\p' -> return (p' >>= f)))\n        \n                        -- Definition of `reflect`\n                        = M (m >>= \\p' -> return (reflect (p' >>= f)))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return (reflect p' >>= \\x -> reflect (f x)))\n                        \n                        -- Definition of `(>>=)`, in reverse\n                        = M (m >>= \\p' -> return (reflect p')) >>= \\x -> reflect (f x)\n                        \n                        -- Definition of `reflect`, in reverse\n                        = reflect (M m) >>= \\x -> reflect (f x)\n                        \n        Pure    r      -> reflect (f r)\n        \n                        -- [Kleisli Category - Left Identity - Pointful]\n                        reflect (return r >>= f)\n                        \n                        -- Coinduction: Reuse the premise\n                        reflect (return r) >>= \\x -> return (f x)\n                        \n                        -- Definition of `return`\n                        reflect (Pure r) >>= \\x -> return (f x)\n                        \n    -- Cleanup\n    = case p of\n        Request a' fa  -> reflect (Request a' fa ) >>= \\x -> reflect (f x)\n        Respond b  fb' -> reflect (Respond b  fb') >>= \\x -> reflect (f x)\n        M          m   -> reflect (M          m  ) >>= \\x -> reflect (f x)\n        Pure    r      -> reflect (Pure    r     ) >>= \\x -> reflect (f x)\n        \n    -- Factor from case statement\n    = reflect (case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure    r      -> Pure    r ) >>= \\x -> reflect (f x)\n        \n    -- case statement = id\n    = reflect p >>= \\x -> reflect (f x)\n    \n    -- Goal complete\n    \n## Zero Law\n\n    Goal: reflect . return = return\n    \n    reflect . return\n    \n    -- Definition of `(.)`\n    = \\r -> reflect (return r)\n    \n    -- [Dual - Zero Law - Pointful]\n    = \\r -> return r\n    \n    -- Eta reduce\n    = return\n    \n    -- Goal complete\n    \n### Pointful\n\n    Goal: reflect (return r) = return r\n    \n    reflect (return r)\n    \n    -- Definition of `return`\n    = reflect (Pure r)\n    \n    -- Definition of `reflect`\n    = Pure r\n    \n    -- Definition of `return`, in reverse\n    = return r\n    \n    -- Goal complete\n    \n## Involution\n\n    Goal: reflect . reflect = id\n    \n    reflect . reflect\n    \n    -- Definition of `(.)`\n    = \\p -> reflect (reflect p)\n    \n    -- [Dual - Involution]\n    = \\p -> p\n    \n    -- Definition of `id`\n    = id\n    \n    -- Goal complete\n    \n### Pointful\n\n    reflect (reflect p) = p\n    \n    reflect (reflect p)\n    \n    -- Definition of `reflect`\n    = reflect (case p of\n        Request a' fa  -> Respond a' (\\a  -> reflect (fa  a ))\n        Respond b  fb' -> Request b  (\\b' -> reflect (fb' b'))\n        M          m   -> M (m >>= \\p' -> return (reflect p'))\n        Pure    r      -> Pure r )\n    \n    -- Distribute over case statement\n    = case p of\n        Request a' fa  -> reflect (Respond a' (\\a -> reflect (fa a))\n        \n                        -- Definition of `reflect`\n                        = Request a' (\\a -> reflect (reflect (fa  a)))\n                        \n                        -- Coinduction: Reuse the premise\n                        = Request a' (\\a -> fa a)\n                        \n                        -- Eta reduction\n                        = Request a' fa\n                        \n        Respond b  fb' -> reflect (Request b (\\b' -> reflect (fb' b')))\n         \n                        -- Definition of `reflect`\n                        = Request b (\\b' -> reflect (reflect (fb' b')))\n                         \n                        -- Coinduction: Reuse the premise\n                        = Request b (\\b' -> fb' b')\n                         \n                        -- Eta reduction\n                        = Request b fb'\n                         \n        M          m   -> reflect (M (m >>= \\p' -> return (reflect p')))\n        \n                        -- Definition of `reflect`\n                        = M (m >>= \\p' -> return (reflect (reflect p')))\n                        \n                        -- Coinduction: Reuse the premise\n                        = M (m >>= \\p' -> return p')\n                        \n                        -- Eta reduce\n                        = M (m >>= return)\n                        \n                        -- [Kleisli Category - Right Identity Law - Pointful]\n                        = M m\n                        \n        Pure    r      -> reflect (Pure r)\n        \n                        -- Definition of `reflect`\n                        = Pure r\n                        \n    -- Clean up\n    = case p of\n        Request a' fa  -> Request a' fa\n        Respond b  fb' -> Respond b  fb'\n        M          m   -> M          m\n        Pure       r   -> Pure r\n    \n    -- case statement = id\n    = p\n    \n    -- Goal complete"
  },
  {
    "path": "nix/.gitkeep",
    "content": ""
  },
  {
    "path": "pipes.cabal",
    "content": "Name: pipes\nVersion: 4.3.16\nCabal-Version: >= 1.10\nBuild-Type: Simple\nTested-With: GHC == 7.10.3, GHC == 8.0.2, GHC == 8.2.2, GHC == 8.4.4, GHC == 8.6.5, GHC == 8.8.1\nLicense: BSD3\nLicense-File: LICENSE\nCopyright: 2012-2016 Gabriella Gonzalez\nAuthor: Gabriella Gonzalez\nMaintainer: GenuineGabriella@gmail.com\nBug-Reports: https://github.com/Gabriella439/Haskell-Pipes-Library/issues\nSynopsis: Compositional pipelines\nDescription:\n  `pipes` is a clean and powerful stream processing library that lets you build\n  and connect reusable streaming components\n  .\n  Advantages over traditional streaming libraries:\n  .\n  * /Concise API/: Use simple commands like 'for', ('>->'), 'await', and 'yield'\n  .\n  * /Blazing fast/: Implementation tuned for speed, including shortcut fusion\n  .\n  * /Lightweight Dependency/: @pipes@ is small and compiles very rapidly,\n    including dependencies\n  .\n  * /Elegant semantics/: Use practical category theory\n  .\n  * /ListT/: Correct implementation of 'ListT' that interconverts with pipes\n  .\n  * /Bidirectionality/: Implement duplex channels\n  .\n  * /Extensive Documentation/: Second to none!\n  .\n  Import \"Pipes\" to use the library.\n  .\n  Read \"Pipes.Tutorial\" for an extensive tutorial.\nCategory: Control, Pipes\nExtra-Source-Files:\n    CHANGELOG.md\nSource-Repository head\n    Type: git\n    Location: https://github.com/Gabriella439/Haskell-Pipes-Library\n\nLibrary\n    Default-Language: Haskell2010\n\n    HS-Source-Dirs: src\n    Build-Depends:\n        base         >= 4.8     && < 5   ,\n        transformers >= 0.2.0.0 && < 0.7 ,\n        exceptions   >= 0.4     && < 0.11,\n        mmorph       >= 1.0.4   && < 1.3 ,\n        mtl          >= 2.2.1   && < 2.4 ,\n        void         >= 0.4     && < 0.8\n\n    if impl(ghc < 8.0)\n        Build-depends:\n            fail       == 4.9.*         ,\n            semigroups >= 0.17 && < 0.20\n\n    Exposed-Modules:\n        Pipes,\n        Pipes.Core,\n        Pipes.Internal,\n        Pipes.Lift,\n        Pipes.Prelude,\n        Pipes.Tutorial\n    GHC-Options: -O2 -Wall\n\nBenchmark prelude-benchmarks\n    Default-Language: Haskell2010\n    Type:             exitcode-stdio-1.0\n    HS-Source-Dirs:   benchmarks\n    Main-Is:          PreludeBench.hs\n    Other-Modules:    Common\n    GHC-Options:     -O2 -Wall -rtsopts -fno-warn-unused-do-bind\n\n    Build-Depends:\n        base      >= 4.4     && < 5  ,\n        criterion >= 1.1.1.0 && < 1.7,\n        optparse-applicative >= 0.12 && < 0.18,\n        mtl       >= 2.1     && < 2.4,\n        pipes\n\ntest-suite tests\n    Default-Language: Haskell2010\n    Type:             exitcode-stdio-1.0\n    HS-Source-Dirs:   tests\n    Main-Is:          Main.hs\n    GHC-Options:      -Wall -rtsopts -fno-warn-missing-signatures -fno-enable-rewrite-rules\n\n    Build-Depends:\n        base                       >= 4.4     && < 5   ,\n        pipes                                          ,\n        QuickCheck                 >= 2.4     && < 3   ,\n        mtl                        >= 2.1     && < 2.4 ,\n        test-framework             >= 0.4     && < 1   ,\n        test-framework-quickcheck2 >= 0.2.0   && < 0.4 ,\n        transformers               >= 0.2.0.0 && < 0.7\n\nBenchmark lift-benchmarks\n    Default-Language: Haskell2010\n    Type:             exitcode-stdio-1.0\n    HS-Source-Dirs:   benchmarks\n    Main-Is:          LiftBench.hs\n    Other-Modules:    Common\n    GHC-Options:     -O2 -Wall -rtsopts -fno-warn-unused-do-bind\n\n    Build-Depends:\n        base                 >= 4.4     && < 5   ,\n        criterion            >= 1.1.1.0 && < 1.7 ,\n        optparse-applicative                     ,\n        mtl                  >= 2.1     && < 2.4 ,\n        pipes                                    ,\n        transformers         >= 0.2.0.0 && < 0.7\n"
  },
  {
    "path": "release.nix",
    "content": "let\n  overlay = pkgsNew: pkgsOld: {\n    haskellPackages = pkgsOld.haskellPackages.override (old: {\n      overrides =\n        pkgsNew.lib.fold pkgsNew.lib.composeExtensions\n          (old.overrides or (_: _: { }))\n          [ (pkgsNew.haskell.lib.packageSourceOverrides {\n              pipes = ./.;\n            })\n            (pkgsNew.haskell.lib.packagesFromDirectory {\n              directory = ./nix;\n            })\n            (haskellPackagesNew: haskellPackagesOld: {\n            })\n          ];\n    });\n  };\n\n  nixpkgs = builtins.fetchTarball {\n    url = \"https://github.com/NixOs/nixpkgs/archive/1b55bc5d4b5cb6b35d71e7fe22cae9558c312937.tar.gz\";\n\n    sha256 = \"05761c8bi6chlj15428h3k30r8b8g4w3h0m4xpsj6f9qcz27d9nf\";\n  };\n\n  pkgs = import nixpkgs { config = { }; overlays = [ overlay ]; };\n\nin\n  { pipes = pkgs.haskellPackages.pipes;\n  }\n"
  },
  {
    "path": "shell.nix",
    "content": "(import ./release.nix).pipes.env\n"
  },
  {
    "path": "src/Pipes/Core.hs",
    "content": "{-| The core functionality for the 'Proxy' monad transformer\n\n    Read \"Pipes.Tutorial\" if you want a beginners tutorial explaining how to use\n    this library.  The documentation in this module targets more advanced users\n    who want to understand the theory behind this library.\n\n    This module is not exported by default, and I recommend you use the\n    unidirectional operations exported by the \"Pipes\" module if you can.  You\n    should only use this module if you require advanced features like:\n\n    * bidirectional communication, or:\n\n    * push-based 'Pipe's.\n-}\n\n{-# LANGUAGE RankNTypes, Trustworthy #-}\n\nmodule Pipes.Core (\n    -- * Proxy Monad Transformer\n    -- $proxy\n      Proxy\n    , runEffect\n\n    -- * Categories\n    -- $categories\n\n    -- ** Respond\n    -- $respond\n    , respond\n    , (/>/)\n    , (//>)\n\n    -- ** Request\n    -- $request\n    , request\n    , (\\>\\)\n    , (>\\\\)\n\n    -- ** Push\n    -- $push\n    , push\n    , (>~>)\n    , (>>~)\n\n    -- ** Pull\n    -- $pull\n    , pull\n    , (>+>)\n    , (+>>)\n\n    -- ** Reflect\n    -- $reflect\n    , reflect\n\n    -- * Concrete Type Synonyms\n    , X\n    , Effect\n    , Producer\n    , Pipe\n    , Consumer\n    , Client\n    , Server\n\n    -- * Polymorphic Type Synonyms\n    , Effect'\n    , Producer'\n    , Consumer'\n    , Client'\n    , Server'\n\n    -- * Flipped operators\n    , (\\<\\)\n    , (/</)\n    , (<~<)\n    , (~<<)\n    , (<+<)\n    , (<\\\\)\n    , (//<)\n    , (<<+)\n\n    -- * Re-exports\n    , closed\n    ) where\n\nimport Pipes.Internal (Proxy(..), X, closed)\n\n{- $proxy\n    Diagrammatically, you can think of a 'Proxy' as having the following shape:\n\n@\n Upstream | Downstream\n     +---------+\n     |         |\n a' <==       <== b'\n     |         |\n a  ==>       ==> b\n     |    |    |\n     +----|----+\n          v\n          r\n@\n\n    You can connect proxies together in five different ways:\n\n    * ('Pipes.>+>'): connect pull-based streams\n\n    * ('Pipes.>~>'): connect push-based streams\n\n    * ('Pipes.\\>\\'): chain folds\n\n    * ('Pipes./>/'): chain unfolds\n\n    * ('Control.Monad.>=>'): sequence proxies\n\n-}\n\n-- | Run a self-contained 'Effect', converting it back to the base monad\nrunEffect :: Monad m => Effect m r -> m r\nrunEffect = go\n  where\n    go p = case p of\n        Request v _ -> closed v\n        Respond v _ -> closed v\n        M       m   -> m >>= go\n        Pure    r   -> return r\n{-# INLINABLE runEffect #-}\n\n{- * Keep proxy composition lower in precedence than function composition, which\n     is 9 at the time of of this comment, so that users can write things like:\n\n\n> lift . k >+> p\n>\n> hoist f . k >+> p\n\n   * Keep the priorities different so that users can mix composition operators\n     like:\n\n> up \\>\\ p />/ dn\n>\n> up >~> p >+> dn\n\n   * Keep 'request' and 'respond' composition lower in precedence than 'pull'\n     and 'push' composition, so that users can do:\n\n> read \\>\\ pull >+> writer\n\n   * I arbitrarily choose a lower priority for downstream operators so that lazy\n     pull-based computations need not evaluate upstream stages unless absolutely\n     necessary.\n-}\ninfixl 3 //>\ninfixr 3 <\\\\      -- GHC will raise a parse error if either of these lines ends\ninfixr 4 />/, >\\\\ -- with '\\', which is why this comment is here\ninfixl 4 \\<\\, //<\ninfixl 5 \\>\\      -- Same thing here\ninfixr 5 /</\ninfixl 6 <<+\ninfixr 6 +>>\ninfixl 7 >+>, >>~\ninfixr 7 <+<, ~<<\ninfixl 8 <~<\ninfixr 8 >~>\n\n{- $categories\n    A 'Control.Category.Category' is a set of components that you can connect\n    with a composition operator, ('Control.Category..'), that has an identity,\n    'Control.Category.id'.  The ('Control.Category..') and 'Control.Category.id'\n    must satisfy the following three 'Control.Category.Category' laws:\n\n@\n\\-\\- Left identity\n'Control.Category.id' 'Control.Category..' f = f\n\n\\-\\- Right identity\nf 'Control.Category..' 'Control.Category.id' = f\n\n\\-\\- Associativity\n(f 'Control.Category..' g) 'Control.Category..' h = f 'Control.Category..' (g 'Control.Category..' h)\n@\n\n    The 'Proxy' type sits at the intersection of five separate categories, four\n    of which are named after their identity:\n\n@\n                     Identity   | Composition |  Point-ful\n                  +-------------+-------------+-------------+\n respond category |   'respond'   |     '/>/'     |     '//>'     |\n request category |   'request'   |     '\\>\\'     |     '>\\\\'     |\n    push category |   'push'      |     '>~>'     |     '>>~'     |\n    pull category |   'pull'      |     '>+>'     |     '+>>'     |\n Kleisli category |   'return'    |     'Control.Monad.>=>'     |     '>>='     |\n                  +-------------+-------------+-------------+\n@\n\n    Each composition operator has a \\\"point-ful\\\" version, analogous to how\n    ('>>=') is the point-ful version of ('Control.Monad.>=>').  For example,\n    ('//>') is the point-ful version of ('/>/').  The convention is that the\n    odd character out faces the argument that is a function.\n-}\n\n{- $respond\n    The 'respond' category closely corresponds to the generator design pattern.\n\n    The 'respond' category obeys the category laws, where 'respond' is the\n    identity and ('/>/') is composition:\n\n@\n\\-\\- Left identity\n'respond' '/>/' f = f\n\n\\-\\- Right identity\nf '/>/' 'respond' = f\n\n\\-\\- Associativity\n(f '/>/' g) '/>/' h = f '/>/' (g '/>/' h)\n@\n\n#respond-diagram#\n\n    The following diagrams show the flow of information:\n\n@\n'respond' :: 'Functor' m\n       =>  a -> 'Proxy' x' x a' a m a'\n\n\\          a\n          |\n     +----|----+\n     |    |    |\n x' <==   \\\\ /==== a'\n     |     X   |\n x  ==>   / \\\\===> a\n     |    |    |\n     +----|----+\n          v\n          a'\n\n('/>/') :: 'Functor' m\n      => (a -> 'Proxy' x' x b' b m a')\n      -> (b -> 'Proxy' x' x c' c m b')\n      -> (a -> 'Proxy' x' x c' c m a')\n\n\\          a                   /===> b                      a\n          |                  /      |                      |\n     +----|----+            /  +----|----+            +----|----+\n     |    v    |           /   |    v    |            |    v    |\n x' <==       <== b' <==\\\\ / x'<==       <== c'    x' <==       <== c'\n     |    f    |         X     |    g    |     =      | f '/>/' g |\n x  ==>       ==> b  ===/ \\\\ x ==>       ==> c     x  ==>       ==> c\n     |    |    |           \\\\   |    |    |            |    |    |\n     +----|----+            \\\\  +----|----+            +----|----+\n          v                  \\\\      v                      v\n          a'                  \\\\==== b'                     a'\n\n('//>') :: 'Functor' m\n      => 'Proxy' x' x b' b m a'\n      -> (b -> 'Proxy' x' x c' c m b')\n      -> 'Proxy' x' x c' c m a'\n\n\\                              /===> b\n                             /      |\n     +---------+            /  +----|----+            +---------+\n     |         |           /   |    v    |            |         |\n x' <==       <== b' <==\\\\ / x'<==       <== c'    x' <==       <== c'\n     |    f    |         X     |    g    |     =      | f '//>' g |\n x  ==>       ==> b  ===/ \\\\ x ==>       ==> c     x  ==>       ==> c'\n     |    |    |           \\\\   |    |    |            |    |    |\n     +----|----+            \\\\  +----|----+            +----|----+\n          v                  \\\\      v                      v\n          a'                  \\\\==== b'                     a'\n@\n\n-}\n\n{-| Send a value of type @a@ downstream and block waiting for a reply of type\n    @a'@\n\n    'respond' is the identity of the respond category.\n-}\nrespond :: Functor m => a -> Proxy x' x a' a m a'\nrespond a = Respond a Pure\n{-# INLINABLE [1] respond #-}\n\n{-| Compose two unfolds, creating a new unfold\n\n@\n(f '/>/' g) x = f x '//>' g\n@\n\n    ('/>/') is the composition operator of the respond category.\n-}\n(/>/)\n    :: Functor m\n    => (a -> Proxy x' x b' b m a')\n    -- ^\n    -> (b -> Proxy x' x c' c m b')\n    -- ^\n    -> (a -> Proxy x' x c' c m a')\n    -- ^\n(fa />/ fb) a = fa a //> fb\n{-# INLINABLE (/>/) #-}\n\n{-| @(p \\/\\/> f)@ replaces each 'respond' in @p@ with @f@.\n\n    Point-ful version of ('/>/')\n-}\n(//>)\n    :: Functor m\n    =>       Proxy x' x b' b m a'\n    -- ^\n    -> (b -> Proxy x' x c' c m b')\n    -- ^\n    ->       Proxy x' x c' c m a'\n    -- ^\np0 //> fb = go p0\n  where\n    go p = case p of\n        Request x' fx  -> Request x' (\\x -> go (fx x))\n        Respond b  fb' -> fb b >>= \\b' -> go (fb' b')\n        M          m   -> M (go <$> m)\n        Pure       a   -> Pure a\n{-# INLINE [1] (//>) #-}\n\n{-# RULES\n    \"(Request x' fx ) //> fb\" forall x' fx  fb .\n        (Request x' fx ) //> fb = Request x' (\\x -> fx x //> fb);\n    \"(Respond b  fb') //> fb\" forall b  fb' fb .\n        (Respond b  fb') //> fb = fb b >>= \\b' -> fb' b' //> fb;\n    \"(M          m  ) //> fb\" forall    m   fb .\n        (M          m  ) //> fb = M ((\\p' -> p' //> fb) <$> m);\n    \"(Pure      a   ) //> fb\" forall a      fb .\n        (Pure    a     ) //> fb = Pure a;\n  #-}\n\n{- $request\n    The 'request' category closely corresponds to the iteratee design pattern.\n\n    The 'request' category obeys the category laws, where 'request' is the\n    identity and ('\\>\\') is composition:\n\n@\n-- Left identity\n'request' '\\>\\' f = f\n\n\\-\\- Right identity\nf '\\>\\' 'request' = f\n\n\\-\\- Associativity\n(f '\\>\\' g) '\\>\\' h = f '\\>\\' (g '\\>\\' h)\n@\n\n#request-diagram#\n\n    The following diagrams show the flow of information:\n\n@\n'request' :: 'Functor' m\n        =>  a' -> 'Proxy' a' a y' y m a\n\n\\          a'\n          |\n     +----|----+\n     |    |    |\n a' <=====/   <== y'\n     |         |\n a  ======\\\\   ==> y\n     |    |    |\n     +----|----+\n          v\n          a\n\n('\\>\\') :: 'Functor' m\n      => (b' -> 'Proxy' a' a y' y m b)\n      -> (c' -> 'Proxy' b' b y' y m c)\n      -> (c' -> 'Proxy' a' a y' y m c)\n\n\\          b'<=====\\\\                c'                     c'\n          |        \\\\               |                      |\n     +----|----+    \\\\         +----|----+            +----|----+\n     |    v    |     \\\\        |    v    |            |    v    |\n a' <==       <== y'  \\\\== b' <==       <== y'    a' <==       <== y'\n     |    f    |              |    g    |     =      | f '\\>\\' g |\n a  ==>       ==> y   /=> b  ==>       ==> y     a  ==>       ==> y\n     |    |    |     /        |    |    |            |    |    |\n     +----|----+    /         +----|----+            +----|----+\n          v        /               v                      v\n          b ======/                c                      c\n\n('>\\\\') :: Functor m\n      => (b' -> Proxy a' a y' y m b)\n      -> Proxy b' b y' y m c\n      -> Proxy a' a y' y m c\n\n\\          b'<=====\\\\\n          |        \\\\\n     +----|----+    \\\\         +---------+            +---------+\n     |    v    |     \\\\        |         |            |         |\n a' <==       <== y'  \\\\== b' <==       <== y'    a' <==       <== y'\n     |    f    |              |    g    |     =      | f '>\\\\' g |\n a  ==>       ==> y   /=> b  ==>       ==> y     a  ==>       ==> y\n     |    |    |     /        |    |    |            |    |    |\n     +----|----+    /         +----|----+            +----|----+\n          v        /               v                      v\n          b ======/                c                      c\n@\n-}\n\n{-| Send a value of type @a'@ upstream and block waiting for a reply of type @a@\n\n    'request' is the identity of the request category.\n-}\nrequest :: Functor m => a' -> Proxy a' a y' y m a\nrequest a' = Request a' Pure\n{-# INLINABLE [1] request #-}\n\n{-| Compose two folds, creating a new fold\n\n@\n(f '\\>\\' g) x = f '>\\\\' g x\n@\n\n    ('\\>\\') is the composition operator of the request category.\n-}\n(\\>\\)\n    :: Functor m\n    => (b' -> Proxy a' a y' y m b)\n    -- ^\n    -> (c' -> Proxy b' b y' y m c)\n    -- ^\n    -> (c' -> Proxy a' a y' y m c)\n    -- ^\n(fb' \\>\\ fc') c' = fb' >\\\\ fc' c'\n{-# INLINABLE (\\>\\) #-}\n\n{-| @(f >\\\\\\\\ p)@ replaces each 'request' in @p@ with @f@.\n\n    Point-ful version of ('\\>\\')\n-}\n(>\\\\)\n    :: Functor m\n    => (b' -> Proxy a' a y' y m b)\n    -- ^\n    ->        Proxy b' b y' y m c\n    -- ^\n    ->        Proxy a' a y' y m c\n    -- ^\nfb' >\\\\ p0 = go p0\n  where\n    go p = case p of\n        Request b' fb  -> fb' b' >>= \\b -> go (fb b)\n        Respond x  fx' -> Respond x (\\x' -> go (fx' x'))\n        M          m   -> M (go <$> m)\n        Pure       a   -> Pure a\n{-# INLINE [1] (>\\\\) #-}\n\n{-# RULES\n    \"fb' >\\\\ (Request b' fb )\" forall fb' b' fb  .\n        fb' >\\\\ (Request b' fb ) = fb' b' >>= \\b -> fb' >\\\\ fb  b;\n    \"fb' >\\\\ (Respond x  fx')\" forall fb' x  fx' .\n        fb' >\\\\ (Respond x  fx') = Respond x (\\x' -> fb' >\\\\ fx' x');\n    \"fb' >\\\\ (M          m  )\" forall fb'    m   .\n        fb' >\\\\ (M          m  ) = M ((\\p' -> fb' >\\\\ p') <$> m);\n    \"fb' >\\\\ (Pure    a    )\" forall fb' a      .\n        fb' >\\\\ (Pure    a     ) = Pure a;\n  #-}\n\n{- $push\n    The 'push' category closely corresponds to push-based Unix pipes.\n\n    The 'push' category obeys the category laws, where 'push' is the identity\n    and ('>~>') is composition:\n\n@\n\\-\\- Left identity\n'push' '>~>' f = f\n\n\\-\\- Right identity\nf '>~>' 'push' = f\n\n\\-\\- Associativity\n(f '>~>' g) '>~>' h = f '>~>' (g '>~>' h)\n@\n\n    The following diagram shows the flow of information:\n\n@\n'push'  :: 'Functor' m\n      =>  a -> 'Proxy' a' a a' a m r\n\n\\          a\n          |\n     +----|----+\n     |    v    |\n a' <============ a'\n     |         |\n a  ============> a\n     |    |    |\n     +----|----+\n          v\n          r\n\n('>~>') :: 'Functor' m\n      => (a -> 'Proxy' a' a b' b m r)\n      -> (b -> 'Proxy' b' b c' c m r)\n      -> (a -> 'Proxy' a' a c' c m r)\n\n\\          a                b                      a\n          |                |                      |\n     +----|----+      +----|----+            +----|----+\n     |    v    |      |    v    |            |    v    |\n a' <==       <== b' <==       <== c'    a' <==       <== c'\n     |    f    |      |    g    |     =      | f '>~>' g |\n a  ==>       ==> b  ==>       ==> c     a  ==>       ==> c\n     |    |    |      |    |    |            |    |    |\n     +----|----+      +----|----+            +----|----+\n          v                v                      v\n          r                r                      r\n@\n\n-}\n\n{-| Forward responses followed by requests\n\n@\n'push' = 'respond' 'Control.Monad.>=>' 'request' 'Control.Monad.>=>' 'push'\n@\n\n    'push' is the identity of the push category.\n-}\npush :: Functor m => a -> Proxy a' a a' a m r\npush = go\n  where\n    go a = Respond a (\\a' -> Request a' go)\n{-# INLINABLE [1] push #-}\n\n{-| Compose two proxies blocked while 'request'ing data, creating a new proxy\n    blocked while 'request'ing data\n\n@\n(f '>~>' g) x = f x '>>~' g\n@\n\n    ('>~>') is the composition operator of the push category.\n-}\n(>~>)\n    :: Functor m\n    => (_a -> Proxy a' a b' b m r)\n    -- ^\n    -> ( b -> Proxy b' b c' c m r)\n    -- ^\n    -> (_a -> Proxy a' a c' c m r)\n    -- ^\n(fa >~> fb) a = fa a >>~ fb\n{-# INLINABLE (>~>) #-}\n\n{-| @(p >>~ f)@ pairs each 'respond' in @p@ with a 'request' in @f@.\n\n    Point-ful version of ('>~>')\n-}\n(>>~)\n    :: Functor m\n    =>       Proxy a' a b' b m r\n    -- ^\n    -> (b -> Proxy b' b c' c m r)\n    -- ^\n    ->       Proxy a' a c' c m r\n    -- ^\np >>~ fb = case p of\n    Request a' fa  -> Request a' (\\a -> fa a >>~ fb)\n    Respond b  fb' -> fb' +>> fb b\n    M          m   -> M ((\\p' -> p' >>~ fb) <$> m)\n    Pure       r   -> Pure r\n{-# INLINE [1] (>>~) #-}\n\n{- $pull\n    The 'pull' category closely corresponds to pull-based Unix pipes.\n\n    The 'pull' category obeys the category laws, where 'pull' is the identity\n    and ('>+>') is composition:\n\n@\n\\-\\- Left identity\n'pull' '>+>' f = f\n\n\\-\\- Right identity\nf '>+>' 'pull' = f\n\n\\-\\- Associativity\n(f '>+>' g) '>+>' h = f '>+>' (g '>+>' h)\n@\n\n#pull-diagram#\n\n    The following diagrams show the flow of information:\n\n@\n'pull'  :: 'Functor' m\n      =>  a' -> 'Proxy' a' a a' a m r\n\n\\          a'\n          |\n     +----|----+\n     |    v    |\n a' <============ a'\n     |         |\n a  ============> a\n     |    |    |\n     +----|----+\n          v\n          r\n\n('>+>') :: 'Functor' m\n      -> (b' -> 'Proxy' a' a b' b m r)\n      -> (c' -> 'Proxy' b' b c' c m r)\n      -> (c' -> 'Proxy' a' a c' c m r)\n\n\\          b'               c'                     c'\n          |                |                      |\n     +----|----+      +----|----+            +----|----+\n     |    v    |      |    v    |            |    v    |\n a' <==       <== b' <==       <== c'    a' <==       <== c'\n     |    f    |      |    g    |     =      | f >+> g |\n a  ==>       ==> b  ==>       ==> c     a  ==>       ==> c\n     |    |    |      |    |    |            |    |    |\n     +----|----+      +----|----+            +----|----+\n          v                v                      v\n          r                r                      r\n@\n\n-}\n\n{-| Forward requests followed by responses:\n\n@\n'pull' = 'request' 'Control.Monad.>=>' 'respond' 'Control.Monad.>=>' 'pull'\n@\n\n    'pull' is the identity of the pull category.\n-}\npull :: Functor m => a' -> Proxy a' a a' a m r\npull = go\n  where\n    go a' = Request a' (\\a -> Respond a go)\n{-# INLINABLE [1] pull #-}\n\n{-| Compose two proxies blocked in the middle of 'respond'ing, creating a new\n    proxy blocked in the middle of 'respond'ing\n\n@\n(f '>+>' g) x = f '+>>' g x\n@\n\n    ('>+>') is the composition operator of the pull category.\n-}\n(>+>)\n    :: Functor m\n    => ( b' -> Proxy a' a b' b m r)\n    -- ^\n    -> (_c' -> Proxy b' b c' c m r)\n    -- ^\n    -> (_c' -> Proxy a' a c' c m r)\n    -- ^\n(fb' >+> fc') c' = fb' +>> fc' c'\n{-# INLINABLE (>+>) #-}\n\n{-| @(f +>> p)@ pairs each 'request' in @p@ with a 'respond' in @f@.\n\n    Point-ful version of ('>+>')\n-}\n(+>>)\n    :: Functor m\n    => (b' -> Proxy a' a b' b m r)\n    -- ^\n    ->        Proxy b' b c' c m r\n    -- ^\n    ->        Proxy a' a c' c m r\n    -- ^\nfb' +>> p = case p of\n    Request b' fb  -> fb' b' >>~ fb\n    Respond c  fc' -> Respond c (\\c' -> fb' +>> fc' c')\n    M          m   -> M ((\\p' -> fb' +>> p') <$> m)\n    Pure       r   -> Pure r\n{-# INLINABLE [1] (+>>) #-}\n\n{- $reflect\n    @(reflect .)@ transforms each streaming category into its dual:\n\n    * The request category is the dual of the respond category\n\n@\n'reflect' '.' 'respond' = 'request'\n\n'reflect' '.' (f '/>/' g) = 'reflect' '.' f '/</' 'reflect' '.' g\n@\n\n@\n'reflect' '.' 'request' = 'respond'\n\n'reflect' '.' (f '\\>\\' g) = 'reflect' '.' f '\\<\\' 'reflect' '.' g\n@\n\n    * The pull category is the dual of the push category\n\n@\n'reflect' '.' 'push' = 'pull'\n\n'reflect' '.' (f '>~>' g) = 'reflect' '.' f '<+<' 'reflect' '.' g\n@\n\n@\n'reflect' '.' 'pull' = 'push'\n\n'reflect' '.' (f '>+>' g) = 'reflect' '.' f '<~<' 'reflect' '.' g\n@\n-}\n\n-- | Switch the upstream and downstream ends\nreflect :: Functor m => Proxy a' a b' b m r -> Proxy b b' a a' m r\nreflect = go\n  where\n    go p = case p of\n        Request a' fa  -> Respond a' (\\a  -> go (fa  a ))\n        Respond b  fb' -> Request b  (\\b' -> go (fb' b'))\n        M          m   -> M (go <$> m)\n        Pure    r      -> Pure r\n{-# INLINABLE reflect #-}\n\n{-| An effect in the base monad\n\n    'Effect's neither 'Pipes.await' nor 'Pipes.yield'\n-}\ntype Effect = Proxy X () () X\n\n-- | 'Producer's can only 'Pipes.yield'\ntype Producer b = Proxy X () () b\n\n-- | 'Pipe's can both 'Pipes.await' and 'Pipes.yield'\ntype Pipe a b = Proxy () a () b\n\n-- | 'Consumer's can only 'Pipes.await'\ntype Consumer a = Proxy () a () X\n\n{-| @Client a' a@ sends requests of type @a'@ and receives responses of\n    type @a@.\n\n    'Client's only 'request' and never 'respond'.\n-}\ntype Client a' a = Proxy a' a () X\n\n{-| @Server b' b@ receives requests of type @b'@ and sends responses of type\n    @b@.\n\n    'Server's only 'respond' and never 'request'.\n-}\ntype Server b' b = Proxy X () b' b\n\n-- | Like 'Effect', but with a polymorphic type\ntype Effect' m r = forall x' x y' y . Proxy x' x y' y m r\n\n-- | Like 'Producer', but with a polymorphic type\ntype Producer' b m r = forall x' x . Proxy x' x () b m r\n\n-- | Like 'Consumer', but with a polymorphic type\ntype Consumer' a m r = forall y' y . Proxy () a y' y m r\n\n-- | Like 'Server', but with a polymorphic type\ntype Server' b' b m r = forall x' x . Proxy x' x b' b m r\n\n-- | Like 'Client', but with a polymorphic type\ntype Client' a' a m r = forall y' y . Proxy a' a y' y m r\n\n-- | Equivalent to ('/>/') with the arguments flipped\n(\\<\\)\n    :: Functor m\n    => (b -> Proxy x' x c' c m b')\n    -- ^\n    -> (a -> Proxy x' x b' b m a')\n    -- ^\n    -> (a -> Proxy x' x c' c m a')\n    -- ^\np1 \\<\\ p2 = p2 />/ p1\n{-# INLINABLE (\\<\\) #-}\n\n-- | Equivalent to ('\\>\\') with the arguments flipped\n(/</)\n    :: Functor m\n    => (c' -> Proxy b' b x' x m c)\n    -- ^\n    -> (b' -> Proxy a' a x' x m b)\n    -- ^\n    -> (c' -> Proxy a' a x' x m c)\n    -- ^\np1 /</ p2 = p2 \\>\\ p1\n{-# INLINABLE (/</) #-}\n\n-- | Equivalent to ('>~>') with the arguments flipped\n(<~<)\n    :: Functor m\n    => (b -> Proxy b' b c' c m r)\n    -- ^\n    -> (a -> Proxy a' a b' b m r)\n    -- ^\n    -> (a -> Proxy a' a c' c m r)\n    -- ^\np1 <~< p2 = p2 >~> p1\n{-# INLINABLE (<~<) #-}\n\n-- | Equivalent to ('>+>') with the arguments flipped\n(<+<)\n    :: Functor m\n    => (c' -> Proxy b' b c' c m r)\n    -- ^\n    -> (b' -> Proxy a' a b' b m r)\n    -- ^\n    -> (c' -> Proxy a' a c' c m r)\n    -- ^\np1 <+< p2 = p2 >+> p1\n{-# INLINABLE (<+<) #-}\n\n-- | Equivalent to ('//>') with the arguments flipped\n(<\\\\)\n    :: Functor m\n    => (b -> Proxy x' x c' c m b')\n    -- ^\n    ->       Proxy x' x b' b m a'\n    -- ^\n    ->       Proxy x' x c' c m a'\n    -- ^\nf <\\\\ p = p //> f\n{-# INLINABLE (<\\\\) #-}\n\n-- | Equivalent to ('>\\\\') with the arguments flipped\n(//<)\n    :: Functor m\n    =>        Proxy b' b y' y m c\n    -- ^\n    -> (b' -> Proxy a' a y' y m b)\n    -- ^\n    ->        Proxy a' a y' y m c\n    -- ^\np //< f = f >\\\\ p\n{-# INLINABLE (//<) #-}\n\n-- | Equivalent to ('>>~') with the arguments flipped\n(~<<)\n    :: Functor m\n    => (b  -> Proxy b' b c' c m r)\n    -- ^\n    ->        Proxy a' a b' b m r\n    -- ^\n    ->        Proxy a' a c' c m r\n    -- ^\nk ~<< p = p >>~ k\n{-# INLINABLE (~<<) #-}\n\n-- | Equivalent to ('+>>') with the arguments flipped\n(<<+)\n    :: Functor m\n    =>         Proxy b' b c' c m r\n    -- ^\n    -> (b'  -> Proxy a' a b' b m r)\n    -- ^\n    ->         Proxy a' a c' c m r\n    -- ^\nk <<+ p = p +>> k\n{-# INLINABLE (<<+) #-}\n\n{-# RULES\n    \"(p //> f) //> g\" forall p f g . (p //> f) //> g = p //> (\\x -> f x //> g)\n\n  ; \"p //> respond\" forall p . p //> respond = p\n\n  ; \"respond x //> f\" forall x f . respond x //>  f = f x\n\n  ; \"f >\\\\ (g >\\\\ p)\" forall f g p . f >\\\\ (g >\\\\ p) = (\\x -> f >\\\\ g x) >\\\\ p\n\n  ; \"request >\\\\ p\" forall p . request >\\\\ p = p\n\n  ; \"f >\\\\ request x\" forall f x . f >\\\\ request x = f x\n\n  ; \"(p >>~ f) >>~ g\" forall p f g . (p >>~ f) >>~ g = p >>~ (\\x -> f x >>~ g)\n\n  ; \"p >>~ push\" forall p . p >>~ push = p\n\n  ; \"push x >>~ f\" forall x f . push x >>~ f = f x\n\n  ; \"f +>> (g +>> p)\" forall f g p . f +>> (g +>> p) = (\\x -> f +>> g x) +>> p\n\n  ; \"pull +>> p\" forall p . pull +>> p = p\n\n  ; \"f +>> pull x\" forall f x . f +>> pull x = f x\n\n  #-}\n"
  },
  {
    "path": "src/Pipes/Internal.hs",
    "content": "{-| This is an internal module, meaning that it is unsafe to import unless you\n    understand the risks.\n\n    This module provides a fast implementation by weakening the monad\n    transformer laws.  These laws do not hold if you can pattern match on the\n    constructors, as the following counter-example illustrates:\n\n@\n'lift' '.' 'return' = 'M' '.' 'return' '.' 'Pure'\n\n'return' = 'Pure'\n\n'lift' '.' 'return' /= 'return'\n@\n\n    You do not need to worry about this if you do not import this module, since\n    the other modules in this library do not export the constructors or export\n    any functions which can violate the monad transformer laws.\n-}\n\n{-# LANGUAGE CPP                   #-}\n{-# LANGUAGE FlexibleInstances     #-}\n{-# LANGUAGE MultiParamTypeClasses #-}\n{-# LANGUAGE RankNTypes            #-}\n{-# LANGUAGE UndecidableInstances  #-}\n{-# LANGUAGE Trustworthy           #-}\n\nmodule Pipes.Internal (\n    -- * Internal\n      Proxy(..)\n    , unsafeHoist\n    , observe\n    , X\n    , closed\n    ) where\n\nimport qualified Control.Monad.Fail as F (MonadFail(fail))\nimport Control.Monad.IO.Class (MonadIO(liftIO))\nimport Control.Monad.Trans.Class (MonadTrans(lift))\nimport Control.Monad.Morph (MFunctor(hoist), MMonad(embed))\nimport Control.Monad.Except (MonadError(..))\nimport Control.Monad.Catch (MonadThrow(..), MonadCatch(..))\nimport Control.Monad.Reader (MonadReader(..))\nimport Control.Monad.State (MonadState(..))\nimport Control.Monad.Writer (MonadWriter(..), censor)\nimport Data.Void (Void)\n\n#if MIN_VERSION_base(4,8,0)\nimport Control.Applicative (Alternative(..))\n#else\nimport Control.Applicative\n#endif\nimport Data.Semigroup\n\nimport qualified Data.Void\n\n{-| A 'Proxy' is a monad transformer that receives and sends information on both\n    an upstream and downstream interface.\n\n    The type variables signify:\n\n    * @a'@ and @a@ - The upstream interface, where @(a')@s go out and @(a)@s\n      come in\n\n    * @b'@ and @b@ - The downstream interface, where @(b)@s go out and @(b')@s\n      come in\n\n    * @m @ - The base monad\n\n    * @r @ - The return value\n-}\ndata Proxy a' a b' b m r\n    = Request a' (a  -> Proxy a' a b' b m r )\n    | Respond b  (b' -> Proxy a' a b' b m r )\n    | M          (m    (Proxy a' a b' b m r))\n    | Pure    r\n\ninstance Functor m => Functor (Proxy a' a b' b m) where\n    fmap f p0 = go p0 where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> M (go <$> m)\n            Pure    r      -> Pure (f r)\n\ninstance Functor m => Applicative (Proxy a' a b' b m) where\n    pure      = Pure\n    pf <*> px = go pf where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> M (go <$> m)\n            Pure    f      -> fmap f px\n    l *> r = go l where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> M (go <$> m)\n            Pure    _      -> r\n\ninstance Functor m => Monad (Proxy a' a b' b m) where\n    return = pure\n    (>>=)  = _bind\n\n_bind\n    :: Functor m\n    => Proxy a' a b' b m r\n    -> (r -> Proxy a' a b' b m r')\n    -> Proxy a' a b' b m r'\np0 `_bind` f = go p0 where\n    go p = case p of\n        Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n        Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n        M          m   -> M (go <$> m)\n        Pure    r      -> f r\n{-# NOINLINE[1] _bind #-}\n\n{-# RULES\n    \"_bind (Request a' k) f\" forall a' k f .\n        _bind (Request a' k) f = Request a' (\\a  -> _bind (k a)  f);\n    \"_bind (Respond b  k) f\" forall b  k f .\n        _bind (Respond b  k) f = Respond b  (\\b' -> _bind (k b') f);\n    \"_bind (M          m) f\" forall m    f .\n        _bind (M          m) f = M ((\\p -> _bind p f) <$> m);\n    \"_bind (Pure    r   ) f\" forall r    f .\n        _bind (Pure    r   ) f = f r;\n  #-}\n\ninstance (Functor m, Semigroup r) => Semigroup (Proxy a' a b' b m r) where\n    p1 <> p2 = go p1 where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> M (go <$> m)\n            Pure    r1     -> fmap (r1 <>) p2\n\ninstance (Functor m, Monoid r, Semigroup r) => Monoid (Proxy a' a b' b m r) where\n    mempty        = Pure mempty\n#if !(MIN_VERSION_base(4,11,0))\n    mappend = (<>)\n#endif\n\ninstance MonadTrans (Proxy a' a b' b) where\n    lift m = M (Pure <$> m)\n\n{-| 'unsafeHoist' is like 'hoist', but faster.\n\n    This is labeled as unsafe because you will break the monad transformer laws\n    if you do not pass a monad morphism as the first argument.  This function is\n    safe if you pass a monad morphism as the first argument.\n-}\nunsafeHoist\n    :: Functor m\n    => (forall x . m x -> n x) -> Proxy a' a b' b m r -> Proxy a' a b' b n r\nunsafeHoist nat = go\n  where\n    go p = case p of\n        Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n        Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n        M          m   -> M (nat (go <$> m))\n        Pure    r      -> Pure r\n{-# INLINABLE unsafeHoist #-}\n\ninstance MFunctor (Proxy a' a b' b) where\n    hoist nat p0 = go (observe p0)\n      where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> M (nat (go <$> m))\n            Pure    r      -> Pure r\n\ninstance MMonad (Proxy a' a b' b) where\n    embed f = go\n      where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            M          m   -> f m >>= go\n            Pure    r      -> Pure r\n\ninstance F.MonadFail m => F.MonadFail (Proxy a' a b' b m) where\n    fail = lift . F.fail\n\ninstance MonadIO m => MonadIO (Proxy a' a b' b m) where\n    liftIO m = M (liftIO (Pure <$> m))\n\ninstance MonadReader r m => MonadReader r (Proxy a' a b' b m) where\n    ask = lift ask\n    local f = go\n        where\n          go p = case p of\n              Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n              Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n              Pure    r      -> Pure r\n              M       m      -> M (go <$> local f m)\n    reader = lift . reader\n\ninstance MonadState s m => MonadState s (Proxy a' a b' b m) where\n    get = lift get\n    put = lift . put\n    state = lift . state\n\ninstance MonadWriter w m => MonadWriter w (Proxy a' a b' b m) where\n    writer = lift . writer\n    tell = lift . tell\n    listen p0 = go p0 mempty\n      where\n        go p w = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ) w)\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b') w)\n            M       m      -> M (do\n                (p', w') <- listen m\n                return (go p' $! mappend w w') )\n            Pure    r      -> Pure (r, w)\n\n    pass p0 = go p0 mempty\n      where\n        go p w = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ) w)\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b') w)\n            M       m      -> M (do\n                (p', w') <- censor (const mempty) (listen m)\n                return (go p' $! mappend w w') )\n            Pure   (r, f)  -> M (pass (return (Pure r, \\_ -> f w)))\n\ninstance MonadError e m => MonadError e (Proxy a' a b' b m) where\n    throwError = lift . throwError\n    catchError p0 f = go p0\n      where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            Pure    r      -> Pure r\n            M          m   -> M ((do\n                p' <- m\n                return (go p') ) `catchError` (\\e -> return (f e)) )\n\ninstance MonadThrow m => MonadThrow (Proxy a' a b' b m) where\n    throwM = lift . throwM\n    {-# INLINE throwM #-}\n\ninstance MonadCatch m => MonadCatch (Proxy a' a b' b m) where\n    catch p0 f = go p0\n      where\n        go p = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n            Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n            Pure    r      -> Pure r\n            M          m   -> M ((do\n                p' <- m\n                return (go p') ) `Control.Monad.Catch.catch` (\\e -> return (f e)) )\n\n{-| The monad transformer laws are correct when viewed through the 'observe'\n    function:\n\n@\n'observe' ('lift' ('return' r)) = 'observe' ('return' r)\n\n'observe' ('lift' (m '>>=' f)) = 'observe' ('lift' m '>>=' 'lift' '.' f)\n@\n\n    This correctness comes at a small cost to performance, so use this function\n    sparingly.\n\n    This function is a convenience for low-level @pipes@ implementers.  You do\n    not need to use 'observe' if you stick to the safe API.\n-}\nobserve :: Monad m => Proxy a' a b' b m r -> Proxy a' a b' b m r\nobserve p0 = M (go p0) where\n    go p = case p of\n        Request a' fa  -> return (Request a' (\\a  -> observe (fa  a )))\n        Respond b  fb' -> return (Respond b  (\\b' -> observe (fb' b')))\n        M          m'  -> m' >>= go\n        Pure    r      -> return (Pure r)\n{-# INLINABLE observe #-}\n\n-- | The empty type, used to close output ends\ntype X = Void\n\n-- | Use 'closed' to \\\"handle\\\" impossible outputs\nclosed :: X -> a\nclosed = Data.Void.absurd\n{-# INLINABLE closed #-}\n"
  },
  {
    "path": "src/Pipes/Lift.hs",
    "content": "{-# LANGUAGE CPP #-}\n\n{-| Many actions in base monad transformers cannot be automatically\n    'Control.Monad.Trans.Class.lift'ed.  These functions lift these remaining\n    actions so that they work in the 'Proxy' monad transformer.\n\n    See the mini-tutorial at the bottom of this module for example code and\n    typical use cases where this module will come in handy.\n-}\n\nmodule Pipes.Lift (\n    -- * Utilities\n      distribute\n\n    -- * ExceptT\n    , exceptP\n    , runExceptP\n    , catchError\n    , liftCatchError\n\n    -- * MaybeT\n    , maybeP\n    , runMaybeP\n\n    -- * ReaderT\n    , readerP\n    , runReaderP\n\n    -- * StateT\n    , stateP\n    , runStateP\n    , evalStateP\n    , execStateP\n\n    -- * WriterT\n    -- $writert\n    , writerP\n    , runWriterP\n    , execWriterP\n\n    -- * RWST\n    , rwsP\n    , runRWSP\n    , evalRWSP\n    , execRWSP\n\n    -- * Tutorial\n    -- $tutorial\n    ) where\n\nimport Control.Monad.Trans.Class (lift, MonadTrans(..))\nimport qualified Control.Monad.Trans.Except as E\nimport qualified Control.Monad.Trans.Maybe as M\nimport qualified Control.Monad.Trans.Reader as R\nimport qualified Control.Monad.Trans.State.Strict as S\nimport qualified Control.Monad.Trans.Writer.Strict as W\nimport qualified Control.Monad.Trans.RWS.Strict as RWS\nimport Pipes.Internal (Proxy(..), unsafeHoist)\nimport Control.Monad.Morph (hoist, MFunctor(..))\nimport Pipes.Core (runEffect, request, respond, (//>), (>\\\\))\n\n#if MIN_VERSION_base(4,8,0)\n#else\nimport Data.Monoid\n#endif\n\n-- | Distribute 'Proxy' over a monad transformer\ndistribute\n    ::  ( Monad m\n        , MonadTrans t\n        , MFunctor t\n        , Monad (t m)\n        , Monad (t (Proxy a' a b' b m))\n        )\n    => Proxy a' a b' b (t m) r\n    -- ^ \n    -> t (Proxy a' a b' b m) r\n    -- ^ \ndistribute p =  runEffect $ request' >\\\\ unsafeHoist (hoist lift) p //> respond'\n  where\n    request' = lift . lift . request\n    respond' = lift . lift . respond\n{-# INLINABLE distribute #-}\n\n-- | Wrap the base monad in 'E.ExceptT'\nexceptP\n    :: Monad m\n    => Proxy a' a b' b m (Either e r)\n    -> Proxy a' a b' b (E.ExceptT e m) r\nexceptP p = do\n    x <- unsafeHoist lift p\n    lift $ E.ExceptT (return x)\n{-# INLINABLE exceptP #-}\n\n-- | Run 'E.ExceptT' in the base monad\nrunExceptP\n    :: Monad m\n    => Proxy a' a b' b (E.ExceptT e m) r\n    -> Proxy a' a b' b m (Either e r)\nrunExceptP    = E.runExceptT . distribute\n{-# INLINABLE runExceptP #-}\n\n-- | Catch an error in the base monad\ncatchError\n    :: Monad m\n    => Proxy a' a b' b (E.ExceptT e m) r\n    -- ^\n    -> (e -> Proxy a' a b' b (E.ExceptT e m) r)\n    -- ^\n    -> Proxy a' a b' b (E.ExceptT e m) r\ncatchError e h = exceptP . E.runExceptT $ \n    E.catchE (distribute e) (distribute . h)\n{-# INLINABLE catchError #-}\n\n-- | Catch an error using a catch function for the base monad\nliftCatchError\n    :: Monad m\n    => (   m (Proxy a' a b' b m r)\n        -> (e -> m (Proxy a' a b' b m r))\n        -> m (Proxy a' a b' b m r) )\n    -- ^\n    ->    (Proxy a' a b' b m r\n        -> (e -> Proxy a' a b' b m r)\n        -> Proxy a' a b' b m r)\n    -- ^\nliftCatchError c p0 f = go p0\n  where\n    go p = case p of\n        Request a' fa  -> Request a' (\\a  -> go (fa  a ))\n        Respond b  fb' -> Respond b  (\\b' -> go (fb' b'))\n        Pure    r      -> Pure r\n        M          m   -> M ((do\n            p' <- m\n            return (go p') ) `c` (\\e -> return (f e)) )\n{-# INLINABLE liftCatchError #-}\n\n-- | Wrap the base monad in 'M.MaybeT'\nmaybeP\n    :: Monad m\n    => Proxy a' a b' b m (Maybe r) -> Proxy a' a b' b (M.MaybeT m) r\nmaybeP p = do\n    x <- unsafeHoist lift p\n    lift $ M.MaybeT (return x)\n{-# INLINABLE maybeP #-}\n\n-- | Run 'M.MaybeT' in the base monad\nrunMaybeP\n    :: Monad m\n    => Proxy a' a b' b (M.MaybeT m) r\n    -> Proxy a' a b' b m (Maybe r)\nrunMaybeP p = M.runMaybeT $ distribute p\n{-# INLINABLE runMaybeP #-}\n\n-- | Wrap the base monad in 'R.ReaderT'\nreaderP\n    :: Monad m\n    => (i -> Proxy a' a b' b m r) -> Proxy a' a b' b (R.ReaderT i m) r\nreaderP k = do\n    i <- lift R.ask\n    unsafeHoist lift (k i)\n{-# INLINABLE readerP #-}\n\n-- | Run 'R.ReaderT' in the base monad\nrunReaderP\n    :: Monad m\n    => i\n    -> Proxy a' a b' b (R.ReaderT i m) r\n    -> Proxy a' a b' b m r\nrunReaderP r p = (`R.runReaderT` r) $ distribute p\n{-# INLINABLE runReaderP #-}\n\n-- | Wrap the base monad in 'S.StateT'\nstateP\n    :: Monad m\n    => (s -> Proxy a' a b' b m (r, s)) -> Proxy a' a b' b (S.StateT s m) r\nstateP k = do\n    s <- lift S.get\n    (r, s') <- unsafeHoist lift (k s)\n    lift (S.put s')\n    return r\n{-# INLINABLE stateP #-}\n\n-- | Run 'S.StateT' in the base monad\nrunStateP\n    :: Monad m\n    => s\n    -> Proxy a' a b' b (S.StateT s m) r\n    -> Proxy a' a b' b m (r, s)\nrunStateP s p = (`S.runStateT` s) $ distribute p\n{-# INLINABLE runStateP #-}\n\n-- | Evaluate 'S.StateT' in the base monad\nevalStateP\n    :: Monad m\n    => s\n    -> Proxy a' a b' b (S.StateT s m) r\n    -> Proxy a' a b' b m r\nevalStateP s p = fmap fst $ runStateP s p\n{-# INLINABLE evalStateP #-}\n\n-- | Execute 'S.StateT' in the base monad\nexecStateP\n    :: Monad m\n    => s\n    -> Proxy a' a b' b (S.StateT s m) r\n    -> Proxy a' a b' b m s\nexecStateP s p = fmap snd $ runStateP s p\n{-# INLINABLE execStateP #-}\n\n{- $writert\n    Note that 'runWriterP' and 'execWriterP' will keep the accumulator in\n    weak-head-normal form so that folds run in constant space when possible.\n\n    This means that until @transformers@ adds a truly strict 'W.WriterT', you\n    should consider unwrapping 'W.WriterT' first using 'runWriterP' or\n    'execWriterP' before running your 'Proxy'.  You will get better performance\n    this way and eliminate space leaks if your accumulator doesn't have any lazy\n    fields.\n-}\n\n-- | Wrap the base monad in 'W.WriterT'\nwriterP\n    :: (Monad m, Monoid w)\n    => Proxy a' a b' b m (r, w) -> Proxy a' a b' b (W.WriterT w m) r\nwriterP p = do\n    (r, w) <- unsafeHoist lift p\n    lift $ W.tell w\n    return r\n{-# INLINABLE writerP #-}\n\n-- | Run 'W.WriterT' in the base monad\nrunWriterP\n    :: (Monad m, Monoid w)\n    => Proxy a' a b' b (W.WriterT w m) r\n    -> Proxy a' a b' b m (r, w)\nrunWriterP p = W.runWriterT $ distribute p\n{-# INLINABLE runWriterP #-}\n\n-- | Execute 'W.WriterT' in the base monad\nexecWriterP\n    :: (Monad m, Monoid w)\n    => Proxy a' a b' b (W.WriterT w m) r\n    -> Proxy a' a b' b m w\nexecWriterP p = fmap snd $ runWriterP p\n{-# INLINABLE execWriterP #-}\n\n-- | Wrap the base monad in 'RWS.RWST'\nrwsP\n    :: (Monad m, Monoid w)\n    => (i -> s -> Proxy a' a b' b m (r, s, w))\n    -> Proxy a' a b' b (RWS.RWST i w s m) r\nrwsP k = do\n    i <- lift RWS.ask\n    s <- lift RWS.get\n    (r, s', w) <- unsafeHoist lift (k i s)\n    lift $ do\n        RWS.put s'\n        RWS.tell w\n    return r\n{-# INLINABLE rwsP #-}\n\n-- | Run 'RWS.RWST' in the base monad\nrunRWSP\n    :: (Monad m, Monoid w)\n    => r\n    -> s\n    -> Proxy a' a b' b (RWS.RWST r w s m) d\n    -> Proxy a' a b' b m (d, s, w)\nrunRWSP  i s p = (\\b -> RWS.runRWST b i s) $ distribute p\n{-# INLINABLE runRWSP #-}\n\n-- | Evaluate 'RWS.RWST' in the base monad\nevalRWSP\n    :: (Monad m, Monoid w)\n    => r\n    -> s\n    -> Proxy a' a b' b (RWS.RWST r w s m) d\n    -> Proxy a' a b' b m (d, w)\nevalRWSP i s p = fmap f $ runRWSP i s p\n  where\n    f x = let (r, _, w) = x in (r, w)\n{-# INLINABLE evalRWSP #-}\n\n-- | Execute 'RWS.RWST' in the base monad\nexecRWSP\n    :: (Monad m, Monoid w)\n    => r\n    -> s\n    -> Proxy a' a b' b (RWS.RWST r w s m) d\n    -> Proxy a' a b' b m (s, w)\nexecRWSP i s p = fmap f $ runRWSP i s p\n  where\n    f x = let (_, s', w) = x in (s', w)\n{-# INLINABLE execRWSP #-}\n\n{- $tutorial\n    Probably the most useful functionality in this module is lifted error\n    handling.  Suppose that you have a 'Pipes.Pipe' whose base monad can fail\n    using 'E.ExceptT':\n\n> import Control.Monad.Trans.Error\n> import Pipes\n>\n> example :: Monad m => Pipe Int Int (ExceptT String m) r\n> example = for cat $ \\n ->\n>     if n == 0\n>     then lift $ throwError \"Zero is forbidden\"\n>     else yield n\n\n    Without the tools in this module you cannot recover from any potential error\n    until after you compose and run the pipeline:\n\n>>> import qualified Pipes.Prelude as P\n>>> runExceptT $ runEffect $ P.readLn >-> example >-> P.print\n42<Enter>\n42\n1<Enter>\n1\n0<Enter>\nZero is forbidden\n>>>\n\n    This module provides `catchError`, which lets you catch and recover from\n    errors inside the 'Pipe':\n\n>  import qualified Pipes.Lift as Lift\n> \n>  caught :: Pipe Int Int (ExceptT String IO) r\n>  caught = example `Lift.catchError` \\str -> do\n>      liftIO (putStrLn str)\n>      caught\n\n    This lets you resume streaming in the face of errors raised within the base\n    monad:\n\n>>> runExceptT $ runEffect $ P.readLn >-> caught >-> P.print\n0<Enter>\nZero is forbidden\n42<Enter>\n42\n0<Enter>\nZero is forbidden\n1<Enter>\n1\n...\n\n    Another common use case is running a base monad before running the pipeline.\n    For example, the following contrived 'Producer' uses 'S.StateT' gratuitously\n    to increment numbers:\n\n> import Control.Monad (forever)\n> import Control.Monad.Trans.State.Strict\n> import Pipes\n> \n> numbers :: Monad m => Producer Int (StateT Int m) r\n> numbers = forever $ do\n>     n <- lift get\n>     yield n\n>     lift $ put $! n + 1\n\n    You can run the 'StateT' monad by supplying an initial state, before you\n    ever compose the 'Producer':\n\n> import Pipes.Lift\n>\n> naturals :: Monad m => Producer Int m r\n> naturals = evalStateP 0 numbers\n\n    This deletes 'StateT' from the base monad entirely, give you a completely\n    pure 'Pipes.Producer':\n\n>>> Pipes.Prelude.toList naturals\n[0,1,2,3,4,5,6...]\n\n    Note that the convention for the 'S.StateT' run functions is backwards from\n    @transformers@ for convenience: the initial state is the first argument.\n\n    All of these functions internally use 'distribute', which can pull out most\n    monad transformers from the base monad.  For example, 'evalStateP' is\n    defined in terms of 'distribute':\n\n> evalStateP s p = evalStateT (distribute p) s\n\n    Therefore you can use 'distribute' to run other monad transformers, too, as\n    long as they implement the 'MFunctor' type class from the @mmorph@ library.\n-}\n"
  },
  {
    "path": "src/Pipes/Prelude.hs",
    "content": "{-| General purpose utilities\n\n    The names in this module clash heavily with the Haskell Prelude, so I\n    recommend the following import scheme:\n\n> import Pipes\n> import qualified Pipes.Prelude as P  -- or use any other qualifier you prefer\n\n    Note that 'String'-based 'IO' is inefficient.  The 'String'-based utilities\n    in this module exist only for simple demonstrations without incurring a\n    dependency on the @text@ package.\n\n    Also, 'stdinLn' and 'stdoutLn' remove and add newlines, respectively.  This\n    behavior is intended to simplify examples.  The corresponding @stdin@ and\n    @stdout@ utilities from @pipes-bytestring@ and @pipes-text@ preserve\n    newlines.\n-}\n\n{-# LANGUAGE RankNTypes, Trustworthy #-}\n{-# OPTIONS_GHC -fno-warn-unused-do-bind #-}\n\nmodule Pipes.Prelude (\n    -- * Producers\n    -- $producers\n      stdinLn\n    , readLn\n    , fromHandle\n    , repeatM\n    , replicateM\n    , unfoldr\n\n    -- * Consumers\n    -- $consumers\n    , stdoutLn\n    , stdoutLn'\n    , mapM_\n    , print\n    , toHandle\n    , drain\n\n    -- * Pipes\n    -- $pipes\n    , map\n    , mapM\n    , sequence\n    , mapFoldable\n    , filter\n    , mapMaybe\n    , filterM\n    , wither\n    , take\n    , takeWhile\n    , takeWhile'\n    , drop\n    , dropWhile\n    , concat\n    , elemIndices\n    , findIndices\n    , scan\n    , scanM\n    , chain\n    , read\n    , show\n    , seq\n\n    -- *ListT\n    , loop\n\n    -- * Folds\n    -- $folds\n    , fold\n    , fold'\n    , foldM\n    , foldM'\n    , all\n    , any\n    , and\n    , or\n    , elem\n    , notElem\n    , find\n    , findIndex\n    , head\n    , index\n    , last\n    , length\n    , maximum\n    , minimum\n    , null\n    , sum\n    , product\n    , toList\n    , toListM\n    , toListM'\n\n    -- * Zips\n    , zip\n    , zipWith\n\n    -- * Utilities\n    , tee\n    , generalize\n    ) where\n\nimport Control.Exception (throwIO, try)\nimport Control.Monad (liftM, when, unless, (>=>))\nimport Control.Monad.Trans.State.Strict (get, put)\nimport Data.Functor.Identity (Identity, runIdentity)\nimport Foreign.C.Error (Errno(Errno), ePIPE)\nimport GHC.Exts (build)\nimport Pipes\nimport Pipes.Core\nimport Pipes.Internal\nimport Pipes.Lift (evalStateP)\nimport qualified GHC.IO.Exception as G\nimport qualified System.IO as IO\nimport qualified Prelude\nimport Prelude hiding (\n      all\n    , and\n    , any\n    , concat\n    , drop\n    , dropWhile\n    , elem\n    , filter\n    , head\n    , last\n    , length\n    , map\n    , mapM\n    , mapM_\n    , maximum\n    , minimum\n    , notElem\n    , null\n    , or\n    , print\n    , product\n    , read\n    , readLn\n    , sequence\n    , show\n    , seq\n    , sum\n    , take\n    , takeWhile\n    , zip\n    , zipWith\n    )\n\n{- $producers\n    Use 'for' loops to iterate over 'Producer's whenever you want to perform the\n    same action for every element:\n\n> -- Echo all lines from standard input to standard output\n> runEffect $ for P.stdinLn $ \\str -> do\n>     lift $ putStrLn str\n\n    ... or more concisely:\n\n>>> runEffect $ for P.stdinLn (lift . putStrLn)\nTest<Enter>\nTest\nABC<Enter>\nABC\n...\n\n-}\n\n{-| Read 'String's from 'IO.stdin' using 'getLine'\n\n    Terminates on end of input\n-}\nstdinLn :: MonadIO m => Producer' String m ()\nstdinLn = fromHandle IO.stdin\n{-# INLINABLE stdinLn #-}\n\n-- | 'read' values from 'IO.stdin', ignoring failed parses\nreadLn :: (MonadIO m, Read a) => Producer' a m ()\nreadLn = stdinLn >-> read\n{-# INLINABLE readLn #-}\n\n{-| Read 'String's from a 'IO.Handle' using 'IO.hGetLine'\n\n    Terminates on end of input\n\n@\n'fromHandle' :: 'MonadIO' m => 'IO.Handle' -> 'Producer' 'String' m ()\n@\n-}\nfromHandle :: MonadIO m => IO.Handle -> Proxy x' x () String m ()\nfromHandle h = go\n  where\n    go = do\n        eof <- liftIO $ IO.hIsEOF h\n        unless eof $ do\n            str <- liftIO $ IO.hGetLine h\n            yield str\n            go\n{-# INLINABLE fromHandle #-}\n\n{-| Repeat a monadic action indefinitely, 'yield'ing each result\n\n'repeatM' :: 'Monad' m => m a -> 'Producer' a m r\n-}\nrepeatM :: Monad m => m a -> Proxy x' x () a m r\nrepeatM m = lift m >~ cat\n{-# INLINABLE [1] repeatM #-}\n\n{-# RULES\n  \"repeatM m >-> p\" forall m p . repeatM m >-> p = lift m >~ p\n  #-}\n\n{-| Repeat a monadic action a fixed number of times, 'yield'ing each result\n\n> replicateM  0      x = return ()\n>\n> replicateM (m + n) x = replicateM m x >> replicateM n x  -- 0 <= {m,n}\n\n@\n'replicateM' :: 'Monad' m => Int -> m a -> 'Producer' a m ()\n@\n-}\nreplicateM :: Monad m => Int -> m a -> Proxy x' x () a m ()\nreplicateM n m = lift m >~ take n\n{-# INLINABLE replicateM #-}\n\n{- $consumers\n    Feed a 'Consumer' the same value repeatedly using ('>~'):\n\n>>> runEffect $ lift getLine >~ P.stdoutLn\nTest<Enter>\nTest\nABC<Enter>\nABC\n...\n\n-}\n\n{-| Write 'String's to 'IO.stdout' using 'putStrLn'\n\n    Unlike 'toHandle', 'stdoutLn' gracefully terminates on a broken output pipe\n-}\nstdoutLn :: MonadIO m => Consumer' String m ()\nstdoutLn = go\n  where\n    go = do\n        str <- await\n        x   <- liftIO $ try (putStrLn str)\n        case x of\n           Left (G.IOError { G.ioe_type  = G.ResourceVanished\n                           , G.ioe_errno = Just ioe })\n                | Errno ioe == ePIPE\n                    -> return ()\n           Left  e  -> liftIO (throwIO e)\n           Right () -> go\n{-# INLINABLE stdoutLn #-}\n\n{-| Write 'String's to 'IO.stdout' using 'putStrLn'\n\n    This does not handle a broken output pipe, but has a polymorphic return\n    value\n-}\nstdoutLn' :: MonadIO m => Consumer' String m r\nstdoutLn' = for cat (\\str -> liftIO (putStrLn str))\n{-# INLINABLE [1] stdoutLn' #-}\n\n{-# RULES\n    \"p >-> stdoutLn'\" forall p .\n        p >-> stdoutLn' = for p (\\str -> liftIO (putStrLn str))\n  #-}\n\n-- | Consume all values using a monadic function\nmapM_ :: Monad m => (a -> m ()) -> Consumer' a m r\nmapM_ f = for cat (\\a -> lift (f a))\n{-# INLINABLE [1] mapM_ #-}\n\n{-# RULES\n    \"p >-> mapM_ f\" forall p f .\n        p >-> mapM_ f = for p (\\a -> lift (f a))\n  #-}\n\n-- | 'print' values to 'IO.stdout'\nprint :: (MonadIO m, Show a) => Consumer' a m r\nprint = for cat (\\a -> liftIO (Prelude.print a))\n{-# INLINABLE [1] print #-}\n\n{-# RULES\n    \"p >-> print\" forall p .\n        p >-> print = for p (\\a -> liftIO (Prelude.print a))\n  #-}\n\n-- | Write 'String's to a 'IO.Handle' using 'IO.hPutStrLn'\ntoHandle :: MonadIO m => IO.Handle -> Consumer' String m r\ntoHandle handle = for cat (\\str -> liftIO (IO.hPutStrLn handle str))\n{-# INLINABLE [1] toHandle #-}\n\n{-# RULES\n    \"p >-> toHandle handle\" forall p handle .\n        p >-> toHandle handle = for p (\\str -> liftIO (IO.hPutStrLn handle str))\n  #-}\n\n-- | 'discard' all incoming values\ndrain :: Functor m => Consumer' a m r\ndrain = for cat discard\n{-# INLINABLE [1] drain #-}\n\n{-# RULES\n    \"p >-> drain\" forall p .\n        p >-> drain = for p discard\n  #-}\n\n{- $pipes\n    Use ('>->') to connect 'Producer's, 'Pipe's, and 'Consumer's:\n\n>>> runEffect $ P.stdinLn >-> P.takeWhile (/= \"quit\") >-> P.stdoutLn\nTest<Enter>\nTest\nABC<Enter>\nABC\nquit<Enter>\n>>>\n\n-}\n\n{-| Apply a function to all values flowing downstream\n\n> map id = cat\n>\n> map (g . f) = map f >-> map g\n-}\nmap :: Functor m => (a -> b) -> Pipe a b m r\nmap f = for cat (\\a -> yield (f a))\n{-# INLINABLE [1] map #-}\n\n{-# RULES\n    \"p >-> map f\" forall p f . p >-> map f = for p (\\a -> yield (f a))\n\n  ; \"map f >-> p\" forall p f . map f >-> p = (do\n        a <- await\n        return (f a) ) >~ p\n  #-}\n\n{-| Apply a monadic function to all values flowing downstream\n\n> mapM return = cat\n>\n> mapM (f >=> g) = mapM f >-> mapM g\n-}\nmapM :: Monad m => (a -> m b) -> Pipe a b m r\nmapM f = for cat $ \\a -> do\n    b <- lift (f a)\n    yield b\n{-# INLINABLE [1] mapM #-}\n\n{-# RULES\n    \"p >-> mapM f\" forall p f . p >-> mapM f = for p (\\a -> do\n        b <- lift (f a)\n        yield b )\n\n  ; \"mapM f >-> p\" forall p f . mapM f >-> p = (do\n        a <- await\n        b <- lift (f a)\n        return b ) >~ p\n  #-}\n\n-- | Convert a stream of actions to a stream of values\nsequence :: Monad m => Pipe (m a) a m r\nsequence = mapM id\n{-# INLINABLE sequence #-}\n\n{- | Apply a function to all values flowing downstream, and\n     forward each element of the result.\n-}\nmapFoldable :: (Functor m, Foldable t) => (a -> t b) -> Pipe a b m r\nmapFoldable f = for cat (\\a -> each (f a))\n{-# INLINABLE [1] mapFoldable #-}\n\n{-# RULES\n    \"p >-> mapFoldable f\" forall p f .\n        p >-> mapFoldable f = for p (\\a -> each (f a))\n  #-}\n\n{-| @(filter predicate)@ only forwards values that satisfy the predicate.\n\n> filter (pure True) = cat\n>\n> filter (liftA2 (&&) p1 p2) = filter p1 >-> filter p2\n>\n> filter f = mapMaybe (\\a -> a <$ guard (f a))\n-}\nfilter :: Functor m => (a -> Bool) -> Pipe a a m r\nfilter predicate = for cat $ \\a -> when (predicate a) (yield a)\n{-# INLINABLE [1] filter #-}\n\n{-# RULES\n    \"p >-> filter predicate\" forall p predicate.\n        p >-> filter predicate = for p (\\a -> when (predicate a) (yield a))\n  #-}\n\n{-| @(mapMaybe f)@ yields 'Just' results of 'f'.\n\nBasic laws:\n\n> mapMaybe (f >=> g) = mapMaybe f >-> mapMaybe g\n>\n> mapMaybe (pure @Maybe . f) = mapMaybe (Just . f) = map f\n>\n> mapMaybe (const Nothing) = drain\n\nAs a result of the second law,\n\n> mapMaybe return = mapMaybe Just = cat\n-}\nmapMaybe :: Functor m => (a -> Maybe b) -> Pipe a b m r\nmapMaybe f = for cat $ maybe (pure ()) yield . f\n{-# INLINABLE [1] mapMaybe #-}\n\n{-# RULES\n    \"p >-> mapMaybe f\" forall p f.\n        p >-> mapMaybe f = for p $ maybe (pure ()) yield . f\n  #-}\n\n{-| @(filterM predicate)@ only forwards values that satisfy the monadic\n    predicate\n\n> filterM (pure (pure True)) = cat\n>\n> filterM (liftA2 (liftA2 (&&)) p1 p2) = filterM p1 >-> filterM p2\n>\n> filterM f = wither (\\a -> (\\b -> a <$ guard b) <$> f a)\n-}\nfilterM :: Monad m => (a -> m Bool) -> Pipe a a m r\nfilterM predicate = for cat $ \\a -> do\n    b <- lift (predicate a)\n    when b (yield a)\n{-# INLINABLE [1] filterM #-}\n\n{-# RULES\n    \"p >-> filterM predicate\" forall p predicate .\n        p >-> filterM predicate = for p (\\a -> do\n            b <- lift (predicate a)\n            when b (yield a) )\n  #-}\n\n{-| @(wither f)@ forwards 'Just' values produced by the\n    monadic action.\n\nBasic laws:\n\n> wither (runMaybeT . (MaybeT . f >=> MaybeT . g)) = wither f >-> wither g\n>\n> wither (runMaybeT . lift . f) = wither (fmap Just . f) = mapM f\n>\n> wither (pure . f) = mapMaybe f\n\nAs a result of the second law,\n\n> wither (runMaybeT . return) = cat\n\nAs a result of the third law,\n\n> wither (pure . const Nothing) = wither (const (pure Nothing)) = drain\n-}\nwither :: Monad m => (a -> m (Maybe b)) -> Pipe a b m r\nwither f = for cat $ lift . f >=> maybe (pure ()) yield\n{-# INLINABLE [1] wither #-}\n\n{-# RULES\n    \"p >-> wither f\" forall p f .\n        p >-> wither f = for p $ lift . f >=> maybe (pure ()) yield\n  #-}\n\n{-| @(take n)@ only allows @n@ values to pass through\n\n> take 0 = return ()\n>\n> take (m + n) = take m >> take n\n\n> take <infinity> = cat\n>\n> take (min m n) = take m >-> take n\n-}\ntake :: Functor m => Int -> Pipe a a m ()\ntake = go\n  where\n    go 0 = return () \n    go n = do \n        a <- await\n        yield a\n        go (n-1)\n{-# INLINABLE take #-}\n\n{-| @(takeWhile p)@ allows values to pass downstream so long as they satisfy\n    the predicate @p@.\n\n> takeWhile (pure True) = cat\n>\n> takeWhile (liftA2 (&&) p1 p2) = takeWhile p1 >-> takeWhile p2\n-}\ntakeWhile :: Functor m => (a -> Bool) -> Pipe a a m ()\ntakeWhile predicate = go\n  where\n    go = do\n        a <- await\n        if (predicate a)\n            then do\n                yield a\n                go\n            else return ()\n{-# INLINABLE takeWhile #-}\n\n{-| @(takeWhile' p)@ is a version of takeWhile that returns the value failing\n    the predicate.\n\n> takeWhile' (pure True) = cat\n>\n> takeWhile' (liftA2 (&&) p1 p2) = takeWhile' p1 >-> takeWhile' p2\n-}\ntakeWhile' :: Functor m => (a -> Bool) -> Pipe a a m a\ntakeWhile' predicate = go\n  where\n    go = do\n        a <- await\n        if (predicate a)\n            then do\n                yield a\n                go\n            else return a\n{-# INLINABLE takeWhile' #-}\n\n{-| @(drop n)@ discards @n@ values going downstream\n\n> drop 0 = cat\n>\n> drop (m + n) = drop m >-> drop n\n-}\ndrop :: Functor m => Int -> Pipe a a m r\ndrop = go\n  where\n    go 0 = cat\n    go n =  do\n        await\n        go (n-1)\n{-# INLINABLE drop #-}\n\n{-| @(dropWhile p)@ discards values going downstream until one violates the\n    predicate @p@.\n\n> dropWhile (pure False) = cat\n>\n> dropWhile (liftA2 (||) p1 p2) = dropWhile p1 >-> dropWhile p2\n-}\ndropWhile :: Functor m => (a -> Bool) -> Pipe a a m r\ndropWhile predicate = go\n  where\n    go = do\n        a <- await\n        if (predicate a)\n            then go\n            else do\n                yield a\n                cat\n{-# INLINABLE dropWhile #-}\n\n-- | Flatten all 'Foldable' elements flowing downstream\nconcat :: (Functor m, Foldable f) => Pipe (f a) a m r\nconcat = for cat each\n{-# INLINABLE [1] concat #-}\n\n{-# RULES\n    \"p >-> concat\" forall p . p >-> concat = for p each\n  #-}\n\n-- | Outputs the indices of all elements that match the given element\nelemIndices :: (Functor m, Eq a) => a -> Pipe a Int m r\nelemIndices a = findIndices (a ==)\n{-# INLINABLE elemIndices #-}\n\n-- | Outputs the indices of all elements that satisfied the predicate\nfindIndices :: Functor m => (a -> Bool) -> Pipe a Int m r\nfindIndices predicate = go 0\n  where\n    go n = do\n        a <- await\n        when (predicate a) (yield n)\n        go $! n + 1\n{-# INLINABLE findIndices #-}\n\n{-| Strict left scan\n\n> Control.Foldl.purely scan :: Monad m => Fold a b -> Pipe a b m r\n-}\nscan :: Functor m => (x -> a -> x) -> x -> (x -> b) -> Pipe a b m r\nscan step begin done = go begin\n  where\n    go x = do\n        yield (done x)\n        a <- await\n        let x' = step x a\n        go $! x'\n{-# INLINABLE scan #-}\n\n{-| Strict, monadic left scan\n\n> Control.Foldl.impurely scanM :: Monad m => FoldM m a b -> Pipe a b m r\n-}\nscanM :: Monad m => (x -> a -> m x) -> m x -> (x -> m b) -> Pipe a b m r\nscanM step begin done = do\n    x <- lift begin\n    go x\n  where\n    go x = do\n        b <- lift (done x)\n        yield b\n        a  <- await\n        x' <- lift (step x a)\n        go $! x'\n{-# INLINABLE scanM #-}\n\n{-| Apply an action to all values flowing downstream\n\n> chain (pure (return ())) = cat\n>\n> chain (liftA2 (>>) m1 m2) = chain m1 >-> chain m2\n-}\nchain :: Monad m => (a -> m ()) -> Pipe a a m r\nchain f = for cat $ \\a -> do\n    lift (f a)\n    yield a\n{-# INLINABLE [1] chain #-}\n\n{-# RULES\n    \"p >-> chain f\" forall p f .\n        p >-> chain f = for p (\\a -> do\n            lift (f a)\n            yield a )\n  ; \"chain f >-> p\" forall p f .\n        chain f >-> p = (do\n            a <- await\n            lift (f a)\n            return a ) >~ p\n  #-}\n\n-- | Parse 'Read'able values, only forwarding the value if the parse succeeds\nread :: (Functor m, Read a) => Pipe String a m r\nread = for cat $ \\str -> case (reads str) of\n    [(a, \"\")] -> yield a\n    _         -> return ()\n{-# INLINABLE [1] read #-}\n\n{-# RULES\n    \"p >-> read\" forall p .\n        p >-> read = for p (\\str -> case (reads str) of\n            [(a, \"\")] -> yield a\n            _         -> return () )\n  #-}\n\n-- | Convert 'Show'able values to 'String's\nshow :: (Functor m, Show a) => Pipe a String m r\nshow = map Prelude.show\n{-# INLINABLE show #-}\n\n-- | Evaluate all values flowing downstream to WHNF\nseq :: Functor m => Pipe a a m r\nseq = for cat $ \\a -> yield $! a\n{-# INLINABLE seq #-}\n\n{-| Create a `Pipe` from a `ListT` transformation\n\n> loop (k1 >=> k2) = loop k1 >-> loop k2\n>\n> loop return = cat\n-}\nloop :: Monad m => (a -> ListT m b) -> Pipe a b m r\nloop k = for cat (every . k)\n{-# INLINABLE loop #-}\n\n{- $folds\n    Use these to fold the output of a 'Producer'.  Many of these folds will stop\n    drawing elements if they can compute their result early, like 'any':\n\n>>> P.any Prelude.null P.stdinLn\nTest<Enter>\nABC<Enter>\n<Enter>\nTrue\n>>>\n\n-}\n\n{-| Strict fold of the elements of a 'Producer'\n\n> Control.Foldl.purely fold :: Monad m => Fold a b -> Producer a m () -> m b\n-}\nfold :: Monad m => (x -> a -> x) -> x -> (x -> b) -> Producer a m () -> m b\nfold step begin done p0 = go p0 begin\n  where\n    go p x = case p of\n        Request v  _  -> closed v\n        Respond a  fu -> go (fu ()) $! step x a\n        M          m  -> m >>= \\p' -> go p' x\n        Pure    _     -> return (done x)\n{-# INLINABLE fold #-}\n\n{-| Strict fold of the elements of a 'Producer' that preserves the return value\n\n> Control.Foldl.purely fold' :: Monad m => Fold a b -> Producer a m r -> m (b, r)\n-}\nfold' :: Monad m => (x -> a -> x) -> x -> (x -> b) -> Producer a m r -> m (b, r)\nfold' step begin done p0 = go p0 begin\n  where\n    go p x = case p of\n        Request v  _  -> closed v\n        Respond a  fu -> go (fu ()) $! step x a\n        M          m  -> m >>= \\p' -> go p' x\n        Pure    r     -> return (done x, r)\n{-# INLINABLE fold' #-}\n\n{-| Strict, monadic fold of the elements of a 'Producer'\n\n> Control.Foldl.impurely foldM :: Monad m => FoldM a b -> Producer a m () -> m b\n-}\nfoldM\n    :: Monad m\n    => (x -> a -> m x) -> m x -> (x -> m b) -> Producer a m () -> m b\nfoldM step begin done p0 = do\n    x0 <- begin\n    go p0 x0\n  where\n    go p x = case p of\n        Request v  _  -> closed v\n        Respond a  fu -> do\n            x' <- step x a\n            go (fu ()) $! x'\n        M          m  -> m >>= \\p' -> go p' x\n        Pure    _     -> done x\n{-# INLINABLE foldM #-}\n\n{-| Strict, monadic fold of the elements of a 'Producer'\n\n> Control.Foldl.impurely foldM' :: Monad m => FoldM a b -> Producer a m r -> m (b, r)\n-}\nfoldM'\n    :: Monad m\n    => (x -> a -> m x) -> m x -> (x -> m b) -> Producer a m r -> m (b, r)\nfoldM' step begin done p0 = do\n    x0 <- begin\n    go p0 x0\n  where\n    go p x = case p of\n        Request v  _  -> closed v\n        Respond a  fu -> do\n            x' <- step x a\n            go (fu ()) $! x'\n        M          m  -> m >>= \\p' -> go p' x\n        Pure    r     -> do\n            b <- done x\n            return (b, r)\n{-# INLINABLE foldM' #-}\n\n{-| @(all predicate p)@ determines whether all the elements of @p@ satisfy the\n    predicate.\n-}\nall :: Monad m => (a -> Bool) -> Producer a m () -> m Bool\nall predicate p = null $ p >-> filter (\\a -> not (predicate a))\n{-# INLINABLE all #-}\n\n{-| @(any predicate p)@ determines whether any element of @p@ satisfies the\n    predicate.\n-}\nany :: Monad m => (a -> Bool) -> Producer a m () -> m Bool\nany predicate p = liftM not $ null (p >-> filter predicate)\n{-# INLINABLE any #-}\n\n-- | Determines whether all elements are 'True'\nand :: Monad m => Producer Bool m () -> m Bool\nand = all id\n{-# INLINABLE and #-}\n\n-- | Determines whether any element is 'True'\nor :: Monad m => Producer Bool m () -> m Bool\nor = any id\n{-# INLINABLE or #-}\n\n{-| @(elem a p)@ returns 'True' if @p@ has an element equal to @a@, 'False'\n    otherwise\n-}\nelem :: (Monad m, Eq a) => a -> Producer a m () -> m Bool\nelem a = any (a ==)\n{-# INLINABLE elem #-}\n\n{-| @(notElem a)@ returns 'False' if @p@ has an element equal to @a@, 'True'\n    otherwise\n-}\nnotElem :: (Monad m, Eq a) => a -> Producer a m () -> m Bool\nnotElem a = all (a /=)\n{-# INLINABLE notElem #-}\n\n-- | Find the first element of a 'Producer' that satisfies the predicate\nfind :: Monad m => (a -> Bool) -> Producer a m () -> m (Maybe a)\nfind predicate p = head (p >-> filter predicate)\n{-# INLINABLE find #-}\n\n{-| Find the index of the first element of a 'Producer' that satisfies the\n    predicate\n-}\nfindIndex :: Monad m => (a -> Bool) -> Producer a m () -> m (Maybe Int)\nfindIndex predicate p = head (p >-> findIndices predicate)\n{-# INLINABLE findIndex #-}\n\n-- | Retrieve the first element from a 'Producer'\nhead :: Monad m => Producer a m () -> m (Maybe a)\nhead p = do\n    x <- next p\n    return $ case x of\n        Left   _     -> Nothing\n        Right (a, _) -> Just a\n{-# INLINABLE head #-}\n\n-- | Index into a 'Producer'\nindex :: Monad m => Int -> Producer a m () -> m (Maybe a)\nindex n p = head (p >-> drop n)\n{-# INLINABLE index #-}\n\n-- | Retrieve the last element from a 'Producer'\nlast :: Monad m => Producer a m () -> m (Maybe a)\nlast p0 = do\n    x <- next p0\n    case x of\n        Left   _      -> return Nothing\n        Right (a, p') -> go a p'\n  where\n    go a p = do\n        x <- next p\n        case x of\n            Left   _       -> return (Just a)\n            Right (a', p') -> go a' p'\n{-# INLINABLE last #-}\n\n-- | Count the number of elements in a 'Producer'\nlength :: Monad m => Producer a m () -> m Int\nlength = fold (\\n _ -> n + 1) 0 id\n{-# INLINABLE length #-}\n\n-- | Find the maximum element of a 'Producer'\nmaximum :: (Monad m, Ord a) => Producer a m () -> m (Maybe a)\nmaximum = fold step Nothing id\n  where\n    step x a = Just $ case x of\n        Nothing -> a\n        Just a' -> max a a'\n{-# INLINABLE maximum #-}\n\n-- | Find the minimum element of a 'Producer'\nminimum :: (Monad m, Ord a) => Producer a m () -> m (Maybe a)\nminimum = fold step Nothing id\n  where\n    step x a = Just $ case x of\n        Nothing -> a\n        Just a' -> min a a'\n{-# INLINABLE minimum #-}\n\n-- | Determine if a 'Producer' is empty\nnull :: Monad m => Producer a m () -> m Bool\nnull p = do\n    x <- next p\n    return $ case x of\n        Left  _ -> True\n        Right _ -> False\n{-# INLINABLE null #-}\n\n-- | Compute the sum of the elements of a 'Producer'\nsum :: (Monad m, Num a) => Producer a m () -> m a\nsum = fold (+) 0 id\n{-# INLINABLE sum #-}\n\n-- | Compute the product of the elements of a 'Producer'\nproduct :: (Monad m, Num a) => Producer a m () -> m a\nproduct = fold (*) 1 id\n{-# INLINABLE product #-}\n\n-- | Convert a pure 'Producer' into a list\ntoList :: Producer a Identity () -> [a]\ntoList prod0 = build (go prod0)\n  where\n    go prod cons nil =\n      case prod of\n        Request v _  -> closed v\n        Respond a fu -> cons a (go (fu ()) cons nil)\n        M         m  -> go (runIdentity m) cons nil\n        Pure    _    -> nil\n{-# INLINE toList #-}\n\n{-| Convert an effectful 'Producer' into a list\n\n    Note: 'toListM' is not an idiomatic use of @pipes@, but I provide it for\n    simple testing purposes.  Idiomatic @pipes@ style consumes the elements\n    immediately as they are generated instead of loading all elements into\n    memory.\n-}\ntoListM :: Monad m => Producer a m () -> m [a]\ntoListM = fold step begin done\n  where\n    step x a = x . (a:)\n    begin = id\n    done x = x []\n{-# INLINABLE toListM #-}\n\n{-| Convert an effectful 'Producer' into a list alongside the return value\n\n    Note: 'toListM'' is not an idiomatic use of @pipes@, but I provide it for\n    simple testing purposes.  Idiomatic @pipes@ style consumes the elements\n    immediately as they are generated instead of loading all elements into\n    memory.\n-}\ntoListM' :: Monad m => Producer a m r -> m ([a], r)\ntoListM' = fold' step begin done\n  where\n    step x a = x . (a:)\n    begin = id\n    done x = x []\n{-# INLINABLE toListM' #-}\n\n-- | Zip two 'Producer's\nzip :: Monad m\n    => (Producer       a     m r)\n    -> (Producer          b  m r)\n    -> (Proxy x' x () (a, b) m r)\nzip = zipWith (,)\n{-# INLINABLE zip #-}\n\n-- | Zip two 'Producer's using the provided combining function\nzipWith :: Monad m\n    => (a -> b -> c)\n    -> (Producer  a m r)\n    -> (Producer  b m r)\n    -> (Proxy x' x () c m r)\nzipWith f = go\n  where\n    go p1 p2 = do\n        e1 <- lift $ next p1\n        case e1 of\n            Left r         -> return r\n            Right (a, p1') -> do\n                e2 <- lift $ next p2\n                case e2 of\n                    Left r         -> return r\n                    Right (b, p2') -> do\n                        yield (f a b)\n                        go p1' p2'\n{-# INLINABLE zipWith #-}\n\n{-| Transform a 'Consumer' to a 'Pipe' that reforwards all values further\n    downstream\n-}\ntee :: Monad m => Consumer a m r -> Pipe a a m r\ntee p = evalStateP Nothing $ do\n    r <- up >\\\\ (hoist lift p //> dn)\n    ma <- lift get\n    case ma of\n        Nothing -> return ()\n        Just a  -> yield a\n    return r\n  where\n    up () = do\n        ma <- lift get\n        case ma of\n            Nothing -> return ()\n            Just a  -> yield a\n        a <- await\n        lift $ put (Just a)\n        return a\n    dn v = closed v\n{-# INLINABLE tee #-}\n\n{-| Transform a unidirectional 'Pipe' to a bidirectional 'Proxy'\n\n> generalize (f >-> g) = generalize f >+> generalize g\n>\n> generalize cat = pull\n-}\ngeneralize :: Monad m => Pipe a b m r -> x -> Proxy x a x b m r\ngeneralize p x0 = evalStateP x0 $ up >\\\\ hoist lift p //> dn\n  where\n    up () = do\n        x <- lift get\n        request x\n    dn a = do\n        x <- respond a\n        lift $ put x\n{-# INLINABLE generalize #-}\n\n{-| The natural unfold into a 'Producer' with a step function and a seed \n\n> unfoldr next = id\n-}\nunfoldr :: Monad m \n        => (s -> m (Either r (a, s))) -> s -> Producer a m r\nunfoldr step = go where\n  go s0 = do\n    e <- lift (step s0)\n    case e of\n      Left r -> return r\n      Right (a,s) -> do \n        yield a\n        go s\n{-# INLINABLE unfoldr #-}\n"
  },
  {
    "path": "src/Pipes/Tutorial.hs",
    "content": "{-# OPTIONS_GHC -fno-warn-unused-imports #-}\n\n{-| Conventional Haskell stream programming forces you to choose only two of the\n    following three features:\n\n    * Effects\n\n    * Streaming\n\n    * Composability\n\n    If you sacrifice /Effects/ you get Haskell's pure and lazy lists, which you\n    can transform using composable functions in constant space, but without\n    interleaving effects.\n\n    If you sacrifice /Streaming/ you get 'mapM', 'forM' and\n    \\\"ListT done wrong\\\", which are composable and effectful, but do not return\n    a single result until the whole list has first been processed and loaded\n    into memory.\n\n    If you sacrifice /Composability/ you write a tightly coupled read,\n    transform, and write loop in 'IO', which is streaming and effectful, but is\n    not modular or separable.\n\n    @pipes@ gives you all three features: effectful, streaming, and composable\n    programming.  @pipes@ also provides a wide variety of stream programming\n    abstractions which are all subsets of a single unified machinery:\n\n    * effectful 'Producer's (like generators),\n\n    * effectful 'Consumer's (like iteratees),\n\n    * effectful 'Pipe's (like Unix pipes), and:\n\n    * 'ListT' done right.\n\n    All of these are connectable and you can combine them together in clever and\n    unexpected ways because they all share the same underlying type.\n\n    @pipes@ requires a basic understanding of monad transformers, which you can\n    learn about by reading either:\n\n    * the paper \\\"Monad Transformers - Step by Step\\\",\n    \n    * part III \\\"Monads in the Real World\\\" of the tutorial \\\"All About Monads\\\",\n\n    * chapter 18 of \\\"Real World Haskell\\\" on monad transformers, or:\n\n    * the documentation of the @transformers@ library.\n\n    If you want a Quick Start guide to @pipes@, read the documentation in\n    \"Pipes.Prelude\" from top to bottom.\n\n    This tutorial is more extensive and explains the @pipes@ API in greater\n    detail and illustrates several idioms.\n-}\n\nmodule Pipes.Tutorial (\n    -- * Introduction\n    -- $introduction\n\n    -- * Producers\n    -- $producers\n\n    -- * Composability\n    -- $composability\n\n    -- * Consumers\n    -- $consumers\n\n    -- * Pipes\n    -- $pipes\n\n    -- * ListT\n    -- $listT\n\n    -- * Tricks\n    -- $tricks\n\n    -- * Conclusion\n    -- $conclusion\n\n    -- * Appendix: Types\n    -- $types\n\n    -- * Appendix: Time Complexity\n    -- $timecomplexity\n\n    -- * Copyright\n    -- $copyright\n    ) where\n\nimport Control.Category\nimport Control.Monad\nimport Pipes\nimport qualified Pipes.Prelude as P\nimport Prelude hiding ((.), id)\n\n{- $introduction\n    The @pipes@ library decouples stream processing stages from each other so\n    that you can mix and match diverse stages to produce useful streaming\n    programs.  If you are a library writer, @pipes@ lets you package up\n    streaming components into a reusable interface.  If you are an application\n    writer, @pipes@ lets you connect pre-made streaming components with minimal\n    effort to produce a highly-efficient program that streams data in constant\n    memory.\n\n    To enforce loose coupling, components can only communicate using two\n    commands:\n\n    * 'yield': Send output data\n\n    * 'await': Receive input data\n\n    @pipes@ has four types of components built around these two commands:\n\n    * 'Producer's can only 'yield' values and they model streaming sources\n\n    * 'Consumer's can only 'await' values and they model streaming sinks\n\n    * 'Pipe's can both 'yield' and 'await' values and they model stream\n      transformations\n\n    * 'Effect's can neither 'yield' nor 'await' and they model non-streaming\n      components\n\n    You can connect these components together in four separate ways which\n    parallel the four above types:\n\n    * 'for' handles 'yield's\n\n    * ('>~') handles 'await's\n\n    * ('>->') handles both 'yield's and 'await's\n\n    * ('>>=') handles return values\n\n    As you connect components their types will change to reflect inputs and\n    outputs that you've fused away.  You know that you're done connecting things\n    when you get an 'Effect', meaning that you have handled all inputs and\n    outputs.  You run this final 'Effect' to begin streaming.\n-}\n\n{- $producers\n    'Producer's are effectful streams of input.  Specifically, a 'Producer' is a\n    monad transformer that extends any base monad with a new 'yield' command.\n    This 'yield' command lets you send output downstream to an anonymous\n    handler, decoupling how you generate values from how you consume them.\n\n    The following @stdinLn@ 'Producer' shows how to incrementally read in\n    'String's from standard input and 'yield' them downstream, terminating\n    gracefully when reaching the end of the input:\n\n> -- echo.hs\n>\n> import Control.Monad (unless)\n> import Pipes\n> import System.IO (isEOF)\n>\n> --         +--------+-- A 'Producer' that yields 'String's\n> --         |        |\n> --         |        |      +-- Every monad transformer has a base monad.\n> --         |        |      |   This time the base monad is 'IO'.\n> --         |        |      |  \n> --         |        |      |  +-- Every monadic action has a return value.\n> --         |        |      |  |   This action returns '()' when finished\n> --         v        v      v  v\n> stdinLn :: Producer String IO ()\n> stdinLn = do\n>     eof <- lift isEOF        -- 'lift' an 'IO' action from the base monad\n>     unless eof $ do\n>         str <- lift getLine\n>         yield str            -- 'yield' the 'String'\n>         stdinLn              -- Loop\n\n    'yield' emits a value, suspending the current 'Producer' until the value is\n    consumed.  If nobody consumes the value (which is possible) then 'yield'\n    never returns.  You can think of 'yield' as having the following type:\n\n@\n 'yield' :: 'Monad' m => a -> 'Producer' a m ()\n@\n\n    The true type of 'yield' is actually more general and powerful.  Throughout\n    the tutorial I will present type signatures like this that are simplified at\n    first and then later reveal more general versions.  So read the above type\n    signature as simply saying: \\\"You can use 'yield' within a 'Producer', but\n    you may be able to use 'yield' in other contexts, too.\\\"\n\n    Click the link to 'yield' to navigate to its documentation.  There you will\n    see that 'yield' actually uses the 'Producer'' (with an apostrophe) type\n    synonym which hides a lot of polymorphism behind a simple veneer.  The\n    documentation for 'yield' says that you can also use 'yield' within a\n    'Pipe', too, because of this polymorphism:\n\n@\n 'yield' :: 'Monad' m => a -> 'Pipe' x a m ()\n@\n\n    Use simpler types like these to guide you until you understand the fully\n    general type.\n\n    'for' loops are the simplest way to consume a 'Producer' like @stdinLn@.\n    'for' has the following type:\n\n@\n \\-\\-                +-- Producer      +-- The body of the   +-- Result\n \\-\\-                |   to loop       |   loop              |\n \\-\\-                v   over          v                     v\n \\-\\-                --------------    ------------------    ----------\n 'for' :: 'Monad' m => 'Producer' a m r -> (a -> 'Effect' m ()) -> 'Effect' m r\n@\n\n    @(for producer body)@ loops over @(producer)@, substituting each 'yield' in\n    @(producer)@ with @(body)@.\n\n    You can also deduce that behavior purely from the type signature:\n\n    * The body of the loop takes exactly one argument of type @(a)@, which is\n      the same as the output type of the 'Producer'.  Therefore, the body of the\n      loop must get its input from that 'Producer' and nowhere else.\n\n    * The return value of the input 'Producer' matches the return value of the\n      result, therefore 'for' must loop over the entire 'Producer' and not skip\n      anything.\n\n    The above type signature is not the true type of 'for', which is actually\n    more general.  Think of the above type signature as saying: \\\"If the first\n    argument of 'for' is a 'Producer' and the second argument returns an\n    'Effect', then the final result must be an 'Effect'.\\\"\n\n    Click the link to 'for' to navigate to its documentation.  There you will\n    see the fully general type and underneath you will see equivalent simpler\n    types.  One of these says that if the body of the loop is a 'Producer', then\n    the result is a 'Producer', too:\n\n@\n 'for' :: 'Monad' m => 'Producer' a m r -> (a -> 'Producer' b m ()) -> 'Producer' b m r\n@\n\n    The first type signature I showed for 'for' was a special case of this\n    slightly more general signature because a 'Producer' that never 'yield's is\n    also an 'Effect':\n\n@\n data 'X'  -- The uninhabited type\n\n\\ type 'Effect' m r = 'Producer' 'X' m r\n@\n\n    This is why 'for' permits two different type signatures.  The first type\n    signature is just a special case of the second one:\n\n@\n 'for' :: 'Monad' m => 'Producer' a m r -> (a -> 'Producer' b m ()) -> 'Producer' b m r\n\n\\ -- Specialize \\'b\\' to \\'X\\'\n 'for' :: 'Monad' m => 'Producer' a m r -> (a -> 'Producer' 'X' m ()) -> 'Producer' 'X' m r\n\n\\ -- Producer X = Effect\n 'for' :: 'Monad' m => 'Producer' a m r -> (a -> 'Effect'     m ()) -> 'Effect'     m r\n@\n\n    This is the same trick that all @pipes@ functions use to work with various\n    combinations of 'Producer's, 'Consumer's, 'Pipe's, and 'Effect's.  Each\n    function really has just one general type, which you can then simplify down\n    to multiple useful alternative types.\n\n    Here's an example use of a 'for' @loop@, where the second argument (the\n    loop body) is an 'Effect':\n\n> -- echo.hs\n>\n> loop :: Effect IO ()\n> loop = for stdinLn $ \\str -> do  -- Read this like: \"for str in stdinLn\"\n>     lift $ putStrLn str          -- The body of the 'for' loop\n>\n> -- more concise: loop = for stdinLn (lift . putStrLn)\n\n    In this example, 'for' loops over @stdinLn@ and replaces every 'yield' in\n    @stdinLn@ with the body of the loop, printing each line.  This is exactly\n    equivalent to the following code, which I've placed side-by-side with the\n    original definition of @stdinLn@ for comparison:\n\n> loop = do                      |  stdinLn = do\n>     eof <- lift isEOF          |      eof <- lift isEOF\n>     unless eof $ do            |      unless eof $ do\n>         str <- lift getLine    |          str <- lift getLine\n>         (lift . putStrLn) str  |          yield str\n>         loop                   |          stdinLn\n\n    You can think of 'yield' as creating a hole and a 'for' loop is one way to\n    fill that hole.\n\n    Notice how the final @loop@ only 'lift's actions from the base monad and\n    does nothing else.  This property is true for all 'Effect's, which are just\n    glorified wrappers around actions in the base monad.  This means we can run\n    these 'Effect's to remove their 'lift's and lower them back to the\n    equivalent computation in the base monad:\n\n@\n 'runEffect' :: 'Monad' m => 'Effect' m r -> m r\n@\n\n    This is the real type signature of 'runEffect', which refuses to accept\n    anything other than an 'Effect'.  This ensures that we handle all inputs and\n    outputs before streaming data:\n\n> -- echo.hs\n>\n> main :: IO ()\n> main = runEffect loop\n\n    ... or you could inline the entire @loop@ into the following one-liner:\n\n> main = runEffect $ for stdinLn (lift . putStrLn)\n\n    Our final program loops over standard input and echoes every line to\n    standard output until we hit @Ctrl-D@ to end the input stream:\n\n> $ ghc -O2 echo.hs\n> $ ./echo\n> Test<Enter>\n> Test\n> ABC<Enter>\n> ABC\n> <Ctrl-D>\n> $\n\n    The final behavior is indistinguishable from just removing all the 'lift's\n    from @loop@:\n\n> main = do               |  loop = do\n>     eof <- isEof        |      eof <- lift isEof\n>     unless eof $ do     |      unless eof $ do\n>         str <- getLine  |          str <- lift getLine\n>         putStrLn str    |          (lift . putStrLn) str\n>         main            |          loop\n\n    This @main@ is what we might have written by hand if we were not using\n    @pipes@, but with @pipes@ we can decouple the input and output logic from\n    each other.  When we connect them back together, we still produce streaming\n    code equivalent to what a sufficiently careful Haskell programmer would\n    have written.\n\n    You can also use 'for' to loop over lists, too.  To do so, convert the list\n    to a 'Producer' using 'each', which is exported by default from \"Pipes\":\n\n> each :: Monad m => [a] -> Producer a m ()\n> each as = mapM_ yield as\n\n    Combine 'for' and 'each' to iterate over lists using a \\\"foreach\\\" loop:\n\n>>> runEffect $ for (each [1..4]) (lift . print)\n1\n2\n3\n4\n\n    'each' is actually more general and works for any 'Foldable':\n\n@\n 'each' :: ('Monad' m, 'Foldable' f) => f a -> 'Producer' a m ()\n@\n\n     So you can loop over any 'Foldable' container or even a 'Maybe':\n\n>>> runEffect $ for (each (Just 1)) (lift . print)\n1\n\n-}\n\n{- $composability\n    You might wonder why the body of a 'for' loop can be a 'Producer'.  Let's\n    test out this feature by defining a new loop body that creates three copies\n    of every value:\n\n> -- nested.hs\n>\n> import Pipes\n> import qualified Pipes.Prelude as P  -- Pipes.Prelude already has 'stdinLn'\n> \n> triple :: Monad m => a -> Producer a m ()\n> triple x = do\n>     yield x\n>     yield x\n>     yield x\n>\n> loop :: Producer String IO ()\n> loop = for P.stdinLn triple\n>\n> -- This is the exact same as:\n> --\n> -- loop = for P.stdinLn $ \\x -> do\n> --     yield x\n> --     yield x\n> --     yield x\n\n    This time our @loop@ is a 'Producer' that outputs 'String's, specifically\n    three copies of each line that we read from standard input.  Since @loop@ is\n    a 'Producer' we cannot run it because there is still unhandled output.\n    However, we can use yet another 'for' to handle this new repeated stream:\n\n> -- nested.hs\n>\n> main = runEffect $ for loop (lift . putStrLn)\n\n    This creates a program which echoes every line from standard input to\n    standard output three times:\n\n> $ ./nested\n> Test<Enter>\n> Test\n> Test\n> Test\n> ABC<Enter>\n> ABC\n> ABC\n> ABC\n> <Ctrl-D>\n> $\n\n    But is this really necessary?  Couldn't we have instead written this using a\n    nested for loop?\n\n> main = runEffect $\n>     for P.stdinLn $ \\str1 ->\n>         for (triple str1) $ \\str2 ->\n>             lift $ putStrLn str2\n\n    Yes, we could have!  In fact, this is a special case of the following\n    equality, which always holds no matter what:\n\n@\n \\-\\- s :: Monad m =>      'Producer' a m ()  -- i.e. \\'P.stdinLn\\'\n \\-\\- f :: Monad m => a -> 'Producer' b m ()  -- i.e. \\'triple\\'\n \\-\\- g :: Monad m => b -> 'Producer' c m ()  -- i.e. \\'(lift . putStrLn)\\'\n\n\\ for (for s f) g = for s (\\\\x -> for (f x) g)\n@\n\n    We can understand the rationale behind this equality if we first define the\n    following operator that is the point-free counterpart to 'for':\n\n@\n (~>) :: Monad m\n      => (a -> 'Producer' b m ())\n      -> (b -> 'Producer' c m ())\n      -> (a -> 'Producer' c m ())\n (f ~> g) x = for (f x) g\n@\n\n    Using ('~>') (pronounced \\\"into\\\"), we can transform our original equality\n    into the following more symmetric equation:\n\n@\n f :: Monad m => a -> 'Producer' b m ()\n g :: Monad m => b -> 'Producer' c m ()\n h :: Monad m => c -> 'Producer' d m ()\n\n\\ \\-\\- Associativity\n (f ~> g) ~> h = f ~> (g ~> h)\n@\n\n    This looks just like an associativity law.  In fact, ('~>') has another nice\n    property, which is that 'yield' is its left and right identity:\n\n> -- Left Identity\n> yield ~> f = f\n\n> -- Right Identity\n> f ~> yield = f\n\n    In other words, 'yield' and ('~>') form a 'Category', specifically the\n    generator category, where ('~>') plays the role of the composition operator\n    and 'yield' is the identity.  If you don't know what a 'Category' is, that's\n    okay, and category theory is not a prerequisite for using @pipes@.  All you\n    really need to know is that @pipes@ uses some simple category theory to keep\n    the API intuitive and easy to use.\n\n    Notice that if we translate the left identity law to use 'for' instead of\n    ('~>') we get:\n\n> for (yield x) f = f x\n\n    This just says that if you iterate over a pure single-element 'Producer',\n    then you could instead cut out the middle man and directly apply the body of\n    the loop to that single element.\n\n    If we translate the right identity law to use 'for' instead of ('~>') we\n    get:\n\n> for s yield = s\n\n    This just says that if the only thing you do is re-'yield' every element of\n    a stream, you get back your original stream.\n\n    These three \\\"for loop\\\" laws summarize our intuition for how 'for' loops\n    should behave and because these are 'Category' laws in disguise that means\n    that 'Producer's are composable in a rigorous sense of the word.\n\n    In fact, we get more out of this than just a bunch of equations.  We also\n    get a useful operator: ('~>').  We can use this operator to condense\n    our original code into the following more succinct form that composes two\n    transformations:\n\n> main = runEffect $ for P.stdinLn (triple ~> lift . putStrLn)\n\n    This means that we can also choose to program in a more functional style and\n    think of stream processing in terms of composing transformations using\n    ('~>') instead of nesting a bunch of 'for' loops.\n\n    The above example is a microcosm of the design philosophy behind the @pipes@\n    library:\n\n    * Define the API in terms of categories\n\n    * Specify expected behavior in terms of category laws\n\n    * Think compositionally instead of sequentially\n-}\n\n{- $consumers\n    Sometimes you don't want to use a 'for' loop because you don't want to consume\n    every element of a 'Producer' or because you don't want to process every\n    value of a 'Producer' the exact same way.\n\n    The most general solution is to externally iterate over the 'Producer' using\n    the 'next' command:\n\n@\n 'next' :: 'Monad' m => 'Producer' a m r -> m ('Either' r (a, 'Producer' a m r))\n@\n\n    Think of 'next' as pattern matching on the head of the 'Producer'.  This\n    'Either' returns a 'Left' if the 'Producer' is done or it returns a 'Right'\n    containing the next value, @a@, along with the remainder of the 'Producer'.\n\n    However, sometimes we can get away with something a little more simple and\n    elegant, like a 'Consumer', which represents an effectful sink of values.  A\n    'Consumer' is a monad transformer that extends the base monad with a new\n    'await' command. This 'await' command lets you receive input from an\n    anonymous upstream source.\n\n    The following @stdoutLn@ 'Consumer' shows how to incrementally 'await'\n    'String's and print them to standard output, terminating gracefully when\n    receiving a broken pipe error:\n\n> import Control.Monad (unless)\n> import Control.Exception (try, throwIO)\n> import qualified GHC.IO.Exception as G\n> import Pipes\n>\n> --          +--------+-- A 'Consumer' that awaits 'String's\n> --          |        |\n> --          v        v\n> stdoutLn :: Consumer String IO ()\n> stdoutLn = do\n>     str <- await  -- 'await' a 'String'\n>     x   <- lift $ try $ putStrLn str\n>     case x of\n>         -- Gracefully terminate if we got a broken pipe error\n>         Left e@(G.IOError { G.ioe_type = t}) ->\n>             lift $ unless (t == G.ResourceVanished) $ throwIO e\n>         -- Otherwise loop\n>         Right () -> stdoutLn\n\n    'await' is the dual of 'yield': we suspend our 'Consumer' until we receive a\n    new value.  If nobody provides a value (which is possible) then 'await'\n    never returns.  You can think of 'await' as having the following type:\n\n@\n 'await' :: 'Monad' m => 'Consumer' a m a\n@\n\n    One way to feed a 'Consumer' is to repeatedly feed the same input using\n    ('>~') (pronounced \\\"feed\\\"):\n\n@\n \\-\\-                 +- Feed       +- Consumer to    +- Returns new\n \\-\\-                 |  action     |  feed           |  Effect\n \\-\\-                 v             v                 v  \n \\-\\-                 ----------    --------------    ----------\n ('>~') :: 'Monad' m => 'Effect' m b -> 'Consumer' b m c -> 'Effect' m c\n@\n\n    @(draw >~ consumer)@ loops over @(consumer)@, substituting each 'await' in\n    @(consumer)@ with @(draw)@.\n\n    So the following code replaces every 'await' in 'P.stdoutLn' with\n    @(lift getLine)@ and then removes all the 'lift's:\n\n>>> runEffect $ lift getLine >~ stdoutLn\nTest<Enter>\nTest\nABC<Enter>\nABC\n42<Enter>\n42\n...\n\n    You might wonder why ('>~') uses an 'Effect' instead of a raw action in the\n    base monad.  The reason why is that ('>~') actually permits the following\n    more general type:\n\n@\n ('>~') :: 'Monad' m => 'Consumer' a m b -> 'Consumer' b m c -> 'Consumer' a m c\n@\n\n    ('>~') is the dual of ('~>'), composing 'Consumer's instead of 'Producer's.\n\n    This means that you can feed a 'Consumer' with yet another 'Consumer' so\n    that you can 'await' while you 'await'.  For example, we could define the\n    following intermediate 'Consumer' that requests two 'String's and returns\n    them concatenated:\n\n> doubleUp :: Monad m => Consumer String m String\n> doubleUp = do\n>     str1 <- await\n>     str2 <- await\n>     return (str1 ++ str2)\n>\n> -- more concise: doubleUp = (++) <$> await <*> await\n\n    We can now insert this in between @(lift getLine)@ and @stdoutLn@ and see\n    what happens:\n\n>>> runEffect $ lift getLine >~ doubleUp >~ stdoutLn\nTest<Enter>\ning<Enter>\nTesting\nABC<Enter>\nDEF<Enter>\nABCDEF\n42<Enter>\n000<Enter>\n42000\n...\n\n    'doubleUp' splits every request from 'stdoutLn' into two separate requests\n    and\n    returns back the concatenated result.\n\n    We didn't need to parenthesize the above chain of ('>~') operators, because\n    ('>~') is associative:\n\n> -- Associativity\n> (f >~ g) >~ h = f >~ (g >~ h)\n\n    ... so we can always omit the parentheses since the meaning is unambiguous:\n\n> f >~ g >~ h\n\n    Also, ('>~') has an identity, which is 'await'!\n\n> -- Left identity\n> await >~ f = f\n>\n> -- Right Identity\n> f >~ await = f\n\n    In other words, ('>~') and 'await' form a 'Category', too, specifically the\n    iteratee category, and 'Consumer's are also composable.\n-}\n\n{- $pipes\n    Our previous programs were unsatisfactory because they were biased either\n    towards the 'Producer' end or the 'Consumer' end.  As a result, we had to\n    choose between gracefully handling end of input (using 'P.stdinLn') or\n    gracefully handling end of output (using 'P.stdoutLn'), but not both at the\n    same time.\n\n    However, we don't need to restrict ourselves to using 'Producer's\n    exclusively or 'Consumer's exclusively.  We can connect 'Producer's and\n    'Consumer's directly together using ('>->') (pronounced \\\"pipe\\\"):\n\n@\n ('>->') :: 'Monad' m => 'Producer' a m r -> 'Consumer' a m r -> 'Effect' m r\n@\n\n    This returns an 'Effect' which we can run:\n\n> -- echo2.hs\n>\n> import Pipes\n> import qualified Pipes.Prelude as P  -- Pipes.Prelude also provides 'stdoutLn'\n>\n> main = runEffect $ P.stdinLn >-> P.stdoutLn\n\n    This program is more declarative of our intent: we want to stream values\n    from 'P.stdinLn' to 'P.stdoutLn'.  The above \\\"pipeline\\\" not only echoes\n    standard input to standard output, but also handles both end of input and\n    broken pipe errors:\n\n> $ ./echo2\n> Test<Enter>\n> Test\n> ABC<Enter>\n> ABC\n> 42<Enter>\n> 42\n> <Ctrl-D>\n> $\n\n    ('>->') is \\\"pull-based\\\" meaning that control flow begins at the most\n    downstream component (i.e. 'P.stdoutLn' in the above example).  Any time a\n    component 'await's a value it blocks and transfers control upstream and\n    every time a component 'yield's a value it blocks and restores control back\n    downstream, satisfying the 'await'.  So in the above example, ('>->')\n    matches every 'await' from 'P.stdoutLn' with a 'yield' from 'P.stdinLn'.\n\n    Streaming stops when either 'P.stdinLn' terminates (i.e. end of input) or\n    'P.stdoutLn' terminates (i.e. broken pipe).  This is why ('>->') requires\n    that both the 'Producer' and 'Consumer' share the same type of return value:\n    whichever one terminates first provides the return value for the entire\n    'Effect'.\n\n    Let's test this by modifying our 'Producer' and 'Consumer' to each return a\n    diagnostic 'String':\n\n> -- echo3.hs\n>\n> import Control.Applicative ((<$))  -- (<$) modifies return values\n> import Pipes\n> import qualified Pipes.Prelude as P\n> import System.IO\n>\n> main = do\n>     hSetBuffering stdout NoBuffering\n>     str <- runEffect $\n>         (\"End of input!\" <$ P.stdinLn) >-> (\"Broken pipe!\" <$ P.stdoutLn)\n>     hPutStrLn stderr str\n\n    This lets us diagnose whether the 'Producer' or 'Consumer' terminated first:\n\n> $ ./echo3\n> Test<Enter>\n> Test\n> <Ctrl-D>\n> End of input!\n> $ ./echo3 | perl -e 'close STDIN'\n> Test<Enter>\n> Broken pipe!\n> $\n\n    You might wonder why ('>->') returns an 'Effect' that we have to run instead\n    of directly returning an action in the base monad.  This is because you can\n    connect things other than 'Producer's and 'Consumer's, like 'Pipe's, which\n    are effectful stream transformations.\n\n    A 'Pipe' is a monad transformer that is a mix between a 'Producer' and\n    'Consumer', because a 'Pipe' can both 'await' and 'yield'.  The following\n    example 'Pipe' is analogous to the Prelude's 'take', only allowing a fixed\n    number of values to flow through:\n\n> -- take.hs\n>\n> import Control.Monad (replicateM_)\n> import Pipes\n> import Prelude hiding (take)\n>\n> --              +--------- A 'Pipe' that\n> --              |    +---- 'await's 'a's and\n> --              |    | +-- 'yield's 'a's\n> --              |    | |\n> --              v    v v\n> take ::  Int -> Pipe a a IO ()\n> take n = do\n>     replicateM_ n $ do                     -- Repeat this block 'n' times\n>         x <- await                         -- 'await' a value of type 'a'\n>         yield x                            -- 'yield' a value of type 'a'\n>     lift $ putStrLn \"You shall not pass!\"  -- Fly, you fools!\n\n    You can use 'Pipe's to transform 'Producer's, 'Consumer's, or even other\n    'Pipe's using the same ('>->') operator:\n\n@\n ('>->') :: 'Monad' m => 'Producer' a m r -> 'Pipe'   a b m r -> 'Producer' b m r\n ('>->') :: 'Monad' m => 'Pipe'   a b m r -> 'Consumer' b m r -> 'Consumer' a m r\n ('>->') :: 'Monad' m => 'Pipe'   a b m r -> 'Pipe'   b c m r -> 'Pipe'   a c m r\n@\n\n    For example, you can compose 'P.take' after 'P.stdinLn' to limit the number\n    of lines drawn from standard input:\n\n> maxInput :: Int -> Producer String IO ()\n> maxInput n = P.stdinLn >-> take n\n\n>>> runEffect $ maxInput 3 >-> P.stdoutLn\nTest<Enter>\nTest\nABC<Enter>\nABC\n42<Enter>\n42\nYou shall not pass!\n>>>\n\n    ... or you can pre-compose 'P.take' before 'P.stdoutLn' to limit the number\n    of lines written to standard output:\n\n> maxOutput :: Int -> Consumer String IO ()\n> maxOutput n = take n >-> P.stdoutLn\n\n>>> runEffect $ P.stdinLn >-> maxOutput 3\n<Exact same behavior>\n\n    Those both gave the same behavior because ('>->') is associative:\n\n> (p1 >-> p2) >-> p3 = p1 >-> (p2 >-> p3)\n\n    Therefore we can just leave out the parentheses:\n\n>>> runEffect $ P.stdinLn >-> take 3 >-> P.stdoutLn\n<Exact same behavior>\n\n    ('>->') is designed to behave like the Unix pipe operator, except with less\n    quirks.  In fact, we can continue the analogy to Unix by defining 'cat'\n    (named after the Unix @cat@ utility), which reforwards elements endlessly:\n\n> cat :: Monad m => Pipe a a m r\n> cat = forever $ do\n>     x <- await\n>     yield x\n\n     'cat' is the identity of ('>->'), meaning that 'cat' satisfies the\n     following two laws:\n\n> -- Useless use of 'cat'\n> cat >-> p = p\n>\n> -- Forwarding output to 'cat' does nothing\n> p >-> cat = p\n\n    Therefore, ('>->') and 'cat' form a 'Category', specifically the category of\n    Unix pipes, and 'Pipe's are also composable.\n\n    A lot of Unix tools have very simple definitions when written using @pipes@:\n\n> -- unix.hs\n>\n> import Control.Monad (forever)\n> import Pipes\n> import qualified Pipes.Prelude as P  -- Pipes.Prelude provides 'take', too\n> import Prelude hiding (head)\n>\n> head :: Monad m => Int -> Pipe a a m ()\n> head = P.take\n>\n> yes :: Monad m => Producer String m r\n> yes = forever $ yield \"y\"\n>\n> main = runEffect $ yes >-> head 3 >-> P.stdoutLn\n\n    This prints out 3 \\'@y@\\'s, just like the equivalent Unix pipeline:\n\n> $ ./unix\n> y\n> y\n> y\n> $ yes | head -3\n> y\n> y\n> y\n> $\n\n    This lets us write \\\"Haskell pipes\\\" instead of Unix pipes.  These are much\n    easier to build than Unix pipes and we can connect them directly within\n    Haskell for interoperability with the Haskell language and ecosystem.\n-}\n\n{- $listT\n    @pipes@ also provides a \\\"ListT done right\\\" implementation.  This differs\n    from the implementation in @transformers@ because this 'ListT':\n\n    * obeys the monad laws, and\n\n    * streams data immediately instead of collecting all results into memory.\n\n    The latter property is actually an elegant consequence of obeying the monad\n    laws.\n\n    To bind a list within a 'ListT' computation, combine 'Select' and 'each':\n\n> import Pipes\n> \n> pair :: ListT IO (Int, Int)\n> pair = do\n>     x <- Select $ each [1, 2]\n>     lift $ putStrLn $ \"x = \" ++ show x\n>     y <- Select $ each [3, 4]\n>     lift $ putStrLn $ \"y = \" ++ show y\n>     return (x, y)\n\n    You can then loop over a 'ListT' by using 'every':\n\n@\n 'every' :: 'Monad' m => 'ListT' m a -> 'Producer' a m ()\n@\n\n    So you can use your 'ListT' within a 'for' loop:\n\n>>> runEffect $ for (every pair) (lift . print)\nx = 1\ny = 3\n(1,3)\ny = 4\n(1,4)\nx = 2\ny = 3\n(2,3)\ny = 4\n(2,4)\n\n    ... or a pipeline:\n\n>>> import qualified Pipes.Prelude as P\n>>> runEffect $ every pair >-> P.print\n<Exact same behavior>\n\n    Note that 'ListT' is lazy and only produces as many elements as we request:\n\n>>> runEffect $ for (every pair >-> P.take 2) (lift . print)\nx = 1\ny = 3\n(1,3)\ny = 4\n(1,4)\n\n    You can also go the other way, binding 'Producer's directly within a\n    'ListT'.  In fact, this is actually what 'Select' was already doing:\n\n@\n 'Select' :: 'Producer' a m () -> 'ListT' m a\n@\n\n    This lets you write crazy code like:\n\n> import Pipes\n> import qualified Pipes.Prelude as P\n> \n> input :: Producer String IO ()\n> input = P.stdinLn >-> P.takeWhile (/= \"quit\")\n> \n> name :: ListT IO String\n> name = do\n>     firstName <- Select input\n>     lastName  <- Select input\n>     return (firstName ++ \" \" ++ lastName)\n\n    Here we're binding standard input non-deterministically (twice) as if it\n    were an effectful list:\n\n>>> runEffect $ every name >-> P.stdoutLn\nDaniel<Enter>\nFischer<Enter>\nDaniel Fischer\nWagner<Enter>\nDaniel Wagner\nquit<Enter>\nDonald<Enter>\nStewart<Enter>\nDonald Stewart\nDuck<Enter>\nDonald Duck\nquit<Enter>\nquit<Enter>\n>>>\n\n    Notice how this streams out values immediately as they are generated, rather\n    than building up a large intermediate result and then printing all the\n    values in one batch at the end.\n\n    `ListT` computations can be combined in more ways than `Pipe`s, so try to\n    program in `ListT` as much as possible and defer converting it to a `Pipe`\n    as late as possible using `P.loop`.\n\n    You can combine `ListT` computations even if their inputs and outputs are\n    completely different:\n\n> data In\n>     = InA A\n>     | InB B\n>     | InC C\n>\n> data Out\n>     = OutD D\n>     | OutE E\n>     | OutF F\n>\n> -- Independent computations\n>\n> example1 :: A -> ListT IO D\n> example2 :: B -> ListT IO E\n> example3 :: C -> ListT IO F\n>\n> -- Combined computation\n>\n> total :: In -> ListT IO Out\n> total input = case input of\n>     InA a -> fmap OutD (example1 a)\n>     InB b -> fmap OutE (example2 b)\n>     InC c -> fmap OutF (example3 c)\n\n    Sometimes you have multiple computations that handle different inputs but\n    the same output, in which case you don't need to unify their outputs:\n\n> -- Overlapping outputs\n>\n> example1 :: A -> ListT IO Out\n> example2 :: B -> ListT IO Out\n> example3 :: C -> ListT IO Out\n>\n> -- Combined computation\n>\n> total :: In -> ListT IO Out\n> total input = case input of\n>     InA a -> example1 a\n>     InB b -> example2 b\n>     InC c -> example3 c\n\n    Other times you have multiple computations that handle the same input but\n    produce different outputs.  You can unify their outputs using the `Monoid`\n    and `Functor` instances for `ListT`:\n\n> -- Overlapping inputs\n>\n> example1 :: In -> ListT IO D\n> example2 :: In -> ListT IO E\n> example3 :: In -> ListT IO F\n>\n> -- Combined computation\n>\n> total :: In -> ListT IO Out\n> total input =\n>        fmap OutD (example1 input)\n>     <> fmap OutE (example2 input)\n>     <> fmap OutF (example3 input)\n\n    You can also chain `ListT` computations, feeding the output of the first\n    computation as the input to the next computation:\n\n> -- End-to-end\n>\n> aToB :: A -> ListT IO B\n> bToC :: B -> ListT IO C\n>\n> -- Combined computation\n>\n> aToC :: A -> LIstT IO C\n> aToC = aToB >=> bToC\n\n    ... or you can just use @do@ notation if you prefer.\n\n    However, the `Pipe` type is more general than `ListT` and can represent\n    things like termination.  Therefore you should consider mixing `Pipe`s with\n    `ListT` when you need to take advantage of these extra features:\n\n> -- Mix ListT with Pipes\n>\n> example :: In -> ListT IO Out\n>\n> pipe :: Pipe In Out IO ()\n> pipe = Pipes.takeWhile (not . isC) >-> loop example\n>   where\n>     isC (InC _) = True\n>     isC  _      = False\n\n    So promote your `ListT` logic to a `Pipe` when you need to take advantage of\n    these `Pipe`-specific features.\n-}\n\n{- $tricks\n    @pipes@ is more powerful than meets the eye so this section presents some\n    non-obvious tricks you may find useful.\n\n    Many pipe combinators will work on unusual pipe types and the next few\n    examples will use the 'cat' pipe to demonstrate this.\n\n    For example, you can loop over the output of a 'Pipe' using 'for', which is\n    how 'P.map' is defined:\n\n> map :: Monad m => (a -> b) -> Pipe a b m r\n> map f = for cat $ \\x -> yield (f x)\n>\n> -- Read this as: For all values flowing downstream, apply 'f'\n\n    This is equivalent to:\n\n> map f = forever $ do\n>     x <- await\n>     yield (f x)\n\n    You can also feed a 'Pipe' input using ('>~').  This means we could have\n    instead defined the @yes@ pipe like this:\n\n> yes :: Monad m => Producer String m r\n> yes = return \"y\" >~ cat\n>\n> -- Read this as: Keep feeding \"y\" downstream\n\n    This is equivalent to:\n\n> yes = forever $ yield \"y\"\n\n    You can also sequence two 'Pipe's together.  This is how 'P.drop' is\n    defined:\n\n> drop :: Monad m => Int -> Pipe a a m r\n> drop n = do\n>     replicateM_ n await\n>     cat\n\n    This is equivalent to:\n\n> drop n = do\n>     replicateM_ n await\n>     forever $ do\n>         x <- await\n>         yield x\n\n    You can even compose pipes inside of another pipe:\n\n> customerService :: Producer String IO ()\n> customerService = do\n>     each [ \"Hello, how can I help you?\"        -- Begin with a script\n>          , \"Hold for one second.\"\n>          ]\n>     P.stdinLn >-> P.takeWhile (/= \"Goodbye!\")  -- Now continue with a human\n\n    Also, you can often use 'each' in conjunction with ('~>') to traverse nested\n    data structures.  For example, you can print all non-'Nothing' elements\n    from a doubly-nested list:\n\n>>> runEffect $ (each ~> each ~> each ~> lift . print) [[Just 1, Nothing], [Just 2, Just 3]]\n1\n2\n3\n\n    Another neat thing to know is that 'every' has a more general type:\n\n@\n 'every' :: ('Monad' m, 'Enumerable' t) => t m a -> 'Producer' a m ()\n@\n\n    'Enumerable' generalizes 'Foldable' and if you have an effectful container\n    of your own that you want others to traverse using @pipes@, just have your\n    container implement the 'toListT' method of the 'Enumerable' class:\n\n> class Enumerable t where\n>     toListT :: Monad m => t m a -> ListT m a\n\n    You can even use 'Enumerable' to traverse effectful types that are not even\n    proper containers, like 'Control.Monad.Trans.Maybe.MaybeT':\n\n> input :: MaybeT IO String\n> input = do\n>     str <- lift getLine\n>     guard (str /= \"Fail\")\n>     return str\n\n>>> runEffect $ every input >-> P.stdoutLn\nTest<Enter>\nTest\n>>> runEffect $ every input >-> P.stdoutLn\nFail<Enter>\n>>>\n\n-}\n\n{- $conclusion\n    This tutorial covers the concepts of connecting, building, and reading\n    @pipes@ code.  However, this library is only the core component in an\n    ecosystem of streaming components.  Derived libraries that build immediately\n    upon @pipes@ include:\n\n    * @pipes-concurrency@: Concurrent reactive programming and message passing\n\n    * @pipes-parse@: Minimal utilities for stream parsing\n\n    * @pipes-safe@: Resource management and exception safety for @pipes@\n\n    * @pipes-group@: Grouping streams in constant space\n\n    These libraries provide functionality specialized to common streaming\n    domains.  Additionally, there are several libraries on Hackage that provide\n    even higher-level functionality, which you can find by searching under the\n    \\\"Pipes\\\" category or by looking for packages with a @pipes-@ prefix in\n    their name.  Current examples include:\n\n    * @pipes-extras@: Miscellaneous utilities\n\n    * @pipes-network@/@pipes-network-tls@: Networking\n\n    * @pipes-zlib@: Compression and decompression\n\n    * @pipes-binary@: Binary serialization\n\n    * @pipes-attoparsec@: High-performance parsing\n\n    * @pipes-aeson@: JSON serialization and deserialization\n\n    Even these derived packages still do not explore the full potential of\n    @pipes@ functionality, which actually permits bidirectional communication.\n    Advanced @pipes@ users can explore this library in greater detail by\n    studying the documentation in the \"Pipes.Core\" module to learn about the\n    symmetry of the underlying 'Proxy' type and operators.\n\n    To learn more about @pipes@, ask questions, or follow @pipes@ development,\n    you can subscribe to the @haskell-pipes@ mailing list at:\n\n    <https://groups.google.com/forum/#!forum/haskell-pipes>\n\n    ... or you can mail the list directly at:\n\n    <mailto:haskell-pipes@googlegroups.com>\n\n    Additionally, for questions regarding types or type errors, you might find\n    the following appendix on types very useful.\n-}\n\n{- $types\n    @pipes@ uses parametric polymorphism (i.e. generics) to overload all\n    operations.  You've probably noticed this overloading already:\n\n    * 'yield' works within both 'Producer's and 'Pipe's\n\n    * 'await' works within both 'Consumer's and 'Pipe's\n\n    * ('>->') connects 'Producer's, 'Consumer's, and 'Pipe's in varying ways\n\n    This overloading is great when it works, but when connections fail they\n    produce type errors that appear intimidating at first.  This section\n    explains the underlying types so that you can work through type errors\n    intelligently.\n\n    'Producer's, 'Consumer's, 'Pipe's, and 'Effect's are all special cases of a\n    single underlying type: a 'Proxy'.  This overarching type permits fully\n    bidirectional communication on both an upstream and downstream interface.\n    You can think of it as having the following shape:\n\n> Proxy a' a b' b m r\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n> a' <==       <== b'  -- Information flowing upstream\n>     |         |\n> a  ==>       ==> b   -- Information flowing downstream\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    The four core types do not use the upstream flow of information.  This means\n    that the @a'@ and @b'@ in the above diagram go unused unless you use the\n    more advanced features provided in \"Pipes.Core\".\n\n    @pipes@ uses type synonyms to hide unused inputs or outputs and clean up\n    type signatures.  These type synonyms come in two flavors:\n\n    * Concrete type synonyms that explicitly close unused inputs and outputs of\n      the 'Proxy' type\n\n    * Polymorphic type synonyms that don't explicitly close unused inputs or\n      outputs\n\n    The concrete type synonyms use @()@ to close unused inputs and 'X' (the\n    uninhabited type) to close unused outputs:\n\n    * 'Effect': explicitly closes both ends, forbidding 'await's and 'yield's\n\n> type Effect = Proxy X () () X\n>\n>  Upstream | Downstream\n>     +---------+\n>     |         |\n> X  <==       <== ()\n>     |         |\n> () ==>       ==> X\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    * 'Producer': explicitly closes the upstream end, forbidding 'await's\n\n> type Producer b = Proxy X () () b\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n> X  <==       <== ()\n>     |         |\n> () ==>       ==> b\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    * 'Consumer': explicitly closes the downstream end, forbidding 'yield's\n\n> type Consumer a = Proxy () a () X\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n> () <==       <== ()\n>     |         |\n> a  ==>       ==> X\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    * 'Pipe': marks both ends open, allowing both 'await's and 'yield's\n\n> type Pipe a b = Proxy () a () b\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n> () <==       <== ()\n>     |         |\n> a  ==>       ==> b\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    When you compose 'Proxy's using ('>->') all you are doing is placing them\n    side by side and fusing them laterally.  For example, when you compose a\n    'Producer', 'Pipe', and a 'Consumer', you can think of information flowing\n    like this:\n\n>        Producer                Pipe                 Consumer\n>     +-----------+          +----------+          +------------+\n>     |           |          |          |          |            |\n> X  <==         <==   ()   <==        <==   ()   <==          <== ()\n>     |  stdinLn  |          |  take 3  |          |  stdoutLn  |\n> () ==>         ==> String ==>        ==> String ==>          ==> X\n>     |     |     |          |    |     |          |      |     |\n>     +-----|-----+          +----|-----+          +------|-----+\n>           v                     v                       v\n>           ()                    ()                      ()\n\n     Composition fuses away the intermediate interfaces, leaving behind an\n     'Effect':\n\n>                    Effect\n>     +-----------------------------------+\n>     |                                   |\n> X  <==                                 <== ()\n>     |  stdinLn >-> take 3 >-> stdoutLn  |\n> () ==>                                 ==> X\n>     |                                   |\n>     +----------------|------------------+\n>                      v\n>                      ()\n\n    @pipes@ also provides polymorphic type synonyms with apostrophes at the end\n    of their names.  These use universal quantification to leave open any unused\n    input or output ends (which I mark using @*@):\n\n    * 'Producer'': marks the upstream end unused but still open\n\n> type Producer' b m r = forall x' x . Proxy x' x () b m r\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n>  * <==       <== ()\n>     |         |\n>  * ==>       ==> b\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    * 'Consumer'': marks the downstream end unused but still open\n\n> type Consumer' a m r = forall y' y . Proxy () a y' y m r\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n> () <==       <== * \n>     |         |\n> a  ==>       ==> *\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    * 'Effect'': marks both ends unused but still open\n\n> type Effect' m r = forall x' x y' y . Proxy x' x y' y m r\n>\n> Upstream | Downstream\n>     +---------+\n>     |         |\n>  * <==       <== * \n>     |         |\n>  * ==>       ==> *\n>     |    |    |\n>     +----|----+\n>          v\n>          r\n\n    Note that there is no polymorphic generalization of a 'Pipe'.\n\n    Like before, if you compose a 'Producer'', a 'Pipe', and a 'Consumer'':\n\n>        Producer'               Pipe                 Consumer'\n>     +-----------+          +----------+          +------------+\n>     |           |          |          |          |            |\n>  * <==         <==   ()   <==        <==   ()   <==          <== *\n>     |  stdinLn  |          |  take 3  |          |  stdoutLn  |\n>  * ==>         ==> String ==>        ==> String ==>          ==> *\n>     |     |     |          |     |    |          |      |     |\n>     +-----|-----+          +-----|----+          +------|-----+\n>           v                      v                      v\n>           ()                     ()                     ()\n\n    ... they fuse into an 'Effect'':\n\n>                    Effect'\n>     +-----------------------------------+\n>     |                                   |\n>  * <==                                 <== *\n>     |  stdinLn >-> take 3 >-> stdoutLn  |\n>  * ==>                                 ==> *\n>     |                                   |\n>     +----------------|------------------+\n>                      v\n>                      ()\n\n    Polymorphic type synonyms come in handy when you want to keep the type as\n    general as possible.  For example, the type signature for 'yield' uses\n    'Producer'' to keep the type signature simple while still leaving the\n    upstream input end open:\n\n@\n 'yield' :: 'Monad' m => a -> 'Producer'' a m ()\n@\n\n    This type signature lets us use 'yield' within a 'Pipe', too, because the\n    'Pipe' type synonym is a special case of the polymorphic 'Producer'' type \n    synonym:\n\n@\n type 'Producer'' b m r = forall x' x . 'Proxy' x' x () b m r\n type 'Pipe'    a b m r =               'Proxy' () a () b m r\n@\n\n    The same is true for 'await', which uses the polymorphic 'Consumer'' type\n    synonym:\n\n@\n 'await' :: 'Monad' m => 'Consumer'' a m a\n@\n\n    We can use 'await' within a 'Pipe' because a 'Pipe' is a special case of the\n    polymorphic 'Consumer'' type synonym:\n\n@\n type 'Consumer'' a   m r = forall y' y . 'Proxy' () a y' y m r\n type 'Pipe'      a b m r =               'Proxy' () a () b m r\n@\n\n    However, polymorphic type synonyms cause problems in many other cases:\n\n    * They usually give the wrong behavior when used as the argument of a\n      function (known as the \\\"negative\\\" or \\\"contravariant\\\" position) like\n      this:\n\n> f :: Producer' a m r -> ...  -- Wrong\n>\n> f :: Producer  a m r -> ...  -- Right\n\n      The former function only accepts polymorphic 'Producer's as arguments.\n      The latter function accepts both polymorphic and concrete 'Producer's,\n      which is probably what you want.\n\n    * Even when you desire a polymorphic argument, this induces a higher-ranked\n      type, because it translates to a @forall@ which you cannot factor out to\n      the top-level to simplify the type signature:\n\n> f :: (forall x' x y' . Proxy x' x y' m r) -> ...\n\n      These kinds of type signatures require the @RankNTypes@ extension.\n\n    * Even when you have polymorphic type synonyms as the result of a function\n      (i.e.  the \\\"positive\\\" or \\\"covariant\\\" position), recent versions of\n      @ghc@ such still require the @RankNTypes@ extension.  For example, the\n      'Pipes.Prelude.fromHandle' function from \"Pipes.Prelude\" requires\n      @RankNTypes@ to compile correctly on @ghc-7.6.3@:\n\n> fromHandle :: MonadIO m => Handle -> Producer' String m ()\n\n    * You can't use polymorphic type synonyms inside other type constructors\n      without the @ImpredicativeTypes@ extension:\n\n> io :: IO (Producer' a m r)  -- Type error without ImpredicativeTypes\n\n    * You can't partially apply polymorphic type synonyms:\n\n> stack :: MaybeT (Producer' a m) r  -- Type error\n\n    In these scenarios you should fall back on the concrete type synonyms, which\n    are better behaved.  If concrete type synonyms are unsatisfactory, then ask\n    @ghc@ to infer the most general type signature and use that.\n\n    For the purposes of debugging type errors you can just remember that:\n\n>  Input --+    +-- Output\n>          |    |\n>          v    v\n> Proxy a' a b' b m r\n>       ^    ^\n>       |    |\n>       +----+-- Ignore these\n\n    For example, let's say that you try to run the 'P.stdinLn' 'Producer'.  This\n    produces the following type error:\n\n>>> runEffect P.stdinLn\n<interactive>:4:5:\n    Couldn't match expected type `X' with actual type `String'\n    Expected type: Effect m0 r0\n      Actual type: Proxy X () () String IO ()\n    In the first argument of `runEffect', namely `P.stdinLn'\n    In the expression: runEffect P.stdinLn\n\n    'runEffect' expects an 'Effect', which is equivalent to the following type:\n\n> Effect          IO () = Proxy X () () X      IO ()\n\n    ... but 'P.stdinLn' type-checks as a 'Producer', which has the following\n    type:\n\n> Producer String IO () = Proxy X () () String IO ()\n\n    The fourth type variable (the output) does not match.  For an 'Effect' this\n    type variable should be closed (i.e. 'X'), but 'P.stdinLn' has a 'String'\n    output, thus the type error:\n\n>    Couldn't match expected type `X' with actual type `String'\n\n    Any time you get type errors like these you can work through them by\n    expanding out the type synonyms and seeing which type variables do not\n    match.\n\n    You may also consult this table of type synonyms to more easily compare\n    them:\n\n> type Effect             = Proxy X  () () X\n> type Producer         b = Proxy X  () () b\n> type Consumer    a      = Proxy () a  () X\n> type Pipe        a    b = Proxy () a  () b\n>\n> type Server        b' b = Proxy X  () b' b \n> type Client   a' a      = Proxy a' a  () X\n>\n> type Effect'            m r = forall x' x y' y . Proxy x' x y' y m r\n> type Producer'        b m r = forall x' x      . Proxy x' x () b m r\n> type Consumer'   a      m r = forall      y' y . Proxy () a y' y m r\n>\n> type Server'       b' b m r = forall x' x      . Proxy x' x b' b m r\n> type Client'  a' a      m r = forall      y' y . Proxy a' a y' y m r\n\n-}\n\n{- $timecomplexity\n    There are three functions that give quadratic time complexity when used in\n    within @pipes@:\n\n    * 'sequence'\n\n    * 'replicateM'\n\n    * 'mapM'\n\n    For example, the time complexity of this code segment scales quadratically\n    with `n`:\n\n> import Control.Monad (replicateM)\n> import Pipes\n>\n> quadratic :: Int -> Consumer a m [a]\n> quadratic n = replicateM n await\n\n    These three functions are generally bad practice to use, because all three\n    of them correspond to \\\"ListT done wrong\\\", building a list in memory\n    instead of streaming results.\n\n    However, sometimes situations arise where one deliberately intends to build\n    a list in memory.  The solution is to use the \\\"codensity transformation\\\"\n    to transform the code to run with linear time complexity.  This involves:\n\n    * wrapping the code in the @Codensity@ monad transformer (from\n      @Control.Monad.Codensity@ module of the @kan-extensions@ package) using\n      'lift'\n\n    * applying 'sequence' \\/ 'replicateM' \\/ 'mapM'\n\n    * unwrapping the code using @lowerCodensity@\n\n    To illustrate this, we'd transform the above example to:\n\n> import Control.Monad.Codensity (lowerCodensity)\n> \n> linear :: Monad m => Int -> Consumer a m [a]\n> linear n = lowerCodensity $ replicateM n $ lift await\n\n    This will produce the exact same result, but in linear time.\n-}\n\n{- $copyright\n    This tutorial is licensed under a\n    <http://creativecommons.org/licenses/by/4.0/ Creative Commons Attribution 4.0 International License>\n-}\n"
  },
  {
    "path": "src/Pipes.hs",
    "content": "{-# LANGUAGE CPP                   #-}\n{-# LANGUAGE RankNTypes            #-}\n{-# LANGUAGE FlexibleInstances     #-}\n{-# LANGUAGE MultiParamTypeClasses #-}\n{-# LANGUAGE UndecidableInstances  #-}\n{-# LANGUAGE Trustworthy           #-}\n\n{-| This module is the recommended entry point to the @pipes@ library.\n\n    Read \"Pipes.Tutorial\" if you want a tutorial explaining how to use this\n    library.\n-}\n\nmodule Pipes (\n    -- * The Proxy Monad Transformer\n      Proxy\n    , X\n    , Effect\n    , Effect'\n    , runEffect\n\n    -- ** Producers\n    -- $producers\n    , Producer\n    , Producer'\n    , yield\n    , for\n    , (~>)\n    , (<~)\n\n    -- ** Consumers\n    -- $consumers\n    , Consumer\n    , Consumer'\n    , await\n    , (>~)\n    , (~<)\n\n    -- ** Pipes\n    -- $pipes\n    , Pipe\n    , cat\n    , (>->)\n    , (<-<)\n\n    -- * ListT\n    , ListT(..)\n    , runListT\n    , Enumerable(..)\n\n    -- * Utilities\n    , next\n    , each\n    , every\n    , discard\n\n    -- * Re-exports\n    -- $reexports\n    , module Control.Monad\n    , module Control.Monad.IO.Class\n    , module Control.Monad.Trans.Class\n    , module Control.Monad.Morph\n    , Foldable\n    ) where\n\nimport Control.Monad (void, MonadPlus(mzero, mplus))\nimport Control.Monad.Catch (MonadThrow(..), MonadCatch(..))\nimport Control.Monad.Except (MonadError(..))\nimport Control.Monad.Fail (MonadFail(..))\nimport Control.Monad.IO.Class (MonadIO(liftIO))\nimport Control.Monad.Reader (MonadReader(..))\nimport Control.Monad.State (MonadState(..))\nimport Control.Monad.Trans.Class (MonadTrans(lift))\nimport Control.Monad.Trans.Except (ExceptT, runExceptT)\nimport Control.Monad.Trans.Identity (IdentityT(runIdentityT))\nimport Control.Monad.Trans.Maybe (MaybeT(runMaybeT))\nimport Control.Monad.Writer (MonadWriter(..))\nimport Control.Monad.Zip (MonadZip(..))\nimport Pipes.Core\nimport Pipes.Internal (Proxy(..))\nimport qualified Data.Foldable as F\n\n#if MIN_VERSION_base(4,8,0)\nimport Control.Applicative (Alternative(..))\n#else\nimport Control.Applicative\nimport Data.Foldable (Foldable)\nimport Data.Traversable (Traversable(..))\n#endif\nimport Data.Semigroup\n\n-- Re-exports\nimport Control.Monad.Morph (MFunctor(hoist), MMonad(embed))\n\ninfixl 4 <~\ninfixr 4 ~>\ninfixl 5 ~<\ninfixr 5 >~\ninfixl 7 >->\ninfixr 7 <-<\n\n{- $producers\n    Use 'yield' to produce output and ('~>') \\/ 'for' to substitute 'yield's.\n\n    'yield' and ('~>') obey the 'Control.Category.Category' laws:\n\n@\n\\-\\- Substituting \\'yield\\' with \\'f\\' gives \\'f\\'\n'yield' '~>' f = f\n\n\\-\\- Substituting every \\'yield\\' with another \\'yield\\' does nothing\nf '~>' 'yield' = f\n\n\\-\\- \\'yield\\' substitution is associative\n(f '~>' g) '~>' h = f '~>' (g '~>' h)\n@\n\n    These are equivalent to the following \\\"for loop laws\\\":\n\n@\n\\-\\- Looping over a single yield simplifies to function application\n'for' ('yield' x) f = f x\n\n\\-\\- Re-yielding every element of a stream returns the original stream\n'for' s 'yield' = s\n\n\\-\\- Nested for loops can become a sequential 'for' loops if the inner loop\n\\-\\- body ignores the outer loop variable\n'for' s (\\\\a -\\> 'for' (f a) g) = 'for' ('for' s f) g = 'for' s (f '~>' g)\n@\n\n-}\n\n{-| Produce a value\n\n@\n'yield' :: 'Monad' m => a -> 'Producer' a m ()\n'yield' :: 'Monad' m => a -> 'Pipe'   x a m ()\n@\n-}\nyield :: Functor m => a -> Proxy x' x () a m ()\nyield = respond\n{-# INLINABLE [1] yield #-}\n\n{-| @(for p body)@ loops over @p@ replacing each 'yield' with @body@.\n\n@\n'for' :: 'Functor' m => 'Producer' b m r -> (b -> 'Effect'       m ()) -> 'Effect'       m r\n'for' :: 'Functor' m => 'Producer' b m r -> (b -> 'Producer'   c m ()) -> 'Producer'   c m r\n'for' :: 'Functor' m => 'Pipe'   x b m r -> (b -> 'Consumer' x   m ()) -> 'Consumer' x   m r\n'for' :: 'Functor' m => 'Pipe'   x b m r -> (b -> 'Pipe'     x c m ()) -> 'Pipe'     x c m r\n@\n\n    The following diagrams show the flow of information:\n\n@\n                              .--->   b\n                             /        |\n   +-----------+            /   +-----|-----+                 +---------------+\n   |           |           /    |     v     |                 |               |\n   |           |          /     |           |                 |               |\nx ==>    p    ==> b   ---'   x ==>   body  ==> c     =     x ==> 'for' p body  ==> c\n   |           |                |           |                 |               |\n   |     |     |                |     |     |                 |       |       |\n   +-----|-----+                +-----|-----+                 +-------|-------+\n         v                            v                               v\n         r                            ()                              r\n@\n\n    For a more complete diagram including bidirectional flow, see \"Pipes.Core#respond-diagram\".\n-}\nfor :: Functor m\n    =>       Proxy x' x b' b m a'\n    -- ^\n    -> (b -> Proxy x' x c' c m b')\n    -- ^\n    ->       Proxy x' x c' c m a'\nfor = (//>)\n-- There are a number of useful rewrites which can be performed on various uses\n-- of this combinator; to ensure that they fire we defer inlining until quite\n-- late.\n{-# INLINABLE [0] for #-}\n\n{-# RULES\n    \"for (for p f) g\" forall p f g . for (for p f) g = for p (\\a -> for (f a) g)\n\n  ; \"for p yield\" forall p . for p yield = p\n\n  ; \"for (yield x) f\" forall x f . for (yield x) f = f x\n\n  ; \"for cat f\" forall f .\n        for cat f =\n            let go = do\n                    x <- await\n                    f x\n                    go\n            in  go\n\n  ; \"f >~ (g >~ p)\" forall f g p . f >~ (g >~ p) = (f >~ g) >~ p\n\n  ; \"await >~ p\" forall p . await >~ p = p\n\n  ; \"p >~ await\" forall p . p >~ await = p\n\n  ; \"m >~ cat\" forall m .\n        m >~ cat =\n            let go = do\n                    x <- m\n                    yield x\n                    go\n            in  go\n\n  ; \"p1 >-> (p2 >-> p3)\" forall p1 p2 p3 .\n        p1 >-> (p2 >-> p3) = (p1 >-> p2) >-> p3\n\n  ; \"p >-> cat\" forall p . p >-> cat = p\n\n  ; \"cat >-> p\" forall p . cat >-> p = p\n\n  #-}\n\n{-| Compose loop bodies\n\n@\n('~>') :: 'Functor' m => (a -> 'Producer' b m r) -> (b -> 'Effect'       m ()) -> (a -> 'Effect'       m r)\n('~>') :: 'Functor' m => (a -> 'Producer' b m r) -> (b -> 'Producer'   c m ()) -> (a -> 'Producer'   c m r)\n('~>') :: 'Functor' m => (a -> 'Pipe'   x b m r) -> (b -> 'Consumer' x   m ()) -> (a -> 'Consumer' x   m r)\n('~>') :: 'Functor' m => (a -> 'Pipe'   x b m r) -> (b -> 'Pipe'     x c m ()) -> (a -> 'Pipe'     x c m r)\n@\n\n    The following diagrams show the flow of information:\n\n@\n         a                    .--->   b                              a\n         |                   /        |                              |\n   +-----|-----+            /   +-----|-----+                 +------|------+\n   |     v     |           /    |     v     |                 |      v      |\n   |           |          /     |           |                 |             |\nx ==>    f    ==> b   ---'   x ==>    g    ==> c     =     x ==>   f '~>' g  ==> c\n   |           |                |           |                 |             |\n   |     |     |                |     |     |                 |      |      |\n   +-----|-----+                +-----|-----+                 +------|------+\n         v                            v                              v\n         r                            ()                             r\n@\n\n    For a more complete diagram including bidirectional flow, see \"Pipes.Core#respond-diagram\".\n-}\n(~>)\n    :: Functor m\n    => (a -> Proxy x' x b' b m a')\n    -- ^\n    -> (b -> Proxy x' x c' c m b')\n    -- ^\n    -> (a -> Proxy x' x c' c m a')\n(~>) = (/>/)\n{-# INLINABLE (~>) #-}\n\n-- | ('~>') with the arguments flipped\n(<~)\n    :: Functor m\n    => (b -> Proxy x' x c' c m b')\n    -- ^\n    -> (a -> Proxy x' x b' b m a')\n    -- ^\n    -> (a -> Proxy x' x c' c m a')\ng <~ f = f ~> g\n{-# INLINABLE (<~) #-}\n\n{- $consumers\n    Use 'await' to request input and ('>~') to substitute 'await's.\n\n    'await' and ('>~') obey the 'Control.Category.Category' laws:\n\n@\n\\-\\- Substituting every \\'await\\' with another \\'await\\' does nothing\n'await' '>~' f = f\n\n\\-\\- Substituting \\'await\\' with \\'f\\' gives \\'f\\'\nf '>~' 'await' = f\n\n\\-\\- \\'await\\' substitution is associative\n(f '>~' g) '>~' h = f '>~' (g '>~' h)\n@\n\n-}\n\n{-| Consume a value\n\n@\n'await' :: 'Functor' m => 'Pipe' a y m a\n@\n-}\nawait :: Functor m => Consumer' a m a\nawait = request ()\n{-# INLINABLE [1] await #-}\n\n{-| @(draw >~ p)@ loops over @p@ replacing each 'await' with @draw@\n\n@\n('>~') :: 'Functor' m => 'Effect'       m b -> 'Consumer' b   m c -> 'Effect'       m c\n('>~') :: 'Functor' m => 'Consumer' a   m b -> 'Consumer' b   m c -> 'Consumer' a   m c\n('>~') :: 'Functor' m => 'Producer'   y m b -> 'Pipe'     b y m c -> 'Producer'   y m c\n('>~') :: 'Functor' m => 'Pipe'     a y m b -> 'Pipe'     b y m c -> 'Pipe'     a y m c\n@\n\n    The following diagrams show the flow of information:\n\n@\n   +-----------+                 +-----------+                 +-------------+\n   |           |                 |           |                 |             |\n   |           |                 |           |                 |             |\na ==>    f    ==> y   .--->   b ==>    g    ==> y     =     a ==>   f '>~' g  ==> y\n   |           |     /           |           |                 |             |\n   |     |     |    /            |     |     |                 |      |      |\n   +-----|-----+   /             +-----|-----+                 +------|------+\n         v        /                    v                              v\n         b   ----'                     c                              c\n@\n\n    For a more complete diagram including bidirectional flow, see \"Pipes.Core#request-diagram\".\n-}\n(>~)\n    :: Functor m\n    => Proxy a' a y' y m b\n    -- ^\n    -> Proxy () b y' y m c\n    -- ^\n    -> Proxy a' a y' y m c\np1 >~ p2 = (\\() -> p1) >\\\\ p2\n{-# INLINABLE [1] (>~) #-}\n\n-- | ('>~') with the arguments flipped\n(~<)\n    :: Functor m\n    => Proxy () b y' y m c\n    -- ^\n    -> Proxy a' a y' y m b\n    -- ^\n    -> Proxy a' a y' y m c\np2 ~< p1 = p1 >~ p2\n{-# INLINABLE (~<) #-}\n\n{- $pipes\n    Use 'await' and 'yield' to build 'Pipe's and ('>->') to connect 'Pipe's.\n\n    'cat' and ('>->') obey the 'Control.Category.Category' laws:\n\n@\n\\-\\- Useless use of cat\n'cat' '>->' f = f\n\n\\-\\- Redirecting output to cat does nothing\nf '>->' 'cat' = f\n\n\\-\\- The pipe operator is associative\n(f '>->' g) '>->' h = f '>->' (g '>->' h)\n@\n\n-}\n\n-- | The identity 'Pipe', analogous to the Unix @cat@ program\ncat :: Functor m => Pipe a a m r\ncat = pull ()\n{-# INLINABLE [1] cat #-}\n\n{-| 'Pipe' composition, analogous to the Unix pipe operator\n\n@\n('>->') :: 'Functor' m => 'Producer' b m r -> 'Consumer' b   m r -> 'Effect'       m r\n('>->') :: 'Functor' m => 'Producer' b m r -> 'Pipe'     b c m r -> 'Producer'   c m r\n('>->') :: 'Functor' m => 'Pipe'   a b m r -> 'Consumer' b   m r -> 'Consumer' a   m r\n('>->') :: 'Functor' m => 'Pipe'   a b m r -> 'Pipe'     b c m r -> 'Pipe'     a c m r\n@\n\n    The following diagrams show the flow of information:\n\n@\n   +-----------+     +-----------+                 +-------------+\n   |           |     |           |                 |             |\n   |           |     |           |                 |             |\na ==>    f    ==> b ==>    g    ==> c     =     a ==>  f '>->' g  ==> c\n   |           |     |           |                 |             |\n   |     |     |     |     |     |                 |      |      |\n   +-----|-----+     +-----|-----+                 +------|------+\n         v                 v                              v\n         r                 r                              r\n@\n\n    For a more complete diagram including bidirectional flow, see \"Pipes.Core#pull-diagram\".\n-}\n(>->)\n    :: Functor m\n    => Proxy a' a () b m r\n    -- ^\n    -> Proxy () b c' c m r\n    -- ^\n    -> Proxy a' a c' c m r\np1 >-> p2 = (\\() -> p1) +>> p2\n{-# INLINABLE [1] (>->) #-}\n\n{-| The list monad transformer, which extends a monad with non-determinism\n\n    The type variables signify:\n\n      * @m@ - The base monad\n      * @a@ - The values that the computation 'yield's throughout its execution\n\n    For basic construction and composition of 'ListT' computations, much can be\n    accomplished using common typeclass methods.\n\n      * 'return' corresponds to 'yield', yielding a single value.\n      * ('>>=') corresponds to 'for', calling the second computation once\n        for each time the first computation 'yield's.\n      * 'mempty' neither 'yield's any values nor produces any effects in the\n        base monad.\n      * ('<>') sequences two computations, 'yield'ing all the values of the\n        first followed by all the values of the second.\n      * 'lift' converts an action in the base monad into a ListT computation\n        which performs the action and 'yield's a single value.\n\n    'ListT' is a newtype wrapper for 'Producer'. You will likely need to use\n    'Select' and 'enumerate' to convert back and forth between these two types\n    to take advantage of all the 'Producer'-related utilities that\n    \"Pipes.Prelude\" has to offer.\n\n      * To lift a plain list into a 'ListT' computation, first apply 'each'\n        to turn the list into a 'Producer'. Then apply the 'Select'\n        constructor to convert from 'Producer' to 'ListT'.\n      * For other ways to construct 'ListT' computations, see the\n        “Producers” section in \"Pipes.Prelude\" to build 'Producer's.\n        These can then be converted to 'ListT' using 'Select'.\n      * To aggregate the values from a 'ListT' computation (for example,\n        to compute the sum of a 'ListT' of numbers), first apply\n        'enumerate' to obtain a 'Producer'. Then see the “Folds”\n        section in \"Pipes.Prelude\" to proceed.\n-}\nnewtype ListT m a = Select { enumerate :: Producer a m () }\n\ninstance Functor m => Functor (ListT m) where\n    fmap f p = Select (for (enumerate p) (\\a -> yield (f a)))\n    {-# INLINE fmap #-}\n\ninstance Functor m => Applicative (ListT m) where\n    pure a = Select (yield a)\n    {-# INLINE pure #-}\n    mf <*> mx = Select (\n        for (enumerate mf) (\\f ->\n        for (enumerate mx) (\\x ->\n        yield (f x) ) ) )\n\ninstance Monad m => Monad (ListT m) where\n    return   = pure\n    {-# INLINE return #-}\n    m >>= f  = Select (for (enumerate m) (\\a -> enumerate (f a)))\n    {-# INLINE (>>=) #-}\n#if !MIN_VERSION_base(4,13,0)\n    fail _   = mzero\n    {-# INLINE fail #-}\n#endif\n\ninstance Monad m => MonadFail (ListT m) where\n    fail _ = mzero\n    {-# INLINE fail #-}\n\ninstance Foldable m => Foldable (ListT m) where\n    foldMap f = go . enumerate\n      where\n        go p = case p of\n            Request v _  -> closed v\n            Respond a fu -> f a `mappend` go (fu ())\n            M       m    -> F.foldMap go m\n            Pure    _    -> mempty\n    {-# INLINE foldMap #-}\n\ninstance (Functor m, Traversable m) => Traversable (ListT m) where\n    traverse k (Select p) = fmap Select (traverse_ p)\n      where\n        traverse_ (Request v _ ) = closed v\n        traverse_ (Respond a fu) = _Respond <$> k a <*> traverse_ (fu ())\n          where\n            _Respond a_ a' = Respond a_ (\\_ -> a')\n        traverse_ (M       m   ) = fmap M (traverse traverse_ m)\n        traverse_ (Pure     r  ) = pure (Pure r)\n\ninstance MonadTrans ListT where\n    lift m = Select (do\n        a <- lift m\n        yield a )\n\ninstance (MonadIO m) => MonadIO (ListT m) where\n    liftIO m = lift (liftIO m)\n    {-# INLINE liftIO #-}\n\ninstance (Functor m) => Alternative (ListT m) where\n    empty = Select (return ())\n    {-# INLINE empty #-}\n    p1 <|> p2 = Select (do\n        enumerate p1\n        enumerate p2 )\n\ninstance (Monad m) => MonadPlus (ListT m) where\n    mzero = empty\n    {-# INLINE mzero #-}\n    mplus = (<|>)\n    {-# INLINE mplus #-}\n\ninstance MFunctor ListT where\n    hoist morph = Select . hoist morph . enumerate\n    {-# INLINE hoist #-}\n\ninstance MMonad ListT where\n    embed f (Select p0) = Select (loop p0)\n      where\n        loop (Request a' fa ) = Request a' (\\a  -> loop (fa  a ))\n        loop (Respond b  fb') = Respond b  (\\b' -> loop (fb' b'))\n        loop (M          m  ) = for (enumerate (fmap loop (f m))) id\n        loop (Pure    r     ) = Pure r\n    {-# INLINE embed #-}\n\ninstance (Functor m) => Semigroup (ListT m a) where\n    (<>) = (<|>)\n    {-# INLINE (<>) #-}\n\ninstance (Functor m) => Monoid (ListT m a) where\n    mempty = empty\n    {-# INLINE mempty #-}\n#if !(MIN_VERSION_base(4,11,0))\n    mappend = (<|>)\n    {-# INLINE mappend #-}\n#endif\n\ninstance (MonadState s m) => MonadState s (ListT m) where\n    get     = lift  get\n    {-# INLINE get #-}\n\n    put   s = lift (put   s)\n    {-# INLINE put #-}\n\n    state f = lift (state f)\n    {-# INLINE state #-}\n\ninstance (MonadWriter w m) => MonadWriter w (ListT m) where\n    writer = lift . writer\n    {-# INLINE writer #-}\n\n    tell w = lift (tell w)\n    {-# INLINE tell #-}\n\n    listen l = Select (go (enumerate l) mempty)\n      where\n        go p w = case p of\n            Request a' fa  -> Request a' (\\a  -> go (fa  a ) w)\n            Respond b  fb' -> Respond (b, w)  (\\b' -> go (fb' b') w)\n            M          m   -> M (do\n                (p', w') <- listen m\n                return (go p' $! mappend w w') )\n            Pure    r      -> Pure r\n\n    pass l = Select (go (enumerate l) mempty)\n      where\n        go p w = case p of\n            Request  a'     fa  -> Request a' (\\a  -> go (fa  a ) w)\n            Respond (b, f)  fb' -> M (pass (return\n                (Respond b (\\b' -> go (fb' b') (f w)), \\_ -> f w) ))\n            M               m   -> M (do\n                (p', w') <- listen m\n                return (go p' $! mappend w w') )\n            Pure     r          -> Pure r\n\ninstance (MonadReader i m) => MonadReader i (ListT m) where\n    ask = lift ask\n    {-# INLINE ask #-}\n\n    local f l = Select (local f (enumerate l))\n    {-# INLINE local #-}\n\n    reader f = lift (reader f)\n    {-# INLINE reader #-}\n\ninstance (MonadError e m) => MonadError e (ListT m) where\n    throwError e = lift (throwError e)\n    {-# INLINE throwError #-}\n\n    catchError l k = Select (catchError (enumerate l) (\\e -> enumerate (k e)))\n    {-# INLINE catchError #-}\n\ninstance MonadThrow m => MonadThrow (ListT m) where\n    throwM = Select . throwM\n    {-# INLINE throwM #-}\n\ninstance MonadCatch m => MonadCatch (ListT m) where\n    catch l k = Select (Control.Monad.Catch.catch (enumerate l) (\\e -> enumerate (k e)))\n    {-# INLINE catch #-}\n\ninstance Monad m => MonadZip (ListT m) where\n    mzipWith f = go\n      where\n        go xs ys = Select $ do\n            xres <- lift $ next (enumerate xs)\n            case xres of\n                Left r -> return r\n                Right (x, xnext) -> do\n                    yres <- lift $ next (enumerate ys)\n                    case yres of\n                        Left r -> return r\n                        Right (y, ynext) -> do\n                            yield (f x y)\n                            enumerate (go (Select xnext) (Select ynext))\n\n-- | Run a self-contained `ListT` computation\nrunListT :: Monad m => ListT m a -> m ()\nrunListT l = runEffect (enumerate (l >> mzero))\n{-# INLINABLE runListT #-}\n\n{-| 'Enumerable' generalizes 'Data.Foldable.Foldable', converting effectful\n    containers to 'ListT's.\n\n    Instances of 'Enumerable' must satisfy these two laws:\n\n> toListT (return r) = return r\n>\n> toListT $ do x <- m  =  do x <- toListT m\n>              f x           toListT (f x)\n\n    In other words, 'toListT' is monad morphism.\n-}\nclass Enumerable t where\n    toListT :: Monad m => t m a -> ListT m a\n\ninstance Enumerable ListT where\n    toListT = id\n\ninstance Enumerable IdentityT where\n    toListT m = Select $ do\n        a <- lift $ runIdentityT m\n        yield a\n\ninstance Enumerable MaybeT where\n    toListT m = Select $ do\n        x <- lift $ runMaybeT m\n        case x of\n            Nothing -> return ()\n            Just a  -> yield a\n\ninstance Enumerable (ExceptT e) where\n    toListT m = Select $ do\n        x <- lift $ runExceptT m\n        case x of\n            Left  _ -> return ()\n            Right a -> yield a\n\n{-| Consume the first value from a 'Producer'\n\n    'next' either fails with a 'Left' if the 'Producer' terminates or succeeds\n    with a 'Right' providing the next value and the remainder of the 'Producer'.\n-}\nnext :: Monad m => Producer a m r -> m (Either r (a, Producer a m r))\nnext = go\n  where\n    go p = case p of\n        Request v _  -> closed v\n        Respond a fu -> return (Right (a, fu ()))\n        M         m  -> m >>= go\n        Pure    r    -> return (Left r)\n{-# INLINABLE next #-}\n\n{-| Convert a 'F.Foldable' to a 'Producer'\n\n@\n'each' :: ('Functor' m, 'Foldable' f) => f a -> 'Producer' a m ()\n@\n-}\neach :: (Functor m, Foldable f) => f a -> Proxy x' x () a m ()\neach = F.foldr (\\a p -> yield a >> p) (return ())\n{-# INLINABLE each #-}\n{-  The above code is the same as:\n\n> each = Data.Foldable.mapM_ yield\n\n    ... except writing it directly in terms of `Data.Foldable.foldr` improves\n    build/foldr fusion\n-}\n\n{-| Convert an 'Enumerable' to a 'Producer'\n\n@\n'every' :: ('Monad' m, 'Enumerable' t) => t m a -> 'Producer' a m ()\n@\n-}\nevery :: (Monad m, Enumerable t) => t m a -> Proxy x' x () a m ()\nevery it = discard >\\\\ enumerate (toListT it)\n{-# INLINABLE every #-}\n\n-- | Discards a value\ndiscard :: Monad m => a -> m ()\ndiscard _ = return ()\n{-# INLINABLE discard #-}\n\n-- | ('>->') with the arguments flipped\n(<-<)\n    :: Functor m\n    => Proxy () b c' c m r\n    -- ^\n    -> Proxy a' a () b m r\n    -- ^\n    -> Proxy a' a c' c m r\np2 <-< p1 = p1 >-> p2\n{-# INLINABLE (<-<) #-}\n\n{- $reexports\n    \"Control.Monad\" re-exports 'void'\n\n    \"Control.Monad.IO.Class\" re-exports 'MonadIO'.\n\n    \"Control.Monad.Trans.Class\" re-exports 'MonadTrans'.\n\n    \"Control.Monad.Morph\" re-exports 'MFunctor'.\n\n    \"Data.Foldable\" re-exports 'Foldable' (the class name only).\n-}\n"
  },
  {
    "path": "stack.yaml",
    "content": "resolver: lts-6.13\n"
  },
  {
    "path": "tests/Main.hs",
    "content": "module Main (main) where\n\nimport Data.Function                        (on)\nimport Data.List                            (intercalate)\nimport Control.Monad                        ((>=>))\nimport Control.Monad.Trans.Writer           (Writer, runWriter, tell)\nimport Test.QuickCheck                      (Gen, Arbitrary(..), choose)\nimport Test.Framework                       (defaultMain, testGroup, Test)\nimport Test.Framework.Providers.QuickCheck2 (testProperty)\n\nimport Pipes\nimport Pipes.Core\nimport Prelude hiding (log)\n\n\nmain :: IO ()\nmain = defaultMain tests\n\ntests :: [Test]\ntests =\n    [ testGroup \"Kleisli Category\"        $ testCategory (>=>) return\n    , testGroup \"Respond Category\"        $ testCategory (/>/) respond\n     ++ [ testProperty \"Distributivity\" prop_respond_Distributivity\n        ]\n    , testGroup \"Request Category\"        $ testCategory (\\>\\) request\n     ++ [ testProperty \"Distributivity\" prop_request_Distributivity\n        , testProperty \"Zero Law\"       prop_request_ZeroLaw\n        ]\n    , testGroup \"Pull Category\"           $ testCategory (>+>) pull\n    , testGroup \"Push Category\"           $ testCategory (>~>) push\n    , testGroup \"Push/Pull\"\n        [ testProperty \"Associativity\"  prop_pushPull_Associativity\n        ]\n    , testGroup \"Duals\"\n        [ testGroup \"Request\"\n            [ testProperty \"Composition\" prop_dual_RequestComposition\n            , testProperty \"Identity\"    prop_dual_RequestIdentity\n            ]\n        , testGroup \"Respond\"\n            [ testProperty \"Composition\" prop_dual_RespondComposition\n            , testProperty \"Identity\"    prop_dual_RespondIdentity\n            ]\n        , testProperty \"Distributivity\"  prop_dual_ReflectDistributivity\n        , testProperty \"Zero Law\"        prop_dual_ReflectZeroLaw\n        , testProperty \"Involution\"      prop_dual_Involution\n        ]\n    , testGroup \"Functor Laws\"\n        [ testProperty \"Identity\"        prop_FunctorIdentity\n        ]\n    ]\n\narbitraryBoundedEnum' :: (Bounded a, Enum a) => Gen a\narbitraryBoundedEnum' =\n  do let mn = minBound\n         mx = maxBound `asTypeOf` mn\n     n <- choose (fromEnum mn, fromEnum mx)\n     return (toEnum n `asTypeOf` mn)\n\ndata ClientStep\n    = ClientRequest\n    | ClientLog\n    | ClientInc\n      deriving (Enum, Bounded)\n\ninstance Arbitrary ClientStep where\n    arbitrary = arbitraryBoundedEnum'\n    shrink _  = []\n\ninstance Show ClientStep where\n    show x = case x of\n        ClientRequest -> \"request\"\n        ClientLog     -> \"log\"\n        ClientInc     -> \"inc\"\n\ndata ServerStep\n    = ServerRespond\n    | ServerLog\n    | ServerInc\n      deriving (Enum, Bounded)\n\ninstance Arbitrary ServerStep where\n    arbitrary = arbitraryBoundedEnum'\n    shrink _  = []\n\ninstance Show ServerStep where\n    show x = case x of\n        ServerRespond -> \"respond\"\n        ServerLog     -> \"log\"\n        ServerInc     -> \"inc\"\n\ndata ProxyStep\n    = ProxyRequest\n    | ProxyRespond\n    | ProxyLog\n    | ProxyInc deriving (Enum, Bounded)\n\ninstance Arbitrary ProxyStep where\n    arbitrary = arbitraryBoundedEnum'\n    shrink _  = []\n\ninstance Show ProxyStep where\n    show x = case x of\n        ProxyRequest -> \"request\"\n        ProxyRespond -> \"respond\"\n        ProxyLog     -> \"log\"\n        ProxyInc     -> \"inc\"\n\nlog :: Int -> Proxy a' a b' b (Writer [Int]) Int\nlog n = do\n    lift (tell [n])\n    return n\n\ninc :: (Monad m) => Int -> Proxy a' a b' b m Int\ninc n = return (n + 1)\n\ncorrect :: String -> String\ncorrect str = case str of\n    [] -> \"return\"\n    _  -> str\n\nnewtype AClient = AClient { unAClient :: [ClientStep] }\n\ninstance Arbitrary AClient where\n    arbitrary = fmap AClient arbitrary\n    shrink    = map AClient . shrink . unAClient\n\ninstance Show AClient where\n    show = correct . intercalate \" >=> \" . map show . unAClient\n\naClient :: AClient -> Int -> Client Int Int (Writer [Int]) Int\naClient = foldr (>=>) return . map f . unAClient\n  where\n    f x = case x of\n        ClientRequest -> request\n        ClientLog     -> log\n        ClientInc     -> inc\n\nnewtype AServer = AServer { unAServer :: [ServerStep] }\n\ninstance Arbitrary AServer where\n    arbitrary = fmap AServer arbitrary\n    shrink    = map AServer . shrink . unAServer\n\ninstance Show AServer where\n    show = correct . intercalate \" >=> \" . map show . unAServer\n\naServer :: AServer -> Int -> Server Int Int (Writer [Int]) Int\naServer = foldr (>=>) return . map f . unAServer\n  where\n    f x = case x of\n        ServerRespond -> respond\n        ServerLog     -> log\n        ServerInc     -> inc\n\nnewtype AProxy = AProxy { unAProxy :: [ProxyStep] }\n\ninstance Arbitrary AProxy where\n    arbitrary = fmap AProxy arbitrary\n    shrink    = map AProxy . shrink . unAProxy\n\ninstance Show AProxy where\n    show = correct . intercalate \" >=> \" . map show . unAProxy\n\naProxy :: AProxy -> Int -> Proxy Int Int Int Int (Writer [Int]) Int\naProxy = foldr (>=>) return . map f . unAProxy\n  where\n    f x = case x of\n        ProxyRequest -> request\n        ProxyRespond -> respond\n        ProxyLog     -> log\n        ProxyInc     -> inc\n\ntype ProxyK    = Int -> Proxy Int Int Int Int (Writer [Int]) Int\ntype Operation = ProxyK -> ProxyK -> ProxyK\n\ninfix 0 ===\n\n(===) :: ProxyK -> ProxyK -> AServer -> AClient -> Bool\n(===) pl pr p0 p1 =\n  let sv  = aServer p0\n      cl  = aClient p1\n      f p = runWriter (runEffect (p 0))\n  in on (==) f (sv >+> pl >+> cl) (sv >+> pr >+> cl)\n\ngen_prop_RightIdentity, gen_prop_LeftIdentity\n    :: Operation\n    -> ProxyK -- right/left identity element\n    -> AProxy -> AServer -> AClient -> Bool\ngen_prop_RightIdentity (>>>) idt f' =\n    let f = aProxy  f'\n    in (f >>> idt) === f\n\ngen_prop_LeftIdentity (>>>) idt f' =\n    let f = aProxy f'\n    in (idt >>> f) === f\n\ngen_prop_Associativity\n    :: Operation\n    -> AProxy -> AProxy -> AProxy -> AServer -> AClient -> Bool\ngen_prop_Associativity (>>>) f' g' h' =\n    let f = aProxy  f'\n        g = aProxy  g'\n        h = aProxy  h'\n    in f >>> (g >>> h) === (f >>> g) >>> h\n\ntestCategory :: Operation -> ProxyK -> [Test]\ntestCategory op idt =\n    [ testProperty \"Left Identity\"  $ gen_prop_LeftIdentity  op idt\n    , testProperty \"Right Identity\" $ gen_prop_RightIdentity op idt\n    , testProperty \"Associativity\"  $ gen_prop_Associativity op\n    ]\n\n-- Respond Category\n\nprop_respond_Distributivity f' g' h' =\n    let f = aProxy  f'\n        g = aProxy  g'\n        h = aProxy  h'\n    in (f >=> g) />/ h === (f />/ h) >=> (g />/ h)\n\n-- Request Category\n\nprop_request_Distributivity f' g' h' =\n    let f = aProxy  f'\n        g = aProxy  g'\n        h = aProxy  h'\n    in f \\>\\ (g >=> h) === (f \\>\\ g) >=> (f \\>\\ h)\n\nprop_request_ZeroLaw f' =\n    let f = aProxy  f'\n    in (f \\>\\ return) === return\n\n-- Push/Pull\n\nprop_pushPull_Associativity f' g' h' =\n    let f = aProxy f'\n        g = aProxy g'\n        h = aProxy h'\n    in (f >+> g) >~> h === f >+> (g >~> h)\n\n-- Duals\n\nprop_dual_RequestComposition f' g' =\n    let f = aProxy f'\n        g = aProxy g'\n    in reflect . (f \\>\\ g) === reflect . g />/ reflect . f\n\nprop_dual_RequestIdentity = reflect . request === respond\n\nprop_dual_RespondComposition f' g' =\n    let f = aProxy f'\n        g = aProxy g'\n    in  reflect . (f />/ g) === reflect . g \\>\\ reflect . f\n\nprop_dual_RespondIdentity = reflect . respond === request\n\nprop_dual_ReflectDistributivity f' g' =\n    let f = aProxy f'\n        g = aProxy g'\n    in reflect . (f >=> g) === reflect . f >=> reflect . g\n\nprop_dual_ReflectZeroLaw = reflect . return === return\n\nprop_dual_Involution f' =\n    let f = aProxy f'\n    in (reflect . reflect) . f >=> return === f\n\n-- Functor Laws\n\nprop_FunctorIdentity p' =\n    let p = aProxy p'\n    in fmap id p === id p\n"
  }
]