Notice how I must use a nested block_on
call:
#[test]
fn create_cnac() {
block_on( async {
load_node_nac().await.and_then(|mut node_nac| {
println!("Loaded NAC with nid {}", node_nac.get_id());
block_on( async { match node_nac.create_client_account(None, false,"tbraun96", "mrmoney10", "Thomas P Braun").await {
Ok(mut cnac) => {
println!("CNAC successfully constructed. Saving to hard drive");
let mut write = cnac.write();
for _ in 0..100 {
write.toolset.update().await.and_then(|_|{
//println!("Update done");
Ok(())
});
}
std::mem::drop(write);
match cnac.save_to_disk() {
Ok(_) => {
println!("Saved CNAC to disk successfully");
},
Err(err) => {
println!("ERR: {}", err.to_string());
}
}
},
Err(err) => {
println!("ERR: {}", err.to_string());
}
}});
Ok(())
})
});
}
Of course, this panics during runtime because we can't have nested executors:
thread 'tests::create_cnac' panicked at 'cannot execute `LocalPool` executor from within another executor: EnterError'
This is me trying to work-around the error caused when I go with the naive approach:
#[test]
fn create_cnac() {
block_on( async {
// notice below how I get rid of block_on, and try to do an inner async closure
load_node_nac().await.and_then(|mut node_nac| async {
println!("Loaded NAC with nid {}", node_nac.get_id());
match node_nac.create_client_account(None, false,"tbraun96", "mrmoney10", "Thomas P Braun").await {
Ok(mut cnac) => {
println!("CNAC successfully constructed. Saving to hard drive");
let mut write = cnac.write();
for _ in 0..100 {
write.toolset.update().await.and_then(|_|{
//println!("Update done");
Ok(())
});
}
std::mem::drop(write);
match cnac.save_to_disk() {
Ok(_) => {
println!("Saved CNAC to disk successfully");
},
Err(err) => {
println!("ERR: {}", err.to_string());
}
}
},
Err(err) => {
println!("ERR: {}", err.to_string());
}
}
})
});
}
And this causes the compile-time error:
'await' is only allowed inside 'async' functions and blocks
Sure, I could fire-up a ThreadPool
and pass around the handle which implements Spawn + Clone
, and then pass the futures into it, but I was wondering if there is a clean way of doing async functional programming
?