{-# LANGUAGE Rank2Types, ScopedTypeVariables #-}
module Test.Tasty.QuickCheck.Laws.ErrorMonad (
testErrorMonadLaws
, testErrorMonadLawCatchReturn
, testErrorMonadLawCatchThrow
, testErrorMonadLawCatchThrowThrow
, testErrorMonadLawThrowBind
) where
import Data.Proxy
( Proxy(..) )
import Data.Typeable
( Typeable, typeRep )
import Test.Tasty
( TestTree, testGroup )
import Test.Tasty.QuickCheck
( testProperty, Property, Arbitrary(..), CoArbitrary(..) )
import Text.Show.Functions
()
import Test.Tasty.QuickCheck.Laws.Class
testErrorMonadLaws
:: ( Monad m
, Eq a, Eq b
, Show t, Show e, Show a
, Arbitrary t, Arbitrary e, Arbitrary a
, Arbitrary (m a), Arbitrary (m b)
, CoArbitrary e, CoArbitrary a
, Typeable m, Typeable e, Typeable a, Typeable b
)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> Proxy b
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> (m a -> (e -> m a) -> m a)
-> TestTree
testErrorMonadLaws pm pt pe pa pb eq throw catch =
let
label = "Error Monad Laws for " ++ (show $ typeRep pm) ++ " with " ++
"e :: " ++ (show $ typeRep pe) ++ ", " ++
"a :: " ++ (show $ typeRep pa) ++ ", " ++
"b :: " ++ (show $ typeRep pb)
in
testGroup label
[ testErrorMonadLawCatchReturn pm pt pe pa eq catch
, testErrorMonadLawCatchThrow pm pt pe pa eq throw catch
, testErrorMonadLawCatchThrowThrow pm pt pe pa eq throw catch
, testErrorMonadLawThrowBind pm pt pe pa pb eq throw
]
testErrorMonadLawCatchReturn
:: ( Monad m
, Eq a
, Show t, Show a
, Arbitrary t, Arbitrary a
, Arbitrary (m a)
, CoArbitrary e
)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (m a -> (e -> m a) -> m a)
-> TestTree
testErrorMonadLawCatchReturn pm pt pe pa eq catch =
testProperty "catch (return a) h === return a" $
errorMonadLawCatchReturn pm pt pe pa eq catch
errorMonadLawCatchReturn
:: (Monad m, Eq a)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (m a -> (e -> m a) -> m a)
-> t -> a -> (e -> m a) -> Bool
errorMonadLawCatchReturn _ _ _ _ eq catch t a h =
(eq t) (catch (return a) h) (return a)
testErrorMonadLawCatchThrow
:: ( Monad m
, Eq a
, Show t, Show e
, Arbitrary t, Arbitrary e
, Arbitrary (m a)
, CoArbitrary e
)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> (m a -> (e -> m a) -> m a)
-> TestTree
testErrorMonadLawCatchThrow pm pt pe pa eq throw catch =
testProperty "catch (throw e) h === h e" $
errorMonadLawCatchThrow pm pt pe pa eq throw catch
errorMonadLawCatchThrow
:: (Monad m, Eq a)
=> Proxy m -> Proxy t -> Proxy e -> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> (m a -> (e -> m a) -> m a)
-> t -> e -> (e -> m a) -> Bool
errorMonadLawCatchThrow _ _ _ _ eq throw catch t e h =
(eq t) (catch (throw e) h) (h e)
testErrorMonadLawCatchThrowThrow
:: ( Monad m
, Eq a
, Show t, Show e
, Arbitrary t, Arbitrary e
)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> (m a -> (e -> m a) -> m a)
-> TestTree
testErrorMonadLawCatchThrowThrow pm pt pe pa eq throw catch =
testProperty "catch (throw e) throw === throw e" $
errorMonadLawCatchThrowThrow pm pt pe pa eq throw catch
errorMonadLawCatchThrowThrow
:: (Monad m, Eq a)
=> Proxy m -> Proxy t -> Proxy e -> Proxy a
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> (m a -> (e -> m a) -> m a)
-> t -> e -> Bool
errorMonadLawCatchThrowThrow _ _ _ _ eq throw catch t e =
(eq t) (catch (throw e) throw) (throw e)
testErrorMonadLawThrowBind
:: ( Monad m
, Eq b
, Show t, Show e
, Arbitrary t, Arbitrary e
, Arbitrary (m b)
, CoArbitrary a
)
=> Proxy m
-> Proxy t
-> Proxy e
-> Proxy a
-> Proxy b
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> TestTree
testErrorMonadLawThrowBind pm pt pe pa pb eq throw =
testProperty "throw e >>= f === throw e" $
errorMonadLawThrowBind pm pt pe pa pb eq throw
errorMonadLawThrowBind
:: (Monad m, Eq b)
=> Proxy m -> Proxy t -> Proxy e -> Proxy a -> Proxy b
-> (forall u. (Eq u) => t -> m u -> m u -> Bool)
-> (forall u. e -> m u)
-> t -> e -> (a -> m b) -> Bool
errorMonadLawThrowBind _ _ _ _ _ eq throw t e f =
(eq t) (throw e >>= f) (throw e)