#[macro_use] extern crate rocket; use rocket::serde::json::Json; use std::collections::HashMap; use rocket::State; use std::sync::Mutex; use std::time::SystemTime; #[derive(serde::Serialize)] struct Response (Result); #[get("/get_message/")] fn get_message(id: usize, db: &State) -> Json> { let lock = db.sdb.lock().unwrap(); match lock.get_message(id) { Some(n) => Json(Response(Ok(n))), None => Json(Response(Err("Message not found"))), } } #[get("/get_message_id_list//")] fn rget_message_id_list(id_start: usize, id_end: usize, db: &State) -> Json, &'static str>> { let lock = db.sdb.lock().unwrap(); let list = lock.get_message_id_list(id_start, id_end); if list.len() == 0 { Json(Response(Err("No messages"))) } else { Json(Response(Ok(list))) } } #[get("/send_message//")] fn send_message(user_id: usize, msg: String, db: &State) -> Json> { let mut lock = db.sdb.lock().unwrap(); let user = match lock.get_user(user_id) { Some(n) => n, None => return Json(Response(Err("User not found"))) }; let msg = Message{ sender: user.clone(), message: msg, date: Date::now(), id: lock.get_next_message_id(), }; lock.send_message(msg.clone()); Json(Response(Ok(msg))) } #[get("/get_user/")] fn get_user(id: usize, db: &State) -> Json> { let lock = db.sdb.lock().unwrap(); match lock.get_user(id) { Some(n) => Json(Response(Ok(n))), None => Json(Response(Err("User not found"))) } } #[get("/get_user_by_name/")] fn get_user_by_name(name: String, db: &State) -> Json, &'static str>> { let lock = db.sdb.lock().unwrap(); match lock.get_user_by_name(name) { Some(n) => Json(Response(Ok(n))), None => Json(Response(Err("User not found"))) } } #[get("/create_user/")] fn create_user(name: String, db: &State) -> Json> { let mut lock = db.sdb.lock().unwrap(); Json(Response(lock.create_user(name))) } struct SharedDB { sdb: Mutex } struct Database { usermap: HashMap, messagemap: HashMap, } impl Database { fn get_message(&self, id: usize) -> Option { match self.messagemap.get(&id) { Some(n) => Some(n.to_owned()), None => None, } } fn get_message_id_list(&self, id_start: usize, id_end: usize) -> Vec { let mut message_id_vec: Vec = vec![]; for x in id_start..=id_end { match self.messagemap.get(&x) { Some(_) => message_id_vec.push(x), None => (), } } return message_id_vec; } fn get_next_message_id(&self) -> usize { self.messagemap.len() } fn send_message(&mut self, msg: Message) { self.messagemap.insert(msg.id, msg); println!("{:?}", self.messagemap.get(&0)); } fn get_user(&self, id: usize) -> Option { match self.usermap.get(&id) { Some(n) => Some(n.to_owned()), None => None } } fn get_user_by_name(&self, name: String) -> Option> { let list: Vec> = self.usermap.values().map(|x| if x.username == name {Some(x.clone())} else {None}).collect(); let mut users = vec![]; for x in list { match x { Some(n) => users.push(n), None => () } } if users.len() == 0 { None } else { Some(users) } } fn create_user(&mut self, name: String) -> Result { let id = self.usermap.len(); let user = User::new(name.clone(), id); match self.get_user_by_name(name) { Some(_) => return Err("ID taken"), None => (), } match self.usermap.get(&id) { Some(_) => Err("ID taken"), None => {self.usermap.insert(id, user.clone()); Ok(user)}, } } pub fn new() -> Database { Database { usermap: HashMap::new(), messagemap: HashMap::new(), } } } #[derive(serde::Serialize, Clone, Debug)] struct Date { date: u64, } impl Date { pub fn now() -> Date { Date{ date: SystemTime::now().duration_since(SystemTime::UNIX_EPOCH).unwrap().as_secs() } } } #[derive(serde::Serialize, Clone, Debug)] struct User { username: String, id: usize } impl User { pub fn new(name: String, id: usize) -> User { User{ username: name, id: id } } } #[derive(serde::Serialize, Clone, Debug)] struct Message { date: Date, message: String, sender: User, id: usize, } #[derive(serde::Serialize)] struct Info { name: String, url: String, users: usize, } impl Info { pub fn get() -> Info { Info{ name: String::from("Infernal Garden"), url: String::from("https://wf.infernal.garden"), users: 1, } } } #[get("/ping")] fn ping() -> Json> { Json(Response(Ok("pong"))) } #[get("/api")] fn api_index() -> Json { Json(Info::get()) } #[derive(serde::Serialize)] struct HitCount { c: usize } #[launch] fn rocket() -> _ { rocket::build() .mount("/api", routes![ get_message, send_message, rget_message_id_list, ping, get_user, create_user, get_user_by_name ]) .mount("/", routes![api_index]) .manage(SharedDB{sdb: Mutex::new(Database::new())}) }