Safe Haskell | Safe-Inferred |
---|---|
Language | Haskell2010 |
Synopsis
- resumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable err eff) r
- raiseResumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). InterpreterTrans (Resumable err eff) eff r
- resumableIO :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). Exception (StopExc err) => Member (Final IO) r => InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable err eff) r
- interpretResumableH :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) -> InterpreterFor (Resumable err eff) r
- interpretResumable :: forall (err :: Type) (eff :: Effect) r. FirstOrder eff "interpretResumable" => (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> InterpreterFor (Resumable err eff) r
- interceptResumableUsingH :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). ElemOf (Resumable err eff) r -> (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) -> Sem r a -> Sem r a
- interceptResumableUsing :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). FirstOrder eff "interceptResumableUsing" => ElemOf (Resumable err eff) r -> (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> Sem r a -> Sem r a
- interceptResumableH :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). Member (Resumable err eff) r => (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) -> Sem r a -> Sem r a
- interceptResumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). Member (Resumable err eff) r => FirstOrder eff "interceptResumable" => (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> Sem r a -> Sem r a
- resumableError :: forall (err :: Type) (eff :: Effect) r. InterpreterFor eff (Error err ': (Stop err ': r)) -> InterpreterFor (Resumable err eff) r
- resumableOr :: forall (err :: Type) (eff :: Effect) unhandled handled r. Member (Error unhandled) r => (err -> Either unhandled handled) -> InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable handled eff) r
- resumableFor :: forall (err :: Type) (eff :: Effect) handled r. Member (Error err) r => (err -> Maybe handled) -> InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable handled eff) r
- catchResumable :: forall (err :: Type) (eff :: Effect) handled r. Members [eff, Error err] r => (err -> Maybe handled) -> InterpreterFor (Resumable handled eff) r
- runAsResumable :: forall (err :: Type) (eff :: Effect) r. Members [Resumable err eff, Stop err] r => InterpreterFor eff r
Documentation
resumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable err eff) r Source #
Convert a bare interpreter for eff
, which (potentially) uses Stop
to signal errors, into an interpreter for
Resumable
.
Beware: This will display unsound behaviour if:
* the interpreter is wrapped with actions of another effect, as in:
interpretEff :: InterpreterFor Eff r
...
interpretEffResumable :: InterpreterFor (Resumable Text Eff) r
interpretEffResumable sem =
resumable (interpretEff (sem finally
releaseResources))
In this case, releaseResources
will be called after every use of Eff
in sem
, not after the entire thunk.
- the interpreter of a higher-order effect uses a different interpreter after using
runT
/bindT
. In this case, it will use the original interpreter instead.
If your use case matches one of these conditions, you'll need to use interpretResumable
.
>>>
run $ resumable interpretStopper (interpretResumer mainProgram)
237
raiseResumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). InterpreterTrans (Resumable err eff) eff r Source #
resumableIO :: forall (err :: Type) (eff :: Effect) (r :: EffectRow). Exception (StopExc err) => Member (Final IO) r => InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable err eff) r Source #
:: forall (err :: Type) (eff :: Effect) (r :: EffectRow). (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) | This handler function has |
-> InterpreterFor (Resumable err eff) r |
Like interpretResumable
, but for higher-order effects.
interpretResumable :: forall (err :: Type) (eff :: Effect) r. FirstOrder eff "interpretResumable" => (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> InterpreterFor (Resumable err eff) r Source #
Create an interpreter for
by supplying a handler function for Resumable
err effeff
, analogous to
interpret
.
If the handler throws errors with Stop
, they will be absorbed into Resumable
, to be caught by
resume
in a downstream interpreter.
interpretStopperResumable :: InterpreterFor Stopper r interpretStopperResumable = interpretResumable \case StopBang -> stop (Bang 13) StopBoom -> stop (Boom "ouch")
>>>
run $ interpretStopperResumable (interpretResumer mainProgram)
237
interceptResumableUsingH :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). ElemOf (Resumable err eff) r -> (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) -> Sem r a -> Sem r a Source #
Interceptor variant of interpretResumableH
.
interceptResumableUsing :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). FirstOrder eff "interceptResumableUsing" => ElemOf (Resumable err eff) r -> (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> Sem r a -> Sem r a Source #
Interceptor variant of interpretResumable
.
interceptResumableH :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). Member (Resumable err eff) r => (forall x r0. eff (Sem r0) x -> Tactical (Resumable err eff) (Sem r0) (Stop err ': r) x) -> Sem r a -> Sem r a Source #
Interceptor variant of interpretResumableH
.
interceptResumable :: forall (err :: Type) (eff :: Effect) (r :: EffectRow) (a :: Type). Member (Resumable err eff) r => FirstOrder eff "interceptResumable" => (forall x r0. eff (Sem r0) x -> Sem (Stop err ': r) x) -> Sem r a -> Sem r a Source #
Interceptor variant of interpretResumable
.
resumableError :: forall (err :: Type) (eff :: Effect) r. InterpreterFor eff (Error err ': (Stop err ': r)) -> InterpreterFor (Resumable err eff) r Source #
resumableOr :: forall (err :: Type) (eff :: Effect) unhandled handled r. Member (Error unhandled) r => (err -> Either unhandled handled) -> InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable handled eff) r Source #
Convert an interpreter for eff
that throws errors of type err
into a Resumable
, but limiting the errors
handled by consumers to the type handled
, which rethrowing Error
s of type unhandled
.
The function canHandle
determines how the errors are split.
newtype Blip = Blip { unBlip :: Int } deriving (Eq, Show) bangOnly :: Boom -> Either Text Blip bangOnly = \case Bang n -> Right (Blip n) Boom msg -> Left msg interpretResumerPartial :: Member (Resumable Blip Stopper) r => InterpreterFor Resumer r interpretResumerPartial = interpret \ MainProgram -> resume (192 <$ stopBang) \ (Blip num) -> pure (num * 3)
>>>
runError (resumableFor bangOnly interpretStopper (interpretResumerPartial mainProgram))
Right 39
resumableFor :: forall (err :: Type) (eff :: Effect) handled r. Member (Error err) r => (err -> Maybe handled) -> InterpreterFor eff (Stop err ': r) -> InterpreterFor (Resumable handled eff) r Source #
Variant of resumableOr
that uses Maybe
and rethrows the original error.
catchResumable :: forall (err :: Type) (eff :: Effect) handled r. Members [eff, Error err] r => (err -> Maybe handled) -> InterpreterFor (Resumable handled eff) r Source #
Reinterpreting variant of resumableFor
.
runAsResumable :: forall (err :: Type) (eff :: Effect) r. Members [Resumable err eff, Stop err] r => InterpreterFor eff r Source #
Interpret an effect eff
by wrapping it in Resumable
and Stop
and leaving the rest up to the user.