{-# LANGUAGE OverloadedStrings #-}
module Test.Attoparsec (tests) where
import Control.Monad (replicateM_)
import Control.Monad.Trans.Writer.Strict (runWriterT, tell)
import qualified Data.Attoparsec.Text as AT
import Data.Functor.Identity (runIdentity)
import Data.Text (Text)
import Pipes (each, for, lift, runEffect)
import Pipes.Attoparsec (parsed)
import Pipes.Prelude (toListM)
import Test.HUnit (Assertion, assert)
import Test.Tasty (TestTree)
import Test.Tasty.HUnit (testCase)
four :: AT.Parser Char
four = do
c <- AT.anyChar
replicateM_ 3 $ AT.char c
return c
type ParseTest = (Bool, String, [Text], [Char], [Text])
assertFoursTest :: ParseTest -> Assertion
assertFoursTest (ok, _title, input, output, mlo) =
assert $ res == output
&& isRight e == ok
&& mlo' == mlo
where
(e, res) = runIdentity . runWriterT . runEffect
$ for (parsed four $ each input)
(\c -> lift $ tell [c])
mlo' = case e of
Right _ -> []
Left (_,pmlo') -> fst . runIdentity
. runWriterT
$ toListM pmlo'
foursTests :: [ParseTest]
foursTests =
[ (True ,"0 chunk" ,[] ,[] ,[])
, (True ,"1 chunk: Empty" ,[] ,[] ,[])
, (True ,"1 chunk: One" ,["aaaa"] ,['a'] ,[])
, (True ,"1 chunk: One twice" ,["aaaaaaaa"] ,['a','a'] ,[])
, (True ,"1 chunk: Two" ,["aaaabbbb"] ,['a','b'] ,[])
, (True ,"1 chunk: Two between null" ,["aaaa","","bbbb"] ,['a','b'] ,[])
, (False ,"1 chunk: Partial" ,["aaaab"] ,['a'] ,["b"])
, (False ,"1 chunk: Wrong" ,["aaxbb"] ,[] ,["aaxbb"])
, (False ,"1 chunk: One then wrong" ,["aaaavz"] ,['a'] ,["vz"])
, (True ,"2 chunk: Empty" ,["",""] ,[] ,[])
, (True ,"2 chunk: Empty then one" ,["","aaaa"] ,['a'] ,[])
, (True ,"2 chunk: One" ,["a","aaa"] ,['a'] ,[])
, (True ,"2 chunk: One'" ,["aa","aa"] ,['a'] ,[])
, (True ,"2 chunk: One''" ,["aaa","a"] ,['a'] ,[])
, (True ,"2 chunk: One'''" ,["aaaa",""] ,['a'] ,[])
, (True ,"2 chunk: Two" ,["aaaa","bbbb"] ,['a','b'] ,[])
, (False ,"2 chunk: Wrong" ,["abcd","efgh"] ,[] ,["abcd","efgh"])
, (False ,"2 chunk: Wrong'" ,["a","axbb"] ,[] ,["a","axbb"])
, (False ,"2 chunk: One then wrong" ,["aaaab","bxz"] ,['a'] ,["b","bxz"])
, (True ,"3 chunk: One" ,["a","a","aa"] ,['a'] ,[])
, (False ,"3 chunk: Wrong" ,["a","a","axbb"] ,[] ,["a","a","axbb"])
]
testCaseFoursTest :: (Bool, [Char], [Text], [Char], [Text]) -> TestTree
testCaseFoursTest ft@(_,name,_,_,_) =
testCase ("Fours." ++ name) $ assertFoursTest ft
tests :: [TestTree]
tests = map testCaseFoursTest foursTests
isRight :: Either a b -> Bool
isRight (Right _) = True
isRight _ = False