packages feed

async 2.0.2 → 2.1.0

raw patch · 3 files changed

+149/−62 lines, 3 filesdep ~basePVP ok

version bump matches the API change (PVP)

Dependency ranges changed: base

API changes (from Hackage documentation)

- Control.Concurrent.Async: instance Alternative Concurrently
- Control.Concurrent.Async: instance Applicative Concurrently
- Control.Concurrent.Async: instance Eq (Async a)
- Control.Concurrent.Async: instance Functor Async
- Control.Concurrent.Async: instance Functor Concurrently
- Control.Concurrent.Async: instance Monad Concurrently
- Control.Concurrent.Async: instance Ord (Async a)
- Control.Concurrent.Async: runConcurrently :: Concurrently a -> IO a
+ Control.Concurrent.Async: [runConcurrently] :: Concurrently a -> IO a
+ Control.Concurrent.Async: forConcurrently :: Traversable t => t a -> (a -> IO b) -> IO (t b)
+ Control.Concurrent.Async: instance GHC.Base.Alternative Control.Concurrent.Async.Concurrently
+ Control.Concurrent.Async: instance GHC.Base.Applicative Control.Concurrent.Async.Concurrently
+ Control.Concurrent.Async: instance GHC.Base.Functor Control.Concurrent.Async.Async
+ Control.Concurrent.Async: instance GHC.Base.Functor Control.Concurrent.Async.Concurrently
+ Control.Concurrent.Async: instance GHC.Base.Monoid a => GHC.Base.Monoid (Control.Concurrent.Async.Concurrently a)
+ Control.Concurrent.Async: instance GHC.Classes.Eq (Control.Concurrent.Async.Async a)
+ Control.Concurrent.Async: instance GHC.Classes.Ord (Control.Concurrent.Async.Async a)
+ Control.Concurrent.Async: waitAnyCatchSTM :: [Async a] -> STM (Async a, Either SomeException a)
+ Control.Concurrent.Async: waitAnySTM :: [Async a] -> STM (Async a, a)
+ Control.Concurrent.Async: waitBothSTM :: Async a -> Async b -> STM (a, b)
+ Control.Concurrent.Async: waitEitherCatchSTM :: Async a -> Async b -> STM (Either (Either SomeException a) (Either SomeException b))
+ Control.Concurrent.Async: waitEitherSTM :: Async a -> Async b -> STM (Either a b)
+ Control.Concurrent.Async: waitEitherSTM_ :: Async a -> Async b -> STM ()

Files

