packages feed

pipes-safe 2.2.0 → 2.2.1

raw patch · 4 files changed

+120/−31 lines, 4 filesdep ~exceptionsPVP ok

version bump matches the API change (PVP)

Dependency ranges changed: exceptions

API changes (from Hackage documentation)

Files

+ README.md view
@@ -0,0 +1,84 @@+# Pipes-Safe v2.2.0++`pipes-safe` builds upon+[the `pipes` library](https://github.com/Gabriel439/Haskell-Pipes-Library) to+provide exception safety and resource management.++## Quick start++* Install the [Haskell Platform](http://www.haskell.org/platform/)+* `cabal install pipes-safe`++The official tutorial is on+[Hackage](http://hackage.haskell.org/package/pipes-safe).++## Features++* *Resource Safety*: Guarantee finalization using `finally`, `bracket`, and more++* *Exception Safety*: Even against asynchronous exceptions!++* *Laziness*: Only acquire resources when you need them++* *Promptness*: Finalize resources early when you are done with them++* *Native Exception Handling*: Catch and resume from exceptions inside pipes++* *No Buy-in*: Mix resource-safe pipes with unmanaged pipes using `hoist`++## Outline++Use `pipes-safe` for production code where you need deterministic and prompt+release of resources in the fact of exceptions or premature pipe termination.+`pipes-safe` lets you safely acquire resources and handle exceptions within+pipelines.++## Development Status++`pipes-safe` is mostly stable.  Research into prompter finalization alternatives+will take place in a separate library.++## Community Resources++Use the same resources as the core `pipes` library to learn more, contribute, or+request help:++* [Haskell wiki page](http://www.haskell.org/haskellwiki/Pipes)++* [Mailing list](mailto:haskell-pipes@googlegroups.com) ([Google Group](https://groups.google.com/forum/?fromgroups#!forum/haskell-pipes))++## How to contribute++* Build derived libraries++* Write `pipes-safe` tutorials++## License (BSD 3-clause)++Copyright (c) 2013 Gabriel Gonzalez+All rights reserved.++Redistribution and use in source and binary forms, with or without modification,+are permitted provided that the following conditions are met:++* Redistributions of source code must retain the above copyright notice, this+  list of conditions and the following disclaimer.++* Redistributions in binary form must reproduce the above copyright notice, this+  list of conditions and the following disclaimer in the documentation and/or+  other materials provided with the distribution.++* Neither the name of Gabriel Gonzalez nor the names of other contributors may+  be used to endorse or promote products derived from this software without+  specific prior written permission.++THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR+ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON+ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ changelog.md view
@@ -0,0 +1,3 @@+# Version 2.2.1++* Raise upper-bound on `exceptions` dependency.
pipes-safe.cabal view
@@ -1,9 +1,10 @@ Name: pipes-safe-Version: 2.2.0+Version: 2.2.1 Cabal-Version: >=1.8.0.2 Build-Type: Simple License: BSD3 License-File: LICENSE+Extra-Source-Files: README.md changelog.md Copyright: 2013, 2014 Gabriel Gonzalez Author: Gabriel Gonzalez Maintainer: Gabriel439@gmail.com@@ -36,7 +37,7 @@     Build-Depends:         base         >= 4       && < 5  ,         containers   >= 0.3.0.0 && < 0.6,-        exceptions   >= 0.6     && < 0.7,+        exceptions   >= 0.6     && < 0.8,         transformers >= 0.2.0.0 && < 0.5,         pipes        >= 4.0.0   && < 4.2     Exposed-Modules:
src/Pipes/Safe.hs view
@@ -123,7 +123,7 @@ import qualified Data.Map as M import Data.Monoid (Monoid) import Pipes (Proxy, Effect, Effect', runEffect)-import Pipes.Internal (unsafeHoist, Proxy(..))+import Pipes.Internal (Proxy(..)) import Pipes.Lift (liftCatchError)  data Restore m = Unmasked | Masked (forall x . m x -> m x)@@ -134,34 +134,35 @@     -> ((forall x . Proxy a' a b' b m x -> Proxy a' a b' b m x)         -> Proxy a' a b' b m r)     -> Proxy a' a b' b m r-liftMask maskFunction k = do-        ioref <- liftIO (newIORef Unmasked)-        let unmask-                :: forall y . (Monad m)-                => Proxy a' a b' b m y -> Proxy a' a b' b m y-            unmask p = do-                mRestore <- liftIO (readIORef ioref)-                case mRestore of-                    Unmasked       -> p-                    Masked restore -> do-                        r <- unsafeHoist restore p-                        lift $ restore $ return ()-                        return r-            loop p = case p of-                Request a' fa  -> Request a' (loop . fa )-                Respond b  fb' -> Respond b  (loop . fb')-                M m0           -> M $ maskFunction $ \restore -> do-                    liftIO $ writeIORef ioref (Masked restore)-                    let loop' m = do-                            p' <- m-                            case p' of-                                M m' -> loop' m'-                                _    -> return p'-                    p' <- loop' m0-                    liftIO $ writeIORef ioref  Unmasked-                    return (loop p')-                Pure r         -> Pure r-        loop (k unmask)+liftMask maskVariant k = do+    ioref <- liftIO $ newIORef Unmasked++    let -- mask adjacent actions in base monad+        loop :: Proxy a' a b' b m r -> Proxy a' a b' b m r+        loop (Request a' fa ) = Request a' (loop . fa )+        loop (Respond b  fb') = Respond b  (loop . fb')+        loop (M m)            = M $ maskVariant $ \unmaskVariant -> do+            -- stash base's unmask and merge action+            liftIO $ writeIORef ioref $ Masked unmaskVariant+            m >>= chunk >>= return . loop+        loop (Pure r)         = Pure r++        -- unmask adjacent actions in base monad+        unmask :: forall q. Proxy a' a b' b m q -> Proxy a' a b' b m q+        unmask (Request a' fa ) = Request a' (unmask . fa )+        unmask (Respond b  fb') = Respond b  (unmask . fb')+        unmask (M m)            = M $ do+            -- retrieve base's unmask and apply to merged action+            Masked unmaskVariant <- liftIO $ readIORef ioref+            unmaskVariant (m >>= chunk >>= return . unmask)+        unmask (Pure q)         = Pure q++        -- merge adjacent actions in base monad+        chunk :: forall s. Proxy a' a b' b m s -> m (Proxy a' a b' b m s)+        chunk (M m) = m >>= chunk+        chunk s     = return s++    loop $ k unmask  instance (MonadThrow m) => MonadThrow (Proxy a' a b' b m) where     throwM = lift . throwM