module Wobsurv.Util.PartialHandler where
import BasePrelude
newtype PartialHandler a =
PartialHandler (SomeException -> Maybe (IO a))
instance Monoid (PartialHandler a) where
mempty =
PartialHandler $ const Nothing
mappend (PartialHandler h1) (PartialHandler h2) =
PartialHandler $ \e -> h1 e <|> h2 e
typed :: Exception e => (e -> Maybe (IO a)) -> PartialHandler a
typed h =
PartialHandler $ \e ->
case fromException e of
Just e' -> h e'
Nothing -> Nothing
toTotal :: PartialHandler a -> (SomeException -> IO a)
toTotal (PartialHandler h) =
\e -> fromMaybe (throwIO e) (h e)
onThreadKilled :: IO a -> PartialHandler a
onThreadKilled io =
typed $ \case
ThreadKilled -> Just io
_ -> Nothing
rethrowTo :: ThreadId -> PartialHandler ()
rethrowTo t =
PartialHandler $ \e -> Just (throwTo t e)
forkFinallyRethrowing :: IO () -> PartialHandler () -> IO () -> IO ThreadId
forkFinallyRethrowing performer handler releaser =
do
t <- myThreadId
forkFinally performer $ \r -> do
releaser
either (toTotal (handler <> rethrowTo t)) return r