Control/Concurrent/Async.hs view
@@ -105,11 +105,17 @@     waitEither_,     waitBoth, +    -- ** Waiting for multiple 'Async's in STM+    waitAnySTM, waitAnyCatchSTM,+    waitEitherSTM, waitEitherCatchSTM,+    waitEitherSTM_,+    waitBothSTM,+     -- ** Linking     link, link2,      -- * Convenient utilities-    race, race_, concurrently, mapConcurrently,+    race, race_, concurrently, mapConcurrently, forConcurrently,     Concurrently(..),    ) where@@ -122,8 +128,15 @@ #endif import Control.Monad import Control.Applicative+#if !MIN_VERSION_base(4,8,0)+import Data.Monoid (Monoid(mempty,mappend)) import Data.Traversable+#endif+#if MIN_VERSION_base(4,9,0)+import Data.Semigroup (Semigroup((<>)))+#endif + import GHC.Exts import GHC.IO hiding (finally, onException) import GHC.Conc@@ -316,9 +329,15 @@ -- If multiple 'Async's complete or have completed, then the value -- returned corresponds to the first completed 'Async' in the list. --+{-# INLINE waitAnyCatch #-} waitAnyCatch :: [Async a] -> IO (Async a, Either SomeException a)-waitAnyCatch asyncs =-  atomically $+waitAnyCatch = atomically . waitAnyCatchSTM++-- | A version of 'waitAnyCatch' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitAnyCatchSTM :: [Async a] -> STM (Async a, Either SomeException a)+waitAnyCatchSTM asyncs =     foldr orElse retry $       map (\a -> do r <- waitCatchSTM a; return (a, r)) asyncs @@ -336,9 +355,15 @@ -- If multiple 'Async's complete or have completed, then the value -- returned corresponds to the first completed 'Async' in the list. --+{-# INLINE waitAny #-} waitAny :: [Async a] -> IO (Async a, a)-waitAny asyncs =-  atomically $+waitAny = atomically . waitAnySTM++-- | A version of 'waitAny' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitAnySTM :: [Async a] -> STM (Async a, a)+waitAnySTM asyncs =     foldr orElse retry $       map (\a -> do r <- waitSTM a; return (a, r)) asyncs @@ -350,11 +375,19 @@   waitAny asyncs `finally` mapM_ cancel asyncs  -- | Wait for the first of two @Async@s to finish.+{-# INLINE waitEitherCatch #-} waitEitherCatch :: Async a -> Async b                 -> IO (Either (Either SomeException a)                               (Either SomeException b))-waitEitherCatch left right =-  atomically $+waitEitherCatch left right = atomically (waitEitherCatchSTM left right)++-- | A version of 'waitEitherCatch' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitEitherCatchSTM :: Async a -> Async b+                -> STM (Either (Either SomeException a)+                               (Either SomeException b))+waitEitherCatchSTM left right =     (Left  <$> waitCatchSTM left)       `orElse`     (Right <$> waitCatchSTM right)@@ -372,18 +405,30 @@ -- that finished first raised an exception, then the exception is -- re-thrown by 'waitEither'. --+{-# INLINE waitEither #-} waitEither :: Async a -> Async b -> IO (Either a b)-waitEither left right =-  atomically $+waitEither left right = atomically (waitEitherSTM left right)++-- | A version of 'waitEither' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitEitherSTM :: Async a -> Async b -> STM (Either a b)+waitEitherSTM left right =     (Left  <$> waitSTM left)       `orElse`     (Right <$> waitSTM right)  -- | Like 'waitEither', but the result is ignored. --+{-# INLINE waitEither_ #-} waitEither_ :: Async a -> Async b -> IO ()-waitEither_ left right =-  atomically $+waitEither_ left right = atomically (waitEitherSTM_ left right)++-- | A version of 'waitEither_' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitEitherSTM_:: Async a -> Async b -> STM ()+waitEitherSTM_ left right =     (void $ waitSTM left)       `orElse`     (void $ waitSTM right)@@ -399,9 +444,15 @@ -- an exception before they have both finished, then the exception is -- re-thrown by 'waitBoth'. --+{-# INLINE waitBoth #-} waitBoth :: Async a -> Async b -> IO (a,b)-waitBoth left right =-  atomically $ do+waitBoth left right = atomically (waitBothSTM left right)++-- | A version of 'waitBoth' that can be used inside an STM transaction.+--+-- @since 2.1.0+waitBothSTM :: Async a -> Async b -> STM (a,b)+waitBothSTM left right = do     a <- waitSTM left            `orElse`          (waitSTM right >> retry)@@ -519,7 +570,9 @@                              `catchAll` (putMVar done . Left)         rid <- forkIO $ restore (right >>= putMVar done . Right . Right)                              `catchAll` (putMVar done . Left)-        let stop = killThread lid >> killThread rid+        let stop = killThread rid >> killThread lid+                   -- kill right before left, to match the semantics of+                   -- the version using withAsync. (#27)         r <- restore (collect done) `onException` stop         stop         return r@@ -538,6 +591,14 @@ mapConcurrently :: Traversable t => (a -> IO b) -> t a -> IO (t b) mapConcurrently f = runConcurrently . traverse (Concurrently . f) +-- | `forConcurrently` is `mapConcurrently` with its arguments flipped+--+-- > pages <- forConcurrently ["url1", "url2", "url3"] $ \url -> getURL url+--+-- @since 2.1.0+forConcurrently :: Traversable t => t a -> (a -> IO b)-> IO (t b)+forConcurrently = flip mapConcurrently+ -- -----------------------------------------------------------------------------  -- | A value of type @Concurrently a@ is an @IO@ operation that can be@@ -571,10 +632,23 @@   Concurrently as <|> Concurrently bs =     Concurrently $ either id id <$> race as bs -instance Monad Concurrently where-  return = pure-  Concurrently a >>= f =-    Concurrently $ a >>= runConcurrently . f+#if MIN_VERSION_base(4,9,0)+-- | Only defined by @async@ for @base >= 4.9@+--+-- @since 2.1.0+instance Semigroup a => Semigroup (Concurrently a) where+  (<>) = liftA2 (<>)++-- | @since 2.1.0+instance (Semigroup a, Monoid a) => Monoid (Concurrently a) where+  mempty = pure mempty+  mappend = (<>)+#else+-- | @since 2.1.0+instance Monoid a => Monoid (Concurrently a) where+  mempty = pure mempty+  mappend = liftA2 mappend+#endif  -- ---------------------------------------------------------------------------- 
async.cabal view
@@ -1,4 +1,6 @@ name:                async+version:             2.1.0+-- don't forget to update ./changelog.md! synopsis:            Run IO operations asynchronously and wait for their results  description:@@ -21,47 +23,7 @@  * The API makes it possible to build a tree of    threads that are automatically killed when    their parent dies (see 'withAsync').- .- Changes in 2.0.2:- .- * Add a Monad instance for Concurrently- * Bump base dependency to allow 4.9- .- Changes in 2.0.1.6:- .- * Add workaround to waitCatch for #14- .- Changes in 2.0.1.5:- .- * Bump @base@ dependencies for GHC 7.8- .- Changes in 2.0.1.4:- .- * Bump @base@ dependency of test suite- .- Changes in 2.0.1.3:- .- * Bump @base@ dependency to allow 4.6- .- Changes in 2.0.1.2:- .- * Bump @stm@ dependency to 2.4- .- Changes in 2.0.1.1:- .- * Safe Haskell support: @Control.Concurrent.Async@ is now @Trustworthy@- .- Changes in 2.0.1.0:- .- * Added a @Functor@ instance for @Async@- .- * Added @asyncBound@, @asyncOn@, @asyncWithUnmask@, @asyncOnWithUnmask@, @withAsyncBound@, @withAsyncOn@, @withAsyncWithUnmask@, @withAsyncOnWithUnmask@.- .- * Added @mapConcurrently@- .- * Added @Concurrently@ (with @Applicative@ and @Alternative@ instances) -version:             2.0.2 license:             BSD3 license-file:        LICENSE author:              Simon Marlow@@ -69,12 +31,13 @@ copyright:           (c) Simon Marlow 2012 category:            Concurrency build-type:          Simple-cabal-version:       >=1.8+cabal-version:       >=1.10 homepage:            https://github.com/simonmar/async bug-reports:         https://github.com/simonmar/async/issues-tested-with:         GHC==7.0.3, GHC==7.2.2, GHC==7.4.1+tested-with:         GHC==7.11.*, GHC==7.10.3, GHC==7.8.4, GHC==7.6.3, GHC==7.4.2, GHC==7.2.2, GHC==7.0.4  extra-source-files:+    changelog.md     bench/race.hs  source-repository head@@ -82,14 +45,19 @@     location: https://github.com/simonmar/async.git  library+    default-language:    Haskell2010+    other-extensions:    CPP, MagicHash, RankNTypes, UnboxedTuples+    if impl(ghc>=7.1)+        other-extensions: Trustworthy     exposed-modules:     Control.Concurrent.Async-    build-depends:       base >= 4.3 && < 4.9, stm >= 2.2 && < 2.5+    build-depends:       base >= 4.3 && < 4.10, stm >= 2.2 && < 2.5  test-suite test-async+    default-language: Haskell2010     type:       exitcode-stdio-1.0     hs-source-dirs: test     main-is:    test-async.hs-    build-depends: base >= 4.3 && < 4.9,+    build-depends: base >= 4.3 && < 4.10,                    async,                    test-framework,                    test-framework-hunit,
+ changelog.md view
@@ -0,0 +1,45 @@+## Changes in 2.1.0:++ - Bump base dependency to allow 4.10+ - Remove invalid Monad instance for `Concurrently`+ - Add `Monoid` and `Semigroup` instances for `Concurrently`+ - Add `forConcurrently` (flipped version of `mapConcurrently`)+ - Add STM version of all applicable IO functions:+   `waitAnySTM`, `waitAnyCatchSTM`, `waitEitherSTM`,+   `waitEitherCatchSTM`, `waitEitherSTM_`, and `waitBothSTM`.++## Changes in 2.0.2:++ - Add a Monad instance for `Concurrently`+ - Bump base dependency to allow 4.9++## Changes in 2.0.1.6:++ - Add workaround to waitCatch for #14++## Changes in 2.0.1.5:++ - Bump `base` dependencies for GHC 7.8++## Changes in 2.0.1.4:++ - Bump `base` dependency of test suite++## Changes in 2.0.1.3:++ - Bump `base` dependency to allow 4.6++## Changes in 2.0.1.2:++ - Bump `stm` dependency to 2.4++## Changes in 2.0.1.1:++ - Safe Haskell support: `Control.Concurrent.Async` is now `Trustworthy`++## Changes in 2.0.1.0:++ - Added a `Functor` instance for `Async`+ - Added `asyncBound`, `asyncOn`, `asyncWithUnmask`, `asyncOnWithUnmask`, `withAsyncBound`, `withAsyncOn`, `withAsyncWithUnmask`, `withAsyncOnWithUnmask`.+ - Added `mapConcurrently`+ - Added `Concurrently` (with `Applicative` and `Alternative` instances)