-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | A simple effect system that integrates with MTL -- -- Please see README.md @package simple-effects @version 0.6.0.2 module Control.Monad.Runnable -- | A class of monads that have a run function. -- -- The runMonad function gives the result inside of IO. The only -- reason for this is to allow an instance for IO to be written. Other -- instances do not perform any aditional IO. -- -- Instances for Identity, IO and (Runnable m, -- RunnableTrans t, Monad (t m)) => Runnable (t -- m) are given so users should only provide additional -- RunnableTrans instances instead of Runnable ones. class Monad m => Runnable m where type MonadicState m :: * type MonadicResult m a :: * where { type family MonadicState m :: *; type family MonadicResult m a :: *; } -- | Get the current state value. currentMonadicState :: Runnable m => m (MonadicState m) -- | If given a result, reconstruct a monadic compitation. restoreMonadicState :: Runnable m => MonadicResult m a -> m a -- | Given the required state value and a computation, run the computation -- up to the IO effect. This should effectively run each layer in the -- transformer stack. The MonadicState should hold all the needed -- information to do so. -- -- A more formal description of what it means to run a transformer is -- given for the runTransformer function. runMonad :: Runnable m => MonadicState m -> m a -> IO (MonadicResult m a) -- | A class of transformers that can run their effects in the underlying -- monad. -- -- The following laws need to hold. -- --
-- t -> do st <- currentTransState -- res <- lift (runTransformer t st) -- restoreTransState res -- == id ---- --
-- f :: (forall a. m a -> m a) -- m s -> runTransformer (lift (f m)) s == m s -> f (runTransformer (lift m) s) --class MonadTrans t => RunnableTrans t where type TransformerState t (m :: * -> *) :: * type TransformerResult t (m :: * -> *) a :: * where { type family TransformerState t (m :: * -> *) :: *; type family TransformerResult t (m :: * -> *) a :: *; } -- | Get the current state value. currentTransState :: (RunnableTrans t, Monad m) => t m (TransformerState t m) -- | If given a result, reconstruct the compitation. restoreTransState :: (RunnableTrans t, Monad m) => TransformerResult t m a -> t m a -- | Given the required state value and a computation, run the effects of -- the transformer in the underlying monad. runTransformer :: (RunnableTrans t, Monad m) => t m a -> TransformerState t m -> m (TransformerResult t m a) instance Control.Monad.Runnable.Runnable Data.Functor.Identity.Identity instance Control.Monad.Runnable.Runnable GHC.Types.IO instance (Control.Monad.Runnable.Runnable m, Control.Monad.Runnable.RunnableTrans t, GHC.Base.Monad (t m)) => Control.Monad.Runnable.Runnable (t m) instance Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.State.Strict.StateT s) instance Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.State.Lazy.StateT s) instance GHC.Base.Monoid s => Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.Writer.Strict.WriterT s) instance GHC.Base.Monoid s => Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.Writer.Lazy.WriterT s) instance Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.Reader.ReaderT s) instance GHC.Base.Monoid w => Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.RWS.Strict.RWST r w s) instance GHC.Base.Monoid w => Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.RWS.Lazy.RWST r w s) instance Control.Monad.Runnable.RunnableTrans Control.Monad.Trans.Identity.IdentityT instance Control.Monad.Trans.Error.Error e => Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.Error.ErrorT e) instance Control.Monad.Runnable.RunnableTrans (Control.Monad.Trans.Except.ExceptT e) instance Control.Monad.Runnable.RunnableTrans Control.Monad.Trans.Maybe.MaybeT instance Control.Monad.Runnable.RunnableTrans ListT.ListT module Control.Effects1 class Monad m => MonadEffect1 eff m -- | Use the effect described by eff. effect1 :: (MonadEffect1 eff m, EffectCon1 eff a) => proxy eff -> EffectMsg1 eff a -> m (EffectRes1 eff a) newtype EffHandling1 eff m EffHandling1 :: (forall a. EffectCon1 eff a => EffectMsg1 eff a -> m (EffectRes1 eff a)) -> EffHandling1 eff m [getHandling1] :: EffHandling1 eff m -> forall a. EffectCon1 eff a => EffectMsg1 eff a -> m (EffectRes1 eff a) -- | The EffectHandler1 is really just a ReaderT carrying -- around the function that knows how to handle the effect. newtype EffectHandler1 eff m a EffectHandler1 :: ReaderT (EffHandling1 eff m) m a -> EffectHandler1 eff m a [unpackEffectHandler1] :: EffectHandler1 eff m a -> ReaderT (EffHandling1 eff m) m a -- | Handle the effect described by eff. handleEffect1 :: (forall a. EffectCon1 eff a => EffectMsg1 eff a -> m (EffectRes1 eff a)) -> EffectHandler1 eff m b -> m b instance Control.Monad.Random.Class.MonadRandom m => Control.Monad.Random.Class.MonadRandom (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.Catch.MonadThrow m => Control.Monad.Catch.MonadThrow (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.Catch.MonadCatch m => Control.Monad.Catch.MonadCatch (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.IO.Class.MonadIO m => Control.Monad.IO.Class.MonadIO (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.State.Class.MonadState s m => Control.Monad.State.Class.MonadState s (Control.Effects1.EffectHandler1 eff m) instance GHC.Base.Alternative m => GHC.Base.Alternative (Control.Effects1.EffectHandler1 eff m) instance GHC.Base.Monad m => GHC.Base.Monad (Control.Effects1.EffectHandler1 eff m) instance GHC.Base.Applicative m => GHC.Base.Applicative (Control.Effects1.EffectHandler1 eff m) instance GHC.Base.Functor m => GHC.Base.Functor (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.Base.MonadBase GHC.Types.IO m => Control.Monad.Base.MonadBase GHC.Types.IO (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.Trans.Class.MonadTrans (Control.Effects1.EffectHandler1 eff) instance Control.Monad.Runnable.RunnableTrans (Control.Effects1.EffectHandler1 eff) instance Control.Monad.Reader.Class.MonadReader s m => Control.Monad.Reader.Class.MonadReader s (Control.Effects1.EffectHandler1 eff m) instance Control.Monad.Trans.Control.MonadBaseControl GHC.Types.IO m => Control.Monad.Trans.Control.MonadBaseControl GHC.Types.IO (Control.Effects1.EffectHandler1 eff m) instance (Control.Effects1.MonadEffect1 eff m, Control.Monad.Trans.Class.MonadTrans t, GHC.Base.Monad (t m)) => Control.Effects1.MonadEffect1 eff (t m) instance GHC.Base.Monad m => Control.Effects1.MonadEffect1 eff (Control.Effects1.EffectHandler1 eff m) module Control.Effects.State data State s data Get data Set data StateMessage s a [GetMessage] :: StateMessage s Get [SetMessage] :: !s -> StateMessage s Set data StateResult s a [GetResult] :: {getGetResult :: !s} -> StateResult s Get [SetResult] :: StateResult s Set type MonadEffectState s m = MonadEffect1 (State s) m stateEffect :: forall s a m. MonadEffectState s m => StateMessage s a -> m (StateResult s a) getState :: forall s m. MonadEffectState s m => m s setState :: forall s m. MonadEffectState s m => s -> m () modifyState :: forall s m. MonadEffectState s m => (s -> s) -> m () handleState :: forall m s a. Monad m => m s -> (s -> m ()) -> EffectHandler1 (State s) m a -> m a handleStateIO :: MonadIO m => s -> EffectHandler1 (State s) m a -> m a handleStateT :: Monad m => s -> StateT s m a -> m a instance GHC.Base.Monad m => Control.Effects1.MonadEffect1 (Control.Effects.State.State s) (Control.Monad.Trans.State.Lazy.StateT s m) module Control.Effects.Parallel forkThread :: IO () -> IO (MVar ()) appendState :: forall s m a proxy. (Semigroup s, MonadEffectState s m) => proxy s -> m a -> m a parallelWithRestore :: forall m a. Runnable m => (m a -> m a) -> [m a] -> m [a] parallelWithSequence :: Runnable m => [m a] -> m [a] parallel :: forall m a. Runnable m => [m a] -> m [MonadicResult m a] module Control.Effects class Monad m => MonadEffect eff m -- | Use the effect described by eff. effect :: MonadEffect eff m => proxy eff -> EffectMsg eff -> m (EffectRes eff) -- | The EffectHandler is really just a ReaderT carrying -- around the function that knows how to handle the effect. newtype EffectHandler eff m a EffectHandler :: ReaderT (EffectMsg eff -> m (EffectRes eff)) m a -> EffectHandler eff m a [unpackEffectHandler] :: EffectHandler eff m a -> ReaderT (EffectMsg eff -> m (EffectRes eff)) m a -- | Handle the effect described by eff. handleEffect :: (EffectMsg eff -> m (EffectRes eff)) -> EffectHandler eff m a -> m a instance Control.Monad.Random.Class.MonadRandom m => Control.Monad.Random.Class.MonadRandom (Control.Effects.EffectHandler eff m) instance Control.Monad.Catch.MonadThrow m => Control.Monad.Catch.MonadThrow (Control.Effects.EffectHandler eff m) instance Control.Monad.Catch.MonadCatch m => Control.Monad.Catch.MonadCatch (Control.Effects.EffectHandler eff m) instance Control.Monad.IO.Class.MonadIO m => Control.Monad.IO.Class.MonadIO (Control.Effects.EffectHandler eff m) instance Control.Monad.State.Class.MonadState s m => Control.Monad.State.Class.MonadState s (Control.Effects.EffectHandler eff m) instance GHC.Base.Alternative m => GHC.Base.Alternative (Control.Effects.EffectHandler eff m) instance GHC.Base.Monad m => GHC.Base.Monad (Control.Effects.EffectHandler eff m) instance GHC.Base.Applicative m => GHC.Base.Applicative (Control.Effects.EffectHandler eff m) instance GHC.Base.Functor m => GHC.Base.Functor (Control.Effects.EffectHandler eff m) instance Control.Monad.Base.MonadBase b m => Control.Monad.Base.MonadBase b (Control.Effects.EffectHandler eff m) instance Control.Monad.Trans.Class.MonadTrans (Control.Effects.EffectHandler eff) instance Control.Monad.Runnable.RunnableTrans (Control.Effects.EffectHandler eff) instance Control.Monad.Reader.Class.MonadReader s m => Control.Monad.Reader.Class.MonadReader s (Control.Effects.EffectHandler eff m) instance Control.Monad.Trans.Control.MonadBaseControl b m => Control.Monad.Trans.Control.MonadBaseControl b (Control.Effects.EffectHandler eff m) instance (Control.Effects.MonadEffect eff m, Control.Monad.Trans.Class.MonadTrans t, GHC.Base.Monad (t m)) => Control.Effects.MonadEffect eff (t m) instance GHC.Base.Monad m => Control.Effects.MonadEffect eff (Control.Effects.EffectHandler eff m) module Control.Effects.Early data Early a -- | Allows you to return early from a function. Make sure you -- handleEarly to get the actual result out. earlyReturn :: forall a b m. MonadEffect (Early a) m => a -> m b -- | Get the result from a computation. Either the early returned one, or -- the regular result. handleEarly :: Monad m => ExceptT a m a -> m a -- | Only do the given action and exit early with it's result. onlyDo :: MonadEffect (Early a) m => m a -> m b -- | Early return the given value if the Maybe is Nothing. -- Otherwise, contnue with the value inside of it. ifNothingEarlyReturn :: MonadEffect (Early a) m => a -> Maybe b -> m b -- | Only do the given action and early return with it's result if the -- given value is Nothing. Otherwise continue with the value -- inside of the Maybe. ifNothingDo :: MonadEffect (Early a) m => m a -> Maybe b -> m b instance GHC.Base.Monad m => Control.Effects.MonadEffect (Control.Effects.Early.Early a) (Control.Monad.Trans.Except.ExceptT a m) module Control.Effects.List data NonDeterministic -- | Runs the rest of the computation for every value in the list choose :: MonadEffect1 NonDeterministic m => [a] -> m a -- | Signals that this branch of execution failed to produce a result. deadEnd :: MonadEffect1 NonDeterministic m => m a -- | Execute all the effects and collect the result in a list. Note that -- this forces all the results, no matter which elements of the result -- list you end up actually using. For lazyer behavior use the other -- handlers. evaluateToList :: Monad m => ListT m a -> m [a] -- | Given a function, apply it to all the results. traverseAllResults :: Monad m => (a -> m ()) -> ListT m a -> m () -- | Given a folding function, fold over every result. If you want to -- terminate eary, use the foldWithEarlyTermination instead. foldAllResults :: Monad m => (r -> a -> m r) -> r -> ListT m a -> m r -- | Same as foldAllResults but the folding function has the ability -- to terminate eary by returning Nothing. foldWithEarlyTermination :: Monad m => (r -> a -> m (Maybe r)) -> r -> ListT m a -> m r -- | Executes only the effects needed to produce the first n results. evaluateNResults :: Monad m => Int -> ListT m a -> m [a] -- | Executes only the effects needed to produce a single result. evaluateOneResult :: Monad m => ListT m a -> m (Maybe a) instance GHC.Base.Monad m => Control.Effects1.MonadEffect1 Control.Effects.List.NonDeterministic (ListT.ListT m) module Control.Effects.Reader data ReadEnv e readEnv :: forall m e. MonadEffect (ReadEnv e) m => m e handleReadEnv :: m e -> EffectHandler (ReadEnv e) m a -> m a handleSubreader :: MonadEffect (ReadEnv e) m => (e -> e') -> EffectHandler (ReadEnv e') m a -> m a module Control.Effects.Signal -- | This class allows you to "throw" a signal. For the most part signals -- are the same as checked exceptions. The difference here is that the -- handler has the option to provide the value that will be the result -- of calling the signal function. This effectively allows -- you to have recoverable exceptions at the call site, instead of just -- at the handling site. -- -- This class can be considered an alias for MonadEffect -- (Signal a b) so your code isn't required to provide any -- instances. class MonadEffect (Signal a b) m => MonadEffectSignal a b m where signal = effect (Proxy :: Proxy (Signal a b)) -- | There are no restrictions on the type of values that can be thrown or -- returned. signal :: MonadEffectSignal a b m => a -> m b -- | The handle function will return a value of this type. data ResumeOrBreak b c -- | Give a value to the caller of signal and keep going. Resume :: b -> ResumeOrBreak b c -- | Continue the execution after the handler. The handler will return this -- value Break :: c -> ResumeOrBreak b c -- | Throw a signal with no possible recovery. The handler is forced to -- only return the Break constructor because it cannot construct a -- Void value. -- -- If this function is used along with handleAsException, this -- module behaves like regular checked exceptions. throwSignal :: Throws a m => a -> m b -- | Handle signals of a computation. The handler function has the option -- to provide a value to the caller of signal and continue -- execution there, or do what regular exception handlers do and continue -- execution after the handler. handleSignal :: Monad m => (a -> m (ResumeOrBreak b c)) -> EffectHandler (Signal a b) (ExceptT c m) c -> m c type Throws e m = MonadEffectSignal e Void m -- | This handler can only behave like a regular exception handler. If used -- along with throwSignal this module behaves like regular checked -- exceptions. handleException :: Monad m => (a -> m c) -> ExceptT a m c -> m c -- | See documentation for handleException. This handler gives you -- an Either. handleToEither :: ExceptT e m a -> m (Either e a) -- | The parameterizable maybe monad, obtained by composing an arbitrary -- monad with the Maybe monad. -- -- Computations are actions that may produce a value or exit. -- -- The return function yields a computation that produces that -- value, while >>= sequences two subcomputations, exiting -- if either computation does. newtype MaybeT (m :: * -> *) a :: (* -> *) -> * -> * MaybeT :: m (Maybe a) -> MaybeT a [runMaybeT] :: MaybeT a -> m (Maybe a) -- | Discard all the Throws and MonadEffectSignal -- constraints. If any exception was thrown the result will be -- Nothing. discardAllExceptions :: MaybeT m a -> m (Maybe a) -- | Satisfies all the Throws and MonadEffectSignal -- constraints if they all throw Showable exceptions. The -- first thrown exception will be shown and returned as a Left -- result. showAllExceptions :: Functor m => ExceptT SomeSignal m a -> m (Either Text a) -- | A class of monads that throw and catch exceptions of type e. -- An overlappable instance is given so you just need to make sure your -- transformers have a RunnableTrans instance. class Throws e m => Handles e m -- | Use this function to handle exceptions without discarding the -- Throws constraint. You'll want to use this if you're writing a -- recursive function. Using the regular handlers in that case will -- result with infinite types. -- -- Since this function doesn't discard constraints, you still need to -- handle the whole thing. -- -- Here's a slightly contrived example. -- --
-- data NotFound = NotFound -- data Tree a = Leaf a | Node (Tree a) (Tree a) -- data Step = GoLeft | GoRight -- findIndex :: (Handles NotFound m, Eq a) => a -> Tree a -> m [Step] -- findIndex x (Leaf a) | x == a = return [] -- | otherwise = throwSignal NotFound -- findIndex x (Node l r) = ((GoLeft :) $ findIndex x l) -- & handleRecursive (NotFound -> (GoRight :) $ findIndex x r) ---- -- Note: When you finally handle the exception effect, the order in which -- you handle it and other effects determines whether -- handleRecursive rolls back other effects if an exception -- occured or it preserves all of them up to the point of the exception. -- Handling exceptions last and handling them first will produce the -- former and latter behaviour respectively. handleRecursive :: Handles e m => (e -> m a) -> m a -> m a -- | handleToEither that doesn't discard Throws constraints. -- See documentation for handleRecursive. handleToEitherRecursive :: Handles e m => m a -> m (Either e a) instance GHC.Show.Show Control.Effects.Signal.SomeSignal instance GHC.Read.Read Control.Effects.Signal.SomeSignal instance GHC.Classes.Ord Control.Effects.Signal.SomeSignal instance GHC.Classes.Eq Control.Effects.Signal.SomeSignal instance GHC.Base.Monad m => Control.Effects.MonadEffect (Control.Effects.Signal.Signal e b) (Control.Monad.Trans.Except.ExceptT e m) instance (GHC.Show.Show e, GHC.Base.Monad m) => Control.Effects.MonadEffect (Control.Effects.Signal.Signal e b) (Control.Monad.Trans.Except.ExceptT Control.Effects.Signal.SomeSignal m) instance GHC.Base.Monad m => Control.Effects.MonadEffect (Control.Effects.Signal.Signal a b) (Control.Monad.Trans.Maybe.MaybeT m) instance (TypeError ...) => Control.Effects.MonadEffect (Control.Effects.Signal.Signal a b) GHC.Types.IO instance (GHC.Base.Monad m, b ~ c) => Control.Effects.Signal.MonadEffectSignal a c (Control.Effects.EffectHandler (Control.Effects.Signal.Signal a b) m) instance GHC.Base.Monad m => Control.Effects.Signal.MonadEffectSignal a b (Control.Monad.Trans.Maybe.MaybeT m) instance GHC.Base.Monad m => Control.Effects.Signal.MonadEffectSignal e b (Control.Monad.Trans.Except.ExceptT e m) instance (GHC.Base.Monad m, GHC.Show.Show e) => Control.Effects.Signal.MonadEffectSignal e b (Control.Monad.Trans.Except.ExceptT Control.Effects.Signal.SomeSignal m) instance Control.Effects.MonadEffect (Control.Effects.Signal.Signal a b) GHC.Types.IO => Control.Effects.Signal.MonadEffectSignal a b GHC.Types.IO instance (Control.Effects.Signal.MonadEffectSignal a b m, Control.Monad.Trans.Class.MonadTrans t, GHC.Base.Monad (t m)) => Control.Effects.Signal.MonadEffectSignal a b (t m) instance GHC.Base.Monad m => Control.Effects.Signal.Handles e (Control.Monad.Trans.Except.ExceptT e m) instance (GHC.Base.Monad m, GHC.Base.Monad (t m), Control.Effects.Signal.Handles e m, Control.Monad.Runnable.RunnableTrans t) => Control.Effects.Signal.Handles e (t m)