{-|
Module      : Control.Monad.STM.Class
Licesnse    : BSD-2
Stability   : experimental

A typeclass for monads which can execute 'STM' actions. (This is essentially
a copy of "Control.Monad.IO.Class", modified for the 'STM' monad.)
-}

{-# OPTIONS_GHC -Wno-deprecations #-}

module Control.Monad.STM.Class
    ( MonadSTM(..) ) where

import Control.Monad.STM
import Control.Monad.Trans.Accum
import Control.Monad.Trans.Class
import Control.Monad.Trans.Cont
import Control.Monad.Trans.Error
import Control.Monad.Trans.Except
import Control.Monad.Trans.Identity
import Control.Monad.Trans.List
import Control.Monad.Trans.Maybe
import qualified Control.Monad.Trans.RWS.CPS as RWS.CPS
import qualified Control.Monad.Trans.RWS.Lazy as RWS.Lazy
import qualified Control.Monad.Trans.RWS.Strict as RWS.Strict
import Control.Monad.Trans.Reader
import Control.Monad.Trans.Select
import qualified Control.Monad.Trans.State.Lazy as State.Lazy
import qualified Control.Monad.Trans.State.Strict as State.Strict
import qualified Control.Monad.Trans.Writer.CPS as Writer.CPS
import qualified Control.Monad.Trans.Writer.Lazy as Writer.Lazy
import qualified Control.Monad.Trans.Writer.Strict as Writer.Strict

-- | Analogous to 'MonadIO'. It allows one to use @'liftSTM'@ when 'STM' is at
--   the "bottom" of the monad transformer stack.
class Monad m => MonadSTM m where
    liftSTM :: STM a -> m a

instance MonadSTM STM where
    liftSTM :: STM a -> STM a
liftSTM = STM a -> STM a
forall a. a -> a
id

instance (Monoid w, MonadSTM m) => MonadSTM (AccumT w m) where
    liftSTM :: STM a -> AccumT w m a
liftSTM = m a -> AccumT w m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> AccumT w m a) -> (STM a -> m a) -> STM a -> AccumT w m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (ContT r m) where
    liftSTM :: STM a -> ContT r m a
liftSTM = m a -> ContT r m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> ContT r m a) -> (STM a -> m a) -> STM a -> ContT r m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Error e, MonadSTM m) => MonadSTM (ErrorT e m) where
    liftSTM :: STM a -> ErrorT e m a
liftSTM = m a -> ErrorT e m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> ErrorT e m a) -> (STM a -> m a) -> STM a -> ErrorT e m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (ExceptT e m) where
    liftSTM :: STM a -> ExceptT e m a
liftSTM = m a -> ExceptT e m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> ExceptT e m a) -> (STM a -> m a) -> STM a -> ExceptT e m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (IdentityT m) where
    liftSTM :: STM a -> IdentityT m a
liftSTM = m a -> IdentityT m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> IdentityT m a) -> (STM a -> m a) -> STM a -> IdentityT m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (ListT m) where
    liftSTM :: STM a -> ListT m a
liftSTM = m a -> ListT m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> ListT m a) -> (STM a -> m a) -> STM a -> ListT m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (MaybeT m) where
    liftSTM :: STM a -> MaybeT m a
liftSTM = m a -> MaybeT m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> MaybeT m a) -> (STM a -> m a) -> STM a -> MaybeT m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (RWS.CPS.RWST r w s m) where
    liftSTM :: STM a -> RWST r w s m a
liftSTM = m a -> RWST r w s m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> RWST r w s m a)
-> (STM a -> m a) -> STM a -> RWST r w s m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (RWS.Lazy.RWST r w s m) where
    liftSTM :: STM a -> RWST r w s m a
liftSTM = m a -> RWST r w s m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> RWST r w s m a)
-> (STM a -> m a) -> STM a -> RWST r w s m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (RWS.Strict.RWST r w s m) where
    liftSTM :: STM a -> RWST r w s m a
liftSTM = m a -> RWST r w s m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> RWST r w s m a)
-> (STM a -> m a) -> STM a -> RWST r w s m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (ReaderT r m) where
    liftSTM :: STM a -> ReaderT r m a
liftSTM = m a -> ReaderT r m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> ReaderT r m a) -> (STM a -> m a) -> STM a -> ReaderT r m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (SelectT r m) where
    liftSTM :: STM a -> SelectT r m a
liftSTM = m a -> SelectT r m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> SelectT r m a) -> (STM a -> m a) -> STM a -> SelectT r m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (State.Lazy.StateT s m) where
    liftSTM :: STM a -> StateT s m a
liftSTM = m a -> StateT s m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> StateT s m a) -> (STM a -> m a) -> STM a -> StateT s m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance MonadSTM m => MonadSTM (State.Strict.StateT s m) where
    liftSTM :: STM a -> StateT s m a
liftSTM = m a -> StateT s m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> StateT s m a) -> (STM a -> m a) -> STM a -> StateT s m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (Writer.CPS.WriterT w m) where
    liftSTM :: STM a -> WriterT w m a
liftSTM = m a -> WriterT w m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> WriterT w m a) -> (STM a -> m a) -> STM a -> WriterT w m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (Writer.Lazy.WriterT w m) where
    liftSTM :: STM a -> WriterT w m a
liftSTM = m a -> WriterT w m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> WriterT w m a) -> (STM a -> m a) -> STM a -> WriterT w m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM

instance (Monoid w, MonadSTM m) => MonadSTM (Writer.Strict.WriterT w m) where
    liftSTM :: STM a -> WriterT w m a
liftSTM = m a -> WriterT w m a
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m a -> WriterT w m a) -> (STM a -> m a) -> STM a -> WriterT w m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. STM a -> m a
forall (m :: * -> *) a. MonadSTM m => STM a -> m a
liftSTM