It works but my goodness it's slow. Time to tease out that global mutex.

main
Sean McArde 2023-11-21 12:26:57 -08:00
parent 014c4debc5
commit 9993892bb5
3 changed files with 1298 additions and 37 deletions

1241
Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@ -9,4 +9,6 @@ edition = "2021"
clap = "4.4.8"
dashmap = "5.5.3"
http = "1.0.0"
once_cell = "1.18.0"
rocket = "0.5.0"
tracing = "0.1.40"

View File

@ -1,15 +1,23 @@
use once_cell::sync::{Lazy};
use std::sync::{Mutex};
use clap::{Arg};
use std::{net::SocketAddr, time::Duration, error::Error, collections::VecDeque, sync::Arc};
use tower::ServiceBuilder;
use std::{net::SocketAddr, time::Duration, error::Error, collections::VecDeque, sync::Arc, thread::current};
use http::status::StatusCode;
use dashmap::DashMap;
static mut QUEUE_MAP : Lazy<Mutex<DashMap<&str, usize>>> = Lazy::new(|| Mutex::new(DashMap::new()));
static mut QUEUES : Lazy<Mutex<Vec<VecDeque<&str>>>> = Lazy::new(|| Mutex::new(Vec::new()));
static mut CURRENT_QUEUE : usize = 0;
static mut DUMB_QUEUE : Lazy<Mutex<DumbQueue>> = Lazy::new(|| Mutex::new(DumbQueue::new()));
#[derive(Debug)]
struct DumbQueue<'a> {
queue_map : DashMap<&'a str, usize>,
queues : Vec<VecDeque<&'a str>>,
struct DumbQueue {
queue_map : DashMap<String, usize>,
queues : Vec<VecDeque<String>>,
current_queue : usize,
}
@ -28,20 +36,7 @@ async fn write_request(kind: &str) -> String {
}
async fn handle_get(Query(args): Query<KVSet>) -> Result<String, StatusCode> {
let res = match &args.opt[..] {
"get" => Ok(write_request("get").await),
"put" => Ok(write_request("put").await),
"status" => Ok(write_request("status").await),
"reset" => Ok(write_request("reset").await),
_ => Ok(String::from("bad request")),
};
return res;
}
impl <'a> DumbQueue<'a> {
impl DumbQueue {
fn new() -> Self {
return DumbQueue {
queue_map: DashMap::new(),
@ -51,45 +46,72 @@ impl <'a> DumbQueue<'a> {
}
fn push_back(&mut self, key: &'a str, val: &'a str) {
let val_key = key;
let value = val;
fn push_back(&mut self, key: String, val: String) {
let lookup_key = key.clone();
let value = val.clone().to_string();
let queue_map = &self.queue_map;
let queue_index = queue_map.get(val_key);
let queue_index = queue_map.get(&lookup_key);
match queue_index {
Some(i) => {
let index : usize = *i;
self.queues[index].push_back(value)
}
None => {
let new_queue = VecDeque::new();
self.queues.push(new_queue);
queue_map.insert(val_key, self.current_queue as usize);
let _ = queue_map.insert(key.to_string(), self.current_queue as usize);
self.queues[self.current_queue].push_back(value);
self.current_queue += 1;
},
Some(i) => {
self.queues[*i].push_back(value);
}
}
}
fn pop_front(&mut self, key: &'a str) -> Option<&str> {
fn pop_front(&mut self, key: String) -> Option<String> {
let val_key = key;
let queue_map = &self.queue_map;
let queue_index = queue_map.get(val_key);
let queue_index = queue_map.get(val_key.as_str());
match queue_index {
Some(i) => {
let index : usize = *i;
return Some(self.queues[index].pop_front().unwrap())
match self.queues[index].pop_front() {
Some(res) => return Some(res),
None => None
}
}
None => None
}
}
}
fn main() {
let mut queue = DumbQueue::new();
#[macro_use] extern crate rocket;
println!("{:?}", queue);
#[get("/")]
fn index() -> &'static str {
"Hello, world!"
}
#[get("/<id>")]
fn get_by_id(id: String) -> String {
let mut dumb_queue = unsafe { DUMB_QUEUE.lock().unwrap() };
let result = match dumb_queue.pop_front(id) {
Some(res) => res.to_string(),
None => String::from("")
};
result
}
#[put("/<id>", data = "<input>")]
fn put_by_id(id: String, input: String) {
let mut dumb_queue = unsafe { DUMB_QUEUE.lock().unwrap() };
dumb_queue.push_back(id, input);
}
#[launch]
fn rocket() -> _ {
rocket::build().mount("/", routes![index, put_by_id, get_by_id])
}