-----------------------------------------------------------------------------

-- |

-- Module      :  Control.Effect.Machinery.Tagger

-- Copyright   :  (c) Michael Szvetits, 2020

-- License     :  BSD3 (see the file LICENSE)

-- Maintainer  :  typedbyte@qualified.name

-- Stability   :  stable

-- Portability :  portable

--

-- This module defines an effect handler which handles tagging, retagging and

-- untagging of effects.

-----------------------------------------------------------------------------

module Control.Effect.Machinery.Tagger where

-- base

import Control.Monad.IO.Class (MonadIO)

-- monad-control

import Control.Monad.Trans.Control (MonadBaseControl, MonadTransControl)

-- transformers

import Control.Monad.Trans.Class (MonadTrans)

-- transformers-base

import Control.Monad.Base (MonadBase)

import Control.Effect.Machinery.Default (Default(Default))

-- | This type provides instances for effect type classes in order to enable

-- tagging, retagging and untagging of effects. Whenever this type is used as

-- handler of an effect, the effect previously tagged with @tag@ will be

-- tagged with @new@ instead.

--

-- You usually don\'t interact with this type directly, since the type class

-- instances for this type are generated by the functions found in the module

-- "Control.Effect.Machinery.TH".

newtype Tagger tag new m a =
  Tagger { Tagger tag new m a -> m a
runTagger :: m a }
    deriving (Functor (Tagger tag new m)
a -> Tagger tag new m a
Functor (Tagger tag new m) =>
(forall a. a -> Tagger tag new m a)
-> (forall a b.
    Tagger tag new m (a -> b)
    -> Tagger tag new m a -> Tagger tag new m b)
-> (forall a b c.
    (a -> b -> c)
    -> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c)
-> (forall a b.
    Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b)
-> (forall a b.
    Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a)
-> Applicative (Tagger tag new m)
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a
Tagger tag new m (a -> b)
-> Tagger tag new m a -> Tagger tag new m b
(a -> b -> c)
-> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c
forall a. a -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *).
Applicative m =>
Functor (Tagger tag new m)
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Applicative m =>
a -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m (a -> b)
-> Tagger tag new m a -> Tagger tag new m b
forall k (tag :: k) k (new :: k) (m :: * -> *) a b c.
Applicative m =>
(a -> b -> c)
-> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c
forall a b.
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a
forall a b.
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
forall a b.
Tagger tag new m (a -> b)
-> Tagger tag new m a -> Tagger tag new m b
forall a b c.
(a -> b -> c)
-> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c
forall (f :: * -> *).
Functor f =>
(forall a. a -> f a)
-> (forall a b. f (a -> b) -> f a -> f b)
-> (forall a b c. (a -> b -> c) -> f a -> f b -> f c)
-> (forall a b. f a -> f b -> f b)
-> (forall a b. f a -> f b -> f a)
-> Applicative f
<* :: Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a
$c<* :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m a
*> :: Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
$c*> :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
liftA2 :: (a -> b -> c)
-> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c
$cliftA2 :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b c.
Applicative m =>
(a -> b -> c)
-> Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m c
<*> :: Tagger tag new m (a -> b)
-> Tagger tag new m a -> Tagger tag new m b
$c<*> :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Applicative m =>
Tagger tag new m (a -> b)
-> Tagger tag new m a -> Tagger tag new m b
pure :: a -> Tagger tag new m a
$cpure :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Applicative m =>
a -> Tagger tag new m a
$cp1Applicative :: forall k (tag :: k) k (new :: k) (m :: * -> *).
Applicative m =>
Functor (Tagger tag new m)
Applicative, a -> Tagger tag new m b -> Tagger tag new m a
(a -> b) -> Tagger tag new m a -> Tagger tag new m b
(forall a b. (a -> b) -> Tagger tag new m a -> Tagger tag new m b)
-> (forall a b. a -> Tagger tag new m b -> Tagger tag new m a)
-> Functor (Tagger tag new m)
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Functor m =>
a -> Tagger tag new m b -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Functor m =>
(a -> b) -> Tagger tag new m a -> Tagger tag new m b
forall a b. a -> Tagger tag new m b -> Tagger tag new m a
forall a b. (a -> b) -> Tagger tag new m a -> Tagger tag new m b
forall (f :: * -> *).
(forall a b. (a -> b) -> f a -> f b)
-> (forall a b. a -> f b -> f a) -> Functor f
<$ :: a -> Tagger tag new m b -> Tagger tag new m a
$c<$ :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Functor m =>
a -> Tagger tag new m b -> Tagger tag new m a
fmap :: (a -> b) -> Tagger tag new m a -> Tagger tag new m b
$cfmap :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Functor m =>
(a -> b) -> Tagger tag new m a -> Tagger tag new m b
Functor, Applicative (Tagger tag new m)
a -> Tagger tag new m a
Applicative (Tagger tag new m) =>
(forall a b.
 Tagger tag new m a
 -> (a -> Tagger tag new m b) -> Tagger tag new m b)
