Patterns
Ask
The Ask pattern allows values to be sent by actors to outside of the actor system. The value is delivered as a Future
.
Let's look at how this works:
use riker_patterns::ask;
struct MyActor;
impl Actor for MyActor {
type Msg = u32;
fn recv(&mut self,
ctx: &Context<Self::Msg>,
msg: Self::Msg,
sender: Sender) {
// sender is the Ask, waiting for a message to be sent back to it
sender.as_ref()
.unwrap()
.try_tell(msg * 2, Some(ctx.myself().into()));
}
}
fn main() {
let sys = ActorSystem::new().unwrap();
let props = Props::new::<MyActor>();
let my_actor = sys.actor_of_props(props, "my-actor");
// ask returns a future that automatically is driven
// to completion by the system.
let res: RemoteHandle<String> = ask(&sys, &my_actor, 100);
// the result future can be passed to a library or fuction that
// expects a future, or it can be extracted locally using `block_on`.
let res = block_on(res);
println!("The result value is: {}", res);
}
In the background Ask sets up a temporary intermediate actor that lives for the lifetime of the ask. Other actors see this temporary actor as the sender
and can send a message back to it. When the temporary ask actor receives a message it fulfills the outstanding future and performs a stop
on itself to cleanup.
Ask is particularly useful when you have part of an application that runs outside of the actor system, or in another actor system, such as a web server (e.g. Hyper) serving API requests. The resulting future can then be chained as part of the future stack.