{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE MultiParamTypeClasses #-}
module Polysemy.State.Law where
import Polysemy
import Polysemy.Law
import Polysemy.State
import Control.Applicative
import Control.Arrow
prop_lawfulState
:: forall r s
. (Eq s, Show s, Arbitrary s, MakeLaw (State s) r)
=> InterpreterFor (State s) r
-> Property
prop_lawfulState i12n = conjoin
[ runLaw i12n law_putTwice
, runLaw i12n law_getTwice
, runLaw i12n law_getPutGet
]
law_putTwice
:: forall s r
. (Eq s, Arbitrary s, Show s, MakeLaw (State s) r)
=> Law (State s) r
law_putTwice =
mkLaw
"put %1 >> put %2 >> get"
(\s s' -> put @s s >> put @s s' >> get @s)
"put %2 >> get"
(\_ s' -> put @s s' >> get @s)
law_getTwice
:: forall s r
. (Eq s, Arbitrary s, Show s, MakeLaw (State s) r)
=> Law (State s) r
law_getTwice =
mkLaw
"liftA2 (,) get get"
(liftA2 (,) (get @s) (get @s))
"(id &&& id) <$> get"
((id &&& id) <$> get @s)
law_getPutGet
:: forall s r
. (Eq s, Arbitrary s, Show s, MakeLaw (State s) r)
=> Law (State s) r
law_getPutGet =
mkLaw
"get >>= put >> get"
(get @s >>= put @s >> get @s)
"get"
(get @s)