diff --git a/Cargo.lock b/Cargo.lock index bb5dfbc..f9eb096 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1222,7 +1222,6 @@ dependencies = [ "rocket_codegen", "rocket_http", "serde", - "serde_json", "state", "tempfile", "time", diff --git a/Cargo.toml b/Cargo.toml index e7339df..171e42a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,7 +6,7 @@ edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] -rocket = {version = "0.5.0-rc.1", features= ["json"]} +rocket = "0.5.0-rc.1" lazy_static = "1.4.0" clap = { version = "3.0.6", features = ["derive"] } rocket_dyn_templates = {version="0.1.0-rc.1", features= ["handlebars"] } diff --git a/src/main.rs b/src/main.rs index d5ba36e..7e33826 100644 --- a/src/main.rs +++ b/src/main.rs @@ -4,16 +4,14 @@ extern crate rocket; extern crate lazy_static; use clap::Parser; - use rocket::fs::{relative, FileServer}; -use rocket::response::stream::{Event, EventStream}; +use rocket::{State, Shutdown}; +use rocket::serde::{Serialize, Deserialize}; use rocket_dyn_templates::Template; - -use std::{ - collections::HashMap, - mem::drop, - sync::{mpsc, Mutex, RwLock}, -}; +use rocket::form::Form; +use rocket::tokio::sync::broadcast::{channel, Sender, error::RecvError}; +use rocket::response::stream::{EventStream, Event, TextStream}; +use std::{collections::HashMap, mem::drop, sync::Mutex}; mod names; mod rooms; @@ -22,8 +20,16 @@ mod templates; lazy_static! { static ref ARGS: Args = Args::parse(); static ref ROOMS: Mutex> = Mutex::new(HashMap::new()); - /// String is the room list - static ref PLAYS: Mutex>> = Mutex::new(HashMap::new()); +} + + +#[derive(Debug, Clone, FromForm, Serialize, Deserialize)] +#[cfg_attr(test, derive(PartialEq, UriDisplayQuery))] +#[serde(crate = "rocket::serde")] +struct Play { + pub roomname: String, + pub position: String, + pub player1: bool, } /* @@ -48,7 +54,7 @@ fn rocket() -> _ { rocket::custom(config) .attach(Template::fairing()) .mount("/", FileServer::from(relative!("static"))) - .mount("/", routes![index, room, stream, play]) + .mount("/", routes![index, room, stream, post]) } /* @@ -102,6 +108,7 @@ async fn room(roomname: &str, token: usize, player1: bool) -> Template { // the room is real and the token is correct if room.token == token { drop(rooms); + //TODO: placeholder templates::get_room(roomname, token, player1) } // the room is real but the token is incorrect @@ -117,47 +124,20 @@ async fn room(roomname: &str, token: usize, player1: bool) -> Template { } } -//* -//sends new board if there have been updates -//* -#[get("/stream//")] -async fn stream(roomname: String, token: usize) -> EventStream![] { - let roomlist = ROOMS.lock().unwrap(); - drop(roomlist); - EventStream! { +#[get("/stream")] +async fn stream(queue: &State>, mut end: Shutdown) -> TextStream![String]{ + let mut rx = queue.subscribe(); + TextStream! { loop { - // TODO - // check if there are any new events, and then if the room token is correct - // if that's the case send the current playing board - // otherwise don't do anything - yield Event::json(&"oof".to_string()); + yield "hello!".to_string(); } } } -//* -// adds new boards to the send queue after calculating move -//* -#[post("/play?&&&&")] -fn play(roomname: &str, token: usize, player1: bool, x: u8, y: u8) { - // get room mutex - let mut roomlist = ROOMS.lock().unwrap(); - // check if room is legal - if rooms::room_and_token_correct(&roomlist, &roomname, &token) { - let board = &roomlist.get_mut(roomname).unwrap().board; - if board.play_is_legal(&x, &y, &player1) { - // change the board by making a new play - board.make_play(&x, &y); - let mut playlist = PLAYS.lock().unwrap(); - // if the board doesn't exist yet, make a new one - if !(playlist.contains_key(roomname)) { - let rn = roomname.to_string(); - playlist.insert(rn, vec![]); - } - // add new board to the play queue - playlist.get_mut(roomname).unwrap().push(board.clone()); - drop(playlist); - } - } - drop(roomlist); +/// Receive a message from a form submission and broadcast it to any receivers. +#[post("/message", data = "
")] +fn post(form: Form, queue: &State>) { + // A send 'fails' if there are no active subscribers. That's okay. + let _res = queue.send(form.into_inner()); } + diff --git a/src/rooms.rs b/src/rooms.rs index 641f165..0c611c0 100644 --- a/src/rooms.rs +++ b/src/rooms.rs @@ -1,100 +1,21 @@ use rand::{thread_rng, Rng}; -use rocket::serde::{Deserialize, Serialize}; -use std::collections::HashMap; #[derive(Debug)] pub struct Room { pub token: usize, pub full: bool, pub play_queue: Vec, - pub board: Board, } impl Room { pub fn new() -> Room { // generate room token - let token: usize = thread_rng().gen(); + let tok: usize = thread_rng().gen(); + // flip coin to see who starts Room { full: false, - token, + token: tok, play_queue: vec![], - board: Board::new(), } } } - -pub fn room_and_token_correct( - rooms: &HashMap, - roomname: &str, - token: &usize, -) -> bool { - if rooms.contains_key(roomname) { - if &rooms.get(roomname).unwrap().token == token { - return true; - } - } - false -} - -#[derive(Debug, Clone, FromForm, Serialize, Deserialize)] -#[cfg_attr(test, derive(PartialEq, UriDisplayQuery))] -#[serde(crate = "rocket::serde")] -pub struct Play { - pub roomname: String, - #[field(validate = len(2...2))] - pub position: String, - pub player1: bool, -} - -#[derive(Debug, Clone, Serialize, Deserialize)] -#[cfg_attr(test, derive(PartialEq))] -#[serde(crate = "rocket::serde")] -pub struct Board { - pub position: String, - pub player1: bool, - pub fields: Vec>, -} - -impl Board { - pub fn new() -> Board { - let mut rng = thread_rng(); - let mut fields: Vec> = vec![]; - let mut i: u8 = 0; - while i <= 8 { - let mut inner: Vec = vec![]; - let mut i_inner: u8 = 0; - while i_inner <= 8 { - inner.push(Field::new()); - i_inner += 1; - } - fields.push(inner); - i += 1; - } - Board { - player1: rng.gen_bool(1.0 / 2.0), - // TODO change this!!! this doesn't make sense! i just put this here for testing - position: "".to_string(), - fields, - } - } - pub fn make_play(&self, x: &u8, y: &u8) { - //TODO - } - pub fn play_is_legal(&self, x: &u8, y: &u8, player1: &bool) -> bool { - true - } -} - -#[derive(Debug, Clone, FromForm, Serialize, Deserialize)] -#[cfg_attr(test, derive(PartialEq, UriDisplayQuery))] -#[serde(crate = "rocket::serde")] -pub struct Field { - owner: u8, -} - - -impl Field { - fn new() -> Field { - Field { owner: 0 } - } -} diff --git a/static/join.js b/static/script.js similarity index 100% rename from static/join.js rename to static/script.js