为了将minimumNumberOfTouches
方法与async / task
actor系统集成,我编写了以下方法
akkling
它基于有关如何将参与者与异步工作流集成的建议(此处为示例https://github.com/Horusiath/Akkling/blob/0b5b0ffa4cd516407706ed230f81915452cdb183/tests/Akkling.Tests/Actors.fs#L124)
但是,如果异步方法抛出异常,那么该问题将由父主管不处理
我希望这段代码可以工作,但不能
let actorOfTask (t: 'a -> Task<'b>) =
(fun (ctx: Actor<_>) ->
let rec loop() =
actor {
let! data = ctx.Receive()
task {
try
let! t' = data |> t
return t'
with e ->
// TODO : Raise exception in order to supervisor can catch it
printf "Exception %O" e
return raise e
}
|> Async.AwaitTask
|!> ctx.Sender()
}
loop())
尽管如果常规角色流中发生异常(未与async集成),则该主管会处理该异常。
任何建议如何解决?
谢谢
答案 0 :(得分:1)
来自Akka.Net文档
https://getakka.net/articles/actors/receive-actor-api.html
WARNING
To complete the Task with an exception you need send a Failure message to the sender. This is not done automatically when an actor throws an exception while processing a message.
try
{
var result = operation();
Sender.Tell(result, Self);
}
catch (Exception e)
{
Sender.Tell(new Failure { Exception = e }, Self);
}
所以演员应该这样实现
let actorOfTask (sendTo: IActorRef<_>) (t: 'a -> Task<_>) =
(fun (ctx: Actor<_>) ->
let rec loop() =
actor {
let! data = ctx.Receive()
task {
try
let! t' = data |> t
return t' :> obj
with e ->
return Akka.Actor.Failure(Exception = e) :> obj
}
|> Async.AwaitTask
|!> (retype sendTo)
}
loop())