I am using the Warp crate for a web service, but I am having problems getting it running from my non-async main.
I have tried several ways and the closest I have gotten is this:
Cargo.toml
[dependencies]
warp = "0.3"
futures = "0.3"
Code:
use std::collections::HashMap;
use std::thread::{sleep, spawn};
use std::time;
use warp::{Filter};
use futures::executor::block_on;
async fn get_ap_list() -> Result<impl warp::Reply, warp::Rejection> {
let mut result = HashMap::new();
// TODO: Get a full list
result.insert("SSID", "rossless_24");
Ok(warp::reply::json(&result))
}
async fn start_ap_server() {
println!("AP server");
let get_ap = warp::get()
.and(warp::path("ap"))
.and(warp::path("list"))
.and(warp::path::end())
.and_then(get_ap_list);
warp::serve(get_ap)
.run(([0, 0, 0, 0], 3030))
.await;
}
// This intermediate function seem a bit redundant but I can't seem to spawn the async server directly
fn init_ap_server() {
println!("Init AP server");
let future = start_ap_server();
block_on(future);
}
fn main() {
let _t1 = spawn(move || {
init_ap_server()
});
// Make sure main is still running
loop {
println!("Alive for test.");
sleep(time::Duration::from_millis(5000));
}
}
That seems to work but I get:
thread '<unnamed>' panicked at 'there is no reactor running, must be called from the context of a Tokio 1.x runtime', /home/tross/.cargo/registry/src/github.com-1ecc6299db9ec823/tokio-1.5.0/src/runtime/context.rs:18:26
Googling around I see that it is probably a Tokio version mismatch, but I don't even have Tokio in my dependencies, I am getting it from Warp.
Taking a step back, is there a simpler way to get what I want? I just want to launch some async code running (probably on its own thread) while leaving main alive and happy.
warpitself does pull in thetokiodependency but it does not come with thertfeature:So there is no runtime to execute the futures on. In order to get a
tokio::Runtimeyou can explicitly spawn aRuntimeand callblock_onon that runtime:with: