mtl 2.3.1 → 2.3.2
raw patch · 12 files changed
+112/−21 lines, 12 filesdep ~basenew-uploader
Dependency ranges changed: base
Files
- CHANGELOG.markdown +9/−0
- Control/Monad/Accum.hs +22/−7
- Control/Monad/Cont/Class.hs +15/−3
- Control/Monad/Error/Class.hs +29/−3
- Control/Monad/Except.hs +1/−0
- Control/Monad/RWS/Class.hs +4/−0
- Control/Monad/Reader/Class.hs +6/−0
- Control/Monad/State/Class.hs +7/−0
- Control/Monad/Writer/CPS.hs +3/−1
- Control/Monad/Writer/Class.hs +8/−0
- README.markdown +1/−1
- mtl.cabal +7/−6
CHANGELOG.markdown view
@@ -1,3 +1,12 @@+2.3.2 -- 2025-12-07+-----+* Add `Accum` monad.+* Generalize `MonadAccum` instance for all `Monad m` underlying `AccumT`, not just `Identity`.+* Allow building monokinded `ContT` if the compiler is MicroHs.+* Fix an issue where `QuantifiedConstraints` in the definition of `liftCallCC` was was preventing building under certain conditions.+* Add `Control.Monad.Class.onError`.+* Add various instances for `Data.Functor.Product.Product`.+ 2.3.1 -- 2022-09-10 ----- * Add `modifyError` to `Control.Monad.Error.Class`, and re-export from
Control/Monad/Accum.hs view
@@ -83,6 +83,22 @@ ( -- * Type class MonadAccum (..), + -- * The 'Accum' monad+ Accum.Accum,+ Accum.runAccum,+ Accum.execAccum,+ Accum.evalAccum,+ Accum.mapAccum,++ -- * The 'AccumT' monad transformer+ Accum.AccumT (..),+ Accum.execAccumT,+ Accum.evalAccumT,+ Accum.mapAccumT,+ Accum.readerToAccumT,+ Accum.writerToAccumT,+ Accum.accumToStateT,+ -- * Lifting helper type LiftingAccum (..), @@ -109,7 +125,6 @@ import qualified Control.Monad.Trans.Writer.Lazy as LazyWriter import qualified Control.Monad.Trans.Writer.Strict as StrictWriter import Data.Functor (($>))-import Data.Functor.Identity (Identity) import Data.Kind (Type) -- | The capability to accumulate. This can be seen in one of two ways:@@ -125,7 +140,7 @@ -- -- 1. @'accum' ('const' (x, 'mempty'))@ @=@ @'pure' x@ -- 2. @'accum' f '*>' 'accum' g@ @=@--- @'accum' '$' \acc -> let (_, v) = f acc+-- @'accum' '$' \\acc -> let (_, v) = f acc -- (res, w) = g (acc '<>' v) in (res, v '<>' w)@ -- -- If you choose to define 'look' and 'add' instead, their definitions must obey@@ -134,14 +149,14 @@ -- 1. @'look' '*>' 'look'@ @=@ @'look'@ -- 2. @'add' 'mempty'@ @=@ @'pure' ()@ -- 3. @'add' x '*>' 'add' y@ @=@ @'add' (x '<>' y)@--- 4. @'add' x '*>' 'look'@ @=@ @'look' '>>=' \w -> 'add' x '$>' w '<>' x@+-- 4. @'add' x '*>' 'look'@ @=@ @'look' '>>=' \\w -> 'add' x '$>' w '<>' x@ -- -- If you want to define both, the relationship between them is as follows. -- These are also the default definitions. ----- 1. @'look'@ @=@ @'accum' '$' \acc -> (acc, mempty)@--- 2. @'add' x@ @=@ @'accum' '$' \acc -> ('()', x)@--- 3. @'accum' f@ @=@ @'look' >>= \acc -> let (res, v) = f acc in 'add' v '$>' res@+-- 1. @'look'@ @=@ @'accum' '$' \\acc -> (acc, mempty)@+-- 2. @'add' x@ @=@ @'accum' '$' \\acc -> ('()', x)@+-- 3. @'accum' f@ @=@ @'look' >>= \\acc -> let (res, v) = f acc in 'add' v '$>' res@ -- -- @since 2.3 class (Monoid w, Monad m) => MonadAccum w m | m -> w where@@ -160,7 +175,7 @@ {-# MINIMAL accum | look, add #-} -- | @since 2.3-instance (Monoid w) => MonadAccum w (AccumT w Identity) where+instance (Monoid w, Monad m) => MonadAccum w (AccumT w m) where look = Accum.look add = Accum.add accum = Accum.accum
Control/Monad/Cont/Class.hs view
@@ -1,3 +1,4 @@+{-# LANGUAGE CPP #-} {-# LANGUAGE RankNTypes #-} {-# LANGUAGE Safe #-} {-# LANGUAGE PolyKinds #-}@@ -113,7 +114,12 @@ {-# MINIMAL callCC #-} -- | @since 2.3.1+#ifdef __MHS__+-- The ContT type is not polykinded with mhs.+instance MonadCont (ContT r m) where+#else instance forall k (r :: k) (m :: (k -> Type)) . MonadCont (ContT r m) where+#endif callCC = ContT.callCC -- ---------------------------------------------------------------------------@@ -185,11 +191,13 @@ -- -- = Note ----- For any function @f@, @'liftCallCC f'@ satisfies the [uniformity+-- For any function @f@, @'liftCallCC' f@ satisfies the [uniformity -- condition](https://hackage.haskell.org/package/transformers-0.5.6.2/docs/Control-Monad-Signatures.html#t:CallCC) -- provided that @f@ is quasi-algebraic. More specifically, for any @g@, we must have: ----- > 'join' '$' f (\exit -> 'pure' '$' g (exit '.' 'pure') = f g+-- @+-- 'join' '$' f (\\exit -> 'pure' '$' g (exit '.' 'pure') = f g+-- @ -- -- 'ContT.callCC' is quasi-algebraic; furthermore, for any quasi-algebraic @f@, -- @'liftCallCC' f@ is also quasi-algebraic. @@ -203,6 +211,10 @@ -- @since 2.3.1 liftCallCC :: forall (t :: (Type -> Type) -> Type -> Type) (m :: Type -> Type) (a :: Type) (b :: Type) . - (MonadTrans t, Monad m, forall (m' :: Type -> Type) . Monad m' => Monad (t m')) => + (MonadTrans t, Monad m+#if !MIN_VERSION_transformers(0,6,0) || defined(__MHS__)+ , forall (m' :: Type -> Type) . Monad m' => Monad (t m')+#endif+ ) => CallCC m (t m a) b -> CallCC (t m) a b liftCallCC f g = join . lift . f $ \exit -> pure $ g (lift . exit . pure)
Control/Monad/Error/Class.hs view
@@ -48,6 +48,7 @@ tryError, withError, handleError,+ onError, mapError, modifyError, ) where@@ -72,9 +73,10 @@ import qualified Control.Monad.Trans.Writer.CPS as CPSWriter import Control.Monad.Trans.Class (lift) import Control.Exception (IOException, catch, ioError)-import Control.Monad (Monad)+import Control.Monad (Monad ((>>=), (>>)))+import Data.Functor.Product (Product(..)) import Data.Monoid (Monoid)-import Prelude (Either (Left, Right), Maybe (Nothing), either, flip, (.), IO, pure, (<$>), (>>=))+import Prelude (Either (Left, Right), Maybe (Nothing), either, flip, (.), IO, pure, (<$>)) {- | The strategy of combining computations that can throw exceptions@@ -205,7 +207,17 @@ throwError = lift . throwError catchError = Accum.liftCatch catchError +-- | @since 2.3.2+instance (MonadError e m, MonadError e n) => MonadError e (Product m n) where+ throwError e = Pair (throwError e) (throwError e)+ catchError (Pair ma na) f = Pair (catchError ma (productFst . f)) (catchError na (productSnd . f))+ where+ productFst (Pair a _) = a+ productSnd (Pair _ b) = b+ -- | 'MonadError' analogue to the 'Control.Exception.try' function.+--+-- @since 2.3 tryError :: MonadError e m => m a -> m (Either e a) tryError action = (Right <$> action) `catchError` (pure . Left) @@ -213,17 +225,31 @@ -- Modify the value (but not the type) of an error. The type is -- fixed because of the functional dependency @m -> e@. If you need -- to change the type of @e@ use 'mapError' or 'modifyError'.+--+-- @since 2.3 withError :: MonadError e m => (e -> e) -> m a -> m a-withError f action = tryError action >>= either (throwError . f) pure+withError f = handleError (throwError . f) -- | As 'handle' is flipped 'Control.Exception.catch', 'handleError' -- is flipped 'catchError'.+--+-- @since 2.3 handleError :: MonadError e m => (e -> m a) -> m a -> m a handleError = flip catchError +-- | If an action throws an error, run a second action and rethrow the error.+-- If the second action also throws an error, it takes precedence. Do not run+-- the second action at all if the first succeeds.+--+-- @since 2.3.2+onError :: MonadError e m => m a -> m b -> m a+onError action1 action2 = action1 `catchError` \e -> action2 >> throwError e+ -- | 'MonadError' analogue of the 'mapExceptT' function. The -- computation is unwrapped, a function is applied to the @Either@, and -- the result is lifted into the second 'MonadError' instance.+--+-- @since 2.3 mapError :: (MonadError e m, MonadError e' n) => (m (Either e a) -> n (Either e' b)) -> m a -> n b mapError f action = f (tryError action) >>= liftEither
Control/Monad/Except.hs view
@@ -41,6 +41,7 @@ Error.tryError, Error.withError, Error.handleError,+ Error.onError, Error.mapError, Error.modifyError, -- * The ExceptT monad transformer
Control/Monad/RWS/Class.hs view
@@ -41,6 +41,7 @@ import qualified Control.Monad.Trans.RWS.CPS as CPS (RWST) import qualified Control.Monad.Trans.RWS.Lazy as Lazy (RWST) import qualified Control.Monad.Trans.RWS.Strict as Strict (RWST)+import Data.Functor.Product (Product(..)) class (Monoid w, MonadReader r m, MonadWriter w m, MonadState s m) => MonadRWS r w s m | m -> r, m -> w, m -> s@@ -62,3 +63,6 @@ instance MonadRWS r w s m => MonadRWS r w s (ExceptT e m) instance MonadRWS r w s m => MonadRWS r w s (IdentityT m) instance MonadRWS r w s m => MonadRWS r w s (MaybeT m)++-- | @since 2.3.2+instance (MonadRWS r w s m, MonadRWS r w s n) => MonadRWS r w s (Product m n)
Control/Monad/Reader/Class.hs view
@@ -69,6 +69,7 @@ import qualified Control.Monad.Trans.RWS.CPS as CPSRWS import qualified Control.Monad.Trans.Writer.CPS as CPS import Control.Monad.Trans.Class (lift)+import Data.Functor.Product (Product(..)) -- ---------------------------------------------------------------------------- -- class MonadReader@@ -202,3 +203,8 @@ r <- ask local f (runSelectT m (local (const r) . c)) reader = lift . reader++-- | @since 2.3.2+instance (MonadReader r m, MonadReader r n) => MonadReader r (Product m n) where+ ask = Pair ask ask+ local f (Pair ma na) = Pair (local f ma) (local f na)
Control/Monad/State/Class.hs view
@@ -52,6 +52,7 @@ import qualified Control.Monad.Trans.RWS.CPS as CPSRWS import qualified Control.Monad.Trans.Writer.CPS as CPS import Control.Monad.Trans.Class (lift)+import Data.Functor.Product (Product(..)) -- --------------------------------------------------------------------------- @@ -192,3 +193,9 @@ get = lift get put = lift . put state = lift . state++-- | @since 2.3.2+instance (MonadState s m, MonadState s n) => MonadState s (Product m n) where+ get = Pair get get+ put s = Pair (put s) (put s)+ state sas = Pair (state sas) (state sas)
Control/Monad/Writer/CPS.hs view
@@ -33,6 +33,8 @@ mapWriter, -- * The WriterT monad transformer WriterT,+ writerT,+ runWriterT, execWriterT, mapWriterT, module Control.Monad.Trans,@@ -42,4 +44,4 @@ import Control.Monad.Trans import Control.Monad.Trans.Writer.CPS ( Writer, runWriter, execWriter, mapWriter,- WriterT, execWriterT, mapWriterT)+ WriterT, writerT, runWriterT, execWriterT, mapWriterT)
Control/Monad/Writer/Class.hs view
@@ -48,6 +48,7 @@ import qualified Control.Monad.Trans.RWS.CPS as CPSRWS import qualified Control.Monad.Trans.Writer.CPS as CPS import Control.Monad.Trans.Class (lift)+import Data.Functor.Product (Product(..)) -- --------------------------------------------------------------------------- -- MonadWriter class@@ -205,3 +206,10 @@ tell = lift . tell listen = Accum.liftListen listen pass = Accum.liftPass pass++-- | @since 2.3.2+instance (MonadWriter w m, MonadWriter w n) => MonadWriter w (Product m n) where+ writer aw = Pair (writer aw) (writer aw)+ tell w = Pair (tell w) (tell w)+ listen (Pair ma na) = Pair (listen ma) (listen na)+ pass (Pair maf naf) = Pair (pass maf) (pass naf)
README.markdown view
@@ -1,4 +1,4 @@-# `mtl` [](https://hackage.haskell.org/package/mtl) [](https://travis-ci.org/haskell/mtl)+# `mtl` [](https://hackage.haskell.org/package/mtl) MTL is a collection of monad classes, extending the `transformers` package, using functional dependencies for generic lifting of monadic
mtl.cabal view
@@ -1,12 +1,11 @@ cabal-version: 3.0 name: mtl-version: 2.3.1+version: 2.3.2 license: BSD-3-Clause license-file: LICENSE author: Andy Gill-maintainer: chessai <chessai1996@gmail.com>,- Emily Pillmore <emilypi@cohomolo.gy>,- Koz Ross <koz.ross@retro-freedom.nz>+maintainer: Koz Ross <koz.ross@retro-freedom.nz>+ Steven Shuck <stevenjshuck@gmail.com> category: Control synopsis: Monad classes for transformers, using functional dependencies homepage: http://github.com/haskell/mtl@@ -19,10 +18,12 @@ build-type: Simple extra-source-files:- CHANGELOG.markdown README.markdown -tested-with: GHC ==8.6.5 || ==8.8.4 || ==8.10.7 || ==9.0.2 || ==9.2.4 || ==9.4.1+extra-doc-files:+ CHANGELOG.markdown++tested-with: GHC ==8.10 || ==9.2 || ==9.8 || ==9.10 || ==9.12, MHS ==0.14.15.0 source-repository head type: git