on master help sign in
The MonadExcept class
commit5289d99d12b572e771437365c525b3a8a52611de authorIndex Int <vlad.z.4096@gmail.com> dateFri 12 Jun 2015, 01:54 (11 years ago) parente950bfe
5 files changed+126−4
ether.cabal+1 src/Control/Monad/Ether/Except.hs+109 src/Control/Monad/Ether/Reader.hs+8−3 src/Control/Monad/Ether/State.hs+7−1 src/Control/Monad/Trans/Ether/Except.hs+1
ether.cabal+1
@@ -31,6 +31,7 @@ library
3131 Control.Monad.Trans.Ether.Except
3232 Control.Monad.Ether.Reader
3333 Control.Monad.Ether.State
34+ Control.Monad.Ether.Except
3435 Control.Monad.Ether.Implicit.Reader
3536 Control.Monad.Ether.Implicit.State
3637
src/Control/Monad/Ether/Except.hsnew file+109
@@ -0,0 +1,109 @@
1+{-# LANGUAGE MultiParamTypeClasses #-}
2+{-# LANGUAGE TypeFamilies #-}
3+{-# LANGUAGE FlexibleInstances #-}
4+{-# LANGUAGE FlexibleContexts #-}
5+{-# LANGUAGE UndecidableInstances #-}
6+{-# LANGUAGE DataKinds #-}
7+{-# LANGUAGE ConstraintKinds #-}
8+{-# LANGUAGE TypeOperators #-}
9+{-# LANGUAGE FunctionalDependencies #-}
10+{-# LANGUAGE ScopedTypeVariables #-}
11+{-# LANGUAGE RankNTypes #-}
12+{-# LANGUAGE GeneralizedNewtypeDeriving #-}
13+module Control.Monad.Ether.Except
14+ (
15+ -- * MonadExcept class
16+ MonadExcept(..)
17+ -- * The Except monad
18+ , Except
19+ , runExcept
20+ -- * The ExceptT monad transformer
21+ , ExceptT
22+ , exceptT
23+ , runExceptT
24+ , mapExceptT
25+ ) where
26+
27+import Data.Proxy (Proxy(Proxy))
28+import Control.Monad.Trans (lift)
29+
30+import qualified Control.Monad.Trans.Ether.Reader as Reader
31+import qualified Control.Monad.Trans.Ether.State as State
32+import Control.Monad.Trans.Ether.Except
33+
34+-- for mtl instances
35+import qualified Control.Monad.Trans.Except as Trans (ExceptT(..), runExceptT)
36+import qualified Control.Monad.Trans.Identity as Trans.I
37+import qualified Control.Monad.Trans.List as Trans.L
38+import qualified Control.Monad.Trans.Maybe as Trans.M
39+import qualified Control.Monad.Trans.Reader as Trans.R
40+import qualified Control.Monad.Trans.State.Lazy as Trans.S.Lazy
41+import qualified Control.Monad.Trans.State.Strict as Trans.S.Strict
42+import qualified Control.Monad.Trans.Writer.Lazy as Trans.W.Lazy
43+import qualified Control.Monad.Trans.Writer.Strict as Trans.W.Strict
44+
45+class Monad m => MonadExcept tag e m | m tag -> e where
46+
47+ throw :: proxy tag -> e -> m a
48+
49+ catch :: proxy tag -> m a -> (e -> m a) -> m a
50+
51+instance {-# OVERLAPPING #-} Monad m => MonadExcept tag e (ExceptT tag e m) where
52+ throw proxy = exceptT proxy . return . Left
53+ catch proxy m h
54+ = exceptT proxy
55+ $ runExceptT proxy m
56+ >>= either (runExceptT proxy . h) (return . Right)
57+
58+instance MonadExcept tag e m => MonadExcept tag e (ExceptT tag' e' m) where
59+ throw proxy = lift . throw proxy
60+ catch proxy = liftCatch Proxy (catch proxy)
61+
62+-- Instances for other tagged transformers
63+
64+instance MonadExcept tag e m => MonadExcept tag e (Reader.ReaderT tag' r m) where
65+ throw proxy = lift . throw proxy
66+ catch proxy = Reader.liftCatch Proxy (catch proxy)
67+
68+instance MonadExcept tag e m => MonadExcept tag e (State.StateT tag' s m) where
69+ throw proxy = lift . throw proxy
70+ catch proxy = State.liftCatch Proxy (catch proxy)
71+
72+
73+-- Instances for mtl transformers
74+
75+instance MonadExcept tag e m => MonadExcept tag e (Trans.ExceptT e' m) where
76+ throw proxy = lift . throw proxy
77+ catch proxy m h = Trans.ExceptT $ catch proxy (Trans.runExceptT m) (Trans.runExceptT . h)
78+
79+instance MonadExcept tag e m => MonadExcept tag e (Trans.I.IdentityT m) where
80+ throw proxy = lift . throw proxy
81+ catch proxy = Trans.I.liftCatch (catch proxy)
82+
83+instance MonadExcept tag e m => MonadExcept tag e (Trans.L.ListT m) where
84+ throw proxy = lift . throw proxy
85+ catch proxy = Trans.L.liftCatch (catch proxy)
86+
87+instance MonadExcept tag e m => MonadExcept tag e (Trans.M.MaybeT m) where
88+ throw proxy = lift . throw proxy
89+ catch proxy = Trans.M.liftCatch (catch proxy)
90+
91+instance MonadExcept tag e m => MonadExcept tag e (Trans.R.ReaderT r m) where
92+ throw proxy = lift . throw proxy
93+ catch proxy = Trans.R.liftCatch (catch proxy)
94+
95+instance MonadExcept tag e m => MonadExcept tag e (Trans.S.Lazy.StateT s m) where
96+ throw proxy = lift . throw proxy
97+ catch proxy = Trans.S.Lazy.liftCatch (catch proxy)
98+
99+instance MonadExcept tag e m => MonadExcept tag e (Trans.S.Strict.StateT s m) where
100+ throw proxy = lift . throw proxy
101+ catch proxy = Trans.S.Strict.liftCatch (catch proxy)
102+
103+instance (Monoid w, MonadExcept tag e m) => MonadExcept tag e (Trans.W.Lazy.WriterT w m) where
104+ throw proxy = lift . throw proxy
105+ catch proxy = Trans.W.Lazy.liftCatch (catch proxy)
106+
107+instance (Monoid w, MonadExcept tag e m) => MonadExcept tag e (Trans.W.Strict.WriterT w m) where
108+ throw proxy = lift . throw proxy
109+ catch proxy = Trans.W.Strict.liftCatch (catch proxy)
src/Control/Monad/Ether/Reader.hs+8−3
@@ -22,13 +22,14 @@ module Control.Monad.Ether.Reader
2222 , ReaderT
2323 , readerT
2424 , runReaderT
25− , mapStateT
25+ , mapReaderT
2626 ) where
2727
2828import Data.Proxy (Proxy(Proxy))
2929import Control.Monad.Trans (lift)
3030
31−import Control.Monad.Trans.Ether.State (StateT, mapStateT)
31+import Control.Monad.Trans.Ether.State (StateT , mapStateT)
32+import Control.Monad.Trans.Ether.Except (ExceptT, mapExceptT)
3233import Control.Monad.Trans.Ether.Reader
3334
3435-- for mtl instances
@@ -81,7 +82,7 @@ instance {-# OVERLAPPING #-} Monad m => MonadReader tag r (ReaderT tag r m) wher
8182 ask proxy = readerT proxy return
8283 local proxy f m = readerT proxy (runReaderT proxy m . f)
8384
84−instance (MonadReader tag r m) => MonadReader tag r (ReaderT tag' r' m) where
85+instance MonadReader tag r m => MonadReader tag r (ReaderT tag' r' m) where
8586 ask proxy = lift (ask proxy)
8687 local proxy = mapReaderT Proxy . local proxy
8788
@@ -91,6 +92,10 @@ instance (MonadReader tag r m) => MonadReader tag r (StateT tag' s m) where
9192 ask proxy = lift (ask proxy)
9293 local proxy = mapStateT Proxy . local proxy
9394
95+instance (MonadReader tag r m) => MonadReader tag r (ExceptT tag' e m) where
96+ ask proxy = lift (ask proxy)
97+ local proxy = mapExceptT Proxy . local proxy
98+
9499-- Instances for mtl transformers
95100
96101instance MonadReader tag r m => MonadReader tag r (Trans.ContT r' m) where
src/Control/Monad/Ether/State.hs+7−1
@@ -33,6 +33,7 @@ module Control.Monad.Ether.State
3333import Control.Monad.Trans (lift)
3434
3535import Control.Monad.Trans.Ether.Reader (ReaderT)
36+import Control.Monad.Trans.Ether.Except (ExceptT)
3637import Control.Monad.Trans.Ether.State
3738
3839-- for mtl instances
@@ -79,7 +80,7 @@ instance {-# OVERLAPPING #-} Monad m => MonadState tag s (StateT tag s m) where
7980 get proxy = stateT proxy (\s -> return (s, s))
8081 put proxy s = stateT proxy (\_ -> return ((), s))
8182
82−instance (MonadState tag s m) => MonadState tag s (StateT tag' s' m) where
83+instance MonadState tag s m => MonadState tag s (StateT tag' s' m) where
8384 get proxy = lift (get proxy)
8485 put proxy = lift . put proxy
8586 state proxy = lift . state proxy
@@ -91,6 +92,11 @@ instance (MonadState tag s m) => MonadState tag s (ReaderT tag' r m) where
9192 put proxy = lift . put proxy
9293 state proxy = lift . state proxy
9394
95+instance (MonadState tag s m) => MonadState tag s (ExceptT tag' e m) where
96+ get proxy = lift (get proxy)
97+ put proxy = lift . put proxy
98+ state proxy = lift . state proxy
99+
94100-- Instances for mtl transformers
95101
96102instance MonadState tag s m => MonadState tag s (Trans.ContT r m) where
src/Control/Monad/Trans/Ether/Except.hs+1
@@ -20,6 +20,7 @@ module Control.Monad.Trans.Ether.Except
2020 , liftCallCC
2121 , liftListen
2222 , liftPass
23+ , liftCatch
2324 ) where
2425
2526import Data.Proxy (Proxy(Proxy))