packages feed

Concurrent-Cache 0.2.1.0 → 0.2.2.0

raw patch · 2 files changed

+14/−11 lines, 2 filesPVP ok

version bump matches the API change (PVP)

API changes (from Hackage documentation)

Files

Concurrent-Cache.cabal view
@@ -2,7 +2,7 @@ -- documentation, see http://haskell.org/cabal/users-guide/  name:                Concurrent-Cache-version:             0.2.1.0+version:             0.2.2.0 synopsis:            A Cached variable for IO functions. description:         This package allows for caching IO functions, either on a                      timeout or designed to only fetch once.
Control/Concurrent/Cache.hs view
@@ -1,16 +1,16 @@ module Control.Concurrent.Cache (CachedData, fetch, fetchCached, createReadOnceCache, createTimedCache) where  import Data.Maybe (isNothing)-import Control.Concurrent (forkIO, threadDelay, killThread, MVar, modifyMVar_, readMVar, ThreadId, newMVar)+import Control.Concurrent (forkIO, threadDelay, killThread, MVar, modifyMVar_, readMVar, ThreadId, newMVar, mkWeakMVar)+import System.Mem.Weak (deRefWeak, Weak) import Control.Monad (when, liftM)  data Timeout = TimeSinceCreation Int | TimeSinceLastRead Int +type TimedCachedDataMVar a = MVar (Maybe ThreadId, IO a, Maybe a) -data CachedData a = TimedCachedData (Timeout, (MVar (Maybe ThreadId, IO a, Maybe a))) | ReadOnceCachedData (MVar (Either (IO a) a))+data CachedData a = TimedCachedData Timeout (TimedCachedDataMVar a) (Weak (TimedCachedDataMVar a)) | ReadOnceCachedData (MVar (Either (IO a) a)) --- |Only fetch data iff it has been cached. Useful for example when--- a database connection is being cached, and it has to be closed when it--- is no longer needed, but should not be opened just to be closed.+-- |Only fetch data if it has been cached. fetchCached :: CachedData a             -> IO (Maybe a) fetchCached (ReadOnceCachedData mvar) = do@@ -19,11 +19,14 @@                   Left _ -> Nothing                   Right value -> Just value -fetchCached (TimedCachedData (timeout, mvar)) = do+fetchCached (TimedCachedData timeout mvar weakMVar) = do   (_,_,value) <- readMVar mvar   modifyMVar_ mvar $ \mvar'@(thread', action', value') -> do     let newThread x = do threadDelay x-                         modifyMVar_ mvar $ \(_, action'', _) -> return (Nothing, action'', Nothing)+                         dereffed <- deRefWeak weakMVar+                         case dereffed of+                              Just mvar'' -> modifyMVar_ mvar'' $ \(_, action'', _) -> return (Nothing, action'', Nothing)+                              Nothing -> return ()     case timeout of          TimeSinceLastRead time -> do            when (not $ isNothing thread') $ let Just thread'' = thread' in killThread thread''@@ -38,7 +41,6 @@  -- |Fetch data from a cache fetch :: CachedData a-      -- ^ @Cache@, the cache to fetch a value from       -> IO (a) fetch state@(ReadOnceCachedData mvar) = go where   go = do@@ -51,7 +53,7 @@         go       Just value -> return value -fetch state@(TimedCachedData (timeout, mvar)) = go where+fetch state@(TimedCachedData timeout mvar _) = go where   go = do     cached <- fetchCached state     case cached of@@ -92,4 +94,5 @@   let timeout' = if resetOnRead                    then TimeSinceLastRead timeout                    else TimeSinceCreation timeout-  return $ TimedCachedData (timeout', var)+  weakMVar <- mkWeakMVar var $ return ()+  return $ TimedCachedData timeout' var weakMVar