1use crate::Router;
3use crate::get;
4use hyper::server::{Server, conn::AddrStream};
5use hyper::service::{make_service_fn, service_fn};
6use std::net::SocketAddr;
7use std::sync::Arc;
8use std::time::{SystemTime, UNIX_EPOCH};
9use tokio::sync::Mutex;
10
11impl Router {
12 pub async fn run(mut self, host: &str, port: u16) {
14 let addr: SocketAddr = format!("{}:{}", host, port)
15 .parse()
16 .expect("invalid socket address: invalid IP address syntax");
17
18 let pin = self.random();
19 let enable_logger = self.enable_logger;
20
21 if enable_logger {
22 let outputs = self.outputs.clone();
23 self = self.route(
24 "/debug",
25 get(move |query| {
26 let value = Arc::clone(&outputs);
27 async move {
28 let value = value.lock().unwrap();
29 if let Some(ipin) = query.get("pin") {
30 if ipin.parse::<u32>().unwrap_or(1000) == pin {
31 value.clone()
32 } else {
33 "401 Unauthorized".to_string()
34 }
35 } else {
36 "401 Unauthorized".to_string()
37 }
38 }
39 }),
40 );
41 }
42
43 if enable_logger {
44 self.log(&format!("Nimble server running on http://{}", addr));
45 self.log("Press Ctrl+C to stop");
46 self.log(&format!("Debug PIN: {}", pin));
47 }
48
49 let router = Arc::new(Mutex::new(self));
50
51 let make_svc = make_service_fn(move |conn: &AddrStream| {
52 let remote_addr = conn.remote_addr(); let router = router.clone();
55
56 async move {
57 Ok::<_, hyper::Error>(service_fn(move |mut req| {
58 req.extensions_mut().insert(remote_addr);
61 let router = router.clone();
62 async move { Ok::<_, hyper::Error>(router.lock().await.handle_request(req).await) }
63 }))
64 }
65 });
66
67 let server = Server::bind(&addr).serve(make_svc);
68 if let Err(e) = server.await {
69 eprintln!("Server error: {}", e);
70 }
71 }
72
73 fn random(&self) -> u32 {
74 let nanos = SystemTime::now()
76 .duration_since(UNIX_EPOCH)
77 .unwrap()
78 .subsec_nanos();
79
80 100 + (nanos % 900)
82 }
83}