module Data.Attoparsec.ByteString.Streaming
(
parse
, parsed
, atto
, atto_
, module Data.Attoparsec.ByteString
)
where
import qualified Data.ByteString as B
import Control.Monad.Trans.State.Strict
import Control.Monad.Trans.Except
import Control.Monad.Trans
import qualified Data.Attoparsec.ByteString as A
import qualified Data.Attoparsec.Internal.Types as T
import Data.Attoparsec.ByteString
hiding (IResult(..), Result, eitherResult, maybeResult,
parse, parseWith, parseTest)
import Streaming hiding (concats, unfold)
import Streaming.Internal (Stream (..))
import Data.ByteString.Streaming
import Data.ByteString.Streaming.Internal
parse :: Monad m
=> A.Parser a
-> ByteString m x
-> m (Either a ([String], String), ByteString m x)
parse p s = case s of
Chunk x xs -> go (A.parse p x) xs
Empty r -> go (A.parse p B.empty) (Empty r)
Go m -> m >>= parse p
where
go (T.Fail x stk msg) ys = return $ (Right (stk, msg), Chunk x ys)
go (T.Done x r) ys = return $ (Left r, Chunk x ys)
go (T.Partial k) (Chunk y ys) = go (k y) ys
go (T.Partial k) (Go m) = m >>= go (T.Partial k)
go (T.Partial k) empty = go (k B.empty) empty
atto :: Monad m => A.Parser a -> StateT (ByteString m x) m (Either a ([String], String))
atto p = StateT (parse p)
atto_ :: Monad m => A.Parser a -> ExceptT ([String], String) (StateT (ByteString m x) m) a
atto_ p = ExceptT $ StateT loop where
loop s = case s of
Chunk x xs -> go (A.parse p x) xs
Empty r -> go (A.parse p B.empty) (Empty r)
Go m -> m >>= loop
go (T.Fail x stk msg) ys = return $ (Left (stk, msg), Chunk x ys)
go (T.Done x r) ys = return $ (Right r, Chunk x ys)
go (T.Partial k) (Chunk y ys) = go (k y) ys
go (T.Partial k) (Go m) = m >>= go (T.Partial k)
go (T.Partial k) blank = go (k B.empty) blank
parsed
:: Monad m
=> A.Parser a
-> ByteString m r
-> Stream (Of a) m (Either (([String],String), ByteString m r) r)
parsed parser = go
where
go p0 = do
x <- lift (nextChunk p0)
case x of
Left r -> Return (Right r)
Right (bs,p1) -> step (chunk bs >>) (A.parse parser bs) p1
step diffP res p0 = case res of
A.Fail _ c m -> Return (Left ((c,m), diffP p0))
A.Done bs b -> Step (b :> go (chunk bs >> p0))
A.Partial k -> do
x <- lift (nextChunk p0)
case x of
Left e -> step diffP (k mempty) (return e)
Right (a,p1) -> step (diffP . (chunk a >>)) (k a) p1