control-0.1.0.0: Control/Monad/Trans/Control.hs
module Control.Monad.Trans.Control where
import Control.Monad.Trans.Accum
import Control.Monad.Trans.Class
import Control.Monad.Trans.Except
import Control.Monad.Trans.Identity
import Control.Monad.Trans.Maybe
import Control.Monad.Trans.Reader
import Control.Monad.Trans.State.Lazy as L
import Control.Monad.Trans.State.Strict as S
import Control.Monad.Trans.Writer.Lazy as L
import Control.Monad.Trans.Writer.Strict as S
class MonadTrans t => MonadTransControl t where
type StT t a
liftWith :: Monad m => (Run t -> m a) -> t m a
restoreT :: Monad m => m (StT t a) -> t m a
type Run t = ∀ n b . Monad n => t n b -> n (StT t b)
instance MonadTransControl IdentityT where
type StT IdentityT a = a
liftWith f = IdentityT $ f runIdentityT
restoreT = IdentityT
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance MonadTransControl MaybeT where
type StT MaybeT a = Maybe a
liftWith f = MaybeT $ fmap pure $ f runMaybeT
restoreT = MaybeT
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance MonadTransControl (ExceptT e) where
type StT (ExceptT e) a = Either e a
liftWith f = ExceptT $ fmap pure $ f runExceptT
restoreT = ExceptT
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance MonadTransControl (ReaderT r) where
type StT (ReaderT r) a = a
liftWith f = ReaderT $ \ r -> f (flip runReaderT r)
restoreT = ReaderT . pure
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance MonadTransControl (L.StateT s) where
type StT (L.StateT s) a = (a, s)
liftWith f = L.StateT $ \ s -> flip (,) s <$> f (flip L.runStateT s)
restoreT = L.StateT . pure
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance MonadTransControl (S.StateT s) where
type StT (S.StateT s) a = (a, s)
liftWith f = S.StateT $ \ s -> flip (,) s <$> f (flip S.runStateT s)
restoreT = S.StateT . pure
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance Monoid w => MonadTransControl (L.WriterT w) where
type StT (L.WriterT w) a = (a, w)
liftWith f = L.WriterT $ flip (,) mempty <$> f L.runWriterT
restoreT = L.WriterT
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance Monoid w => MonadTransControl (S.WriterT w) where
type StT (S.WriterT w) a = (a, w)
liftWith f = S.WriterT $ flip (,) mempty <$> f S.runWriterT
restoreT = S.WriterT
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}
instance Monoid c => MonadTransControl (AccumT c) where
type StT (AccumT c) a = (a, c)
liftWith f = AccumT $ \ c -> flip (,) c <$> f (flip runAccumT c)
restoreT = AccumT . pure
{-# INLINABLE liftWith #-}
{-# INLINABLE restoreT #-}