-> (forall a b.
    Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b)
-> (forall a. a -> Tagger tag new m a)
-> Monad (Tagger tag new m)
Tagger tag new m a
-> (a -> Tagger tag new m b) -> Tagger tag new m b
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
forall a. a -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *).
Monad m =>
Applicative (Tagger tag new m)
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
a -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Monad m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Monad m =>
Tagger tag new m a
-> (a -> Tagger tag new m b) -> Tagger tag new m b
forall a b.
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
forall a b.
Tagger tag new m a
-> (a -> Tagger tag new m b) -> Tagger tag new m b
forall (m :: * -> *).
Applicative m =>
(forall a b. m a -> (a -> m b) -> m b)
-> (forall a b. m a -> m b -> m b)
-> (forall a. a -> m a)
-> Monad m
return :: a -> Tagger tag new m a
$creturn :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
a -> Tagger tag new m a
>> :: Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
$c>> :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Monad m =>
Tagger tag new m a -> Tagger tag new m b -> Tagger tag new m b
>>= :: Tagger tag new m a
-> (a -> Tagger tag new m b) -> Tagger tag new m b
$c>>= :: forall k (tag :: k) k (new :: k) (m :: * -> *) a b.
Monad m =>
Tagger tag new m a
-> (a -> Tagger tag new m b) -> Tagger tag new m b
$cp1Monad :: forall k (tag :: k) k (new :: k) (m :: * -> *).
Monad m =>
Applicative (Tagger tag new m)
Monad, Monad (Tagger tag new m)
Monad (Tagger tag new m) =>
(forall a. IO a -> Tagger tag new m a)
-> MonadIO (Tagger tag new m)
IO a -> Tagger tag new m a
forall a. IO a -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *).
MonadIO m =>
Monad (Tagger tag new m)
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
MonadIO m =>
IO a -> Tagger tag new m a
forall (m :: * -> *).
Monad m =>
(forall a. IO a -> m a) -> MonadIO m
liftIO :: IO a -> Tagger tag new m a
$cliftIO :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
MonadIO m =>
IO a -> Tagger tag new m a
$cp1MonadIO :: forall k (tag :: k) k (new :: k) (m :: * -> *).
MonadIO m =>
Monad (Tagger tag new m)
MonadIO)
    deriving (m a -> Tagger tag new m a
(forall (m :: * -> *) a. Monad m => m a -> Tagger tag new m a)
-> MonadTrans (Tagger tag new)
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
m a -> Tagger tag new m a
forall (m :: * -> *) a. Monad m => m a -> Tagger tag new m a
forall (t :: (* -> *) -> * -> *).
(forall (m :: * -> *) a. Monad m => m a -> t m a) -> MonadTrans t
lift :: m a -> Tagger tag new m a
$clift :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
m a -> Tagger tag new m a
MonadTrans, MonadTrans (Tagger tag new)
m (StT (Tagger tag new) a) -> Tagger tag new m a
MonadTrans (Tagger tag new) =>
(forall (m :: * -> *) a.
 Monad m =>
 (Run (Tagger tag new) -> m a) -> Tagger tag new m a)
-> (forall (m :: * -> *) a.
    Monad m =>
    m (StT (Tagger tag new) a) -> Tagger tag new m a)
-> MonadTransControl (Tagger tag new)
(Run (Tagger tag new) -> m a) -> Tagger tag new m a
forall k (tag :: k) k (new :: k). MonadTrans (Tagger tag new)
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
m (StT (Tagger tag new) a) -> Tagger tag new m a
forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
(Run (Tagger tag new) -> m a) -> Tagger tag new m a
forall (m :: * -> *) a.
Monad m =>
m (StT (Tagger tag new) a) -> Tagger tag new m a
forall (m :: * -> *) a.
Monad m =>
(Run (Tagger tag new) -> m a) -> Tagger tag new m a
forall (t :: (* -> *) -> * -> *).
MonadTrans t =>
(forall (m :: * -> *) a. Monad m => (Run t -> m a) -> t m a)
-> (forall (m :: * -> *) a. Monad m => m (StT t a) -> t m a)
-> MonadTransControl t
restoreT :: m (StT (Tagger tag new) a) -> Tagger tag new m a
$crestoreT :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
m (StT (Tagger tag new) a) -> Tagger tag new m a
liftWith :: (Run (Tagger tag new) -> m a) -> Tagger tag new m a
$cliftWith :: forall k (tag :: k) k (new :: k) (m :: * -> *) a.
Monad m =>
(Run (Tagger tag new) -> m a) -> Tagger tag new m a
$cp1MonadTransControl :: forall k (tag :: k) k (new :: k). MonadTrans (Tagger tag new)
MonadTransControl) via Default
    deriving (MonadBase b, MonadBaseControl b)