Streaming

Mature, resource-safe (ResourceT), large ecosystem (http-conduit, xml-conduit)

Simple "free monad of functor" design, works with Stream (Of a) m r

Elegant, principled (pipes-bytestring, pipes-parse) High-performance, concurrent streams with fusion Simple IO-based streams

Streaming avoids lazy IO's pitfalls: deterministic resource release, bounded memory, and composable pipelines.

-- conduit: streaming with resource safety and constant memory
{-# LANGUAGE OverloadedStrings #-}
import Conduit
import qualified Data.Text as T

main :: IO ()
main = do
  -- Sum the numbers 1..1,000,000 in constant memory
  total <- runConduit $ yieldMany [1 .. 1000000 :: Int] .| sumC
  print total

  -- Process a large file line by line
  runConduitRes $
    sourceFile "big.log"
      .| decodeUtf8C
      .| linesUnboundedC
      .| filterC (T.isInfixOf "ERROR")
      .| mapC (<> "\n")
      .| encodeUtf8C
      .| sinkFile "errors.log"