add error handling for sending message when not in the room

This commit is contained in:
David Westgate 2023-11-30 01:03:05 -08:00
parent 2f66815631
commit ac1eecd9e5
3 changed files with 43 additions and 12 deletions

View File

@ -64,16 +64,19 @@ fn process_message(msg_bytes: &[u8], nick: &str) {
match msg_bytes[0] { match msg_bytes[0] {
codes::ERROR => match msg_bytes[1] { codes::ERROR => match msg_bytes[1] {
codes::error::INVALID_ROOM => { codes::error::INVALID_ROOM => {
println!("Operation Performed on an invalid room. Try again"); eprintln!("Operation Performed on an invalid room. Try again");
} }
codes::error::NICKNAME_COLLISION => { codes::error::NICKNAME_COLLISION => {
println!("Nickname already in use on server. Connect again with a different one"); eprintln!("Nickname already in use on server. Connect again with a different one");
} }
codes::error::SERVER_FULL => { codes::error::SERVER_FULL => {
println!("Server is full. Try again later"); eprintln!("Server is full. Try again later");
}
codes::error::NOT_IN_ROOM => {
eprintln!("Cannot send a message before joining room. Use /join [room].")
} }
_ => { _ => {
println!("Error code: {:x?}", msg_bytes[1]); eprintln!("Error code: {:x?}", msg_bytes[1]);
} }
}, },
@ -171,7 +174,12 @@ pub fn start() {
one_param_op(codes::client::REGISTER_NICK, &mut stream, &nick); one_param_op(codes::client::REGISTER_NICK, &mut stream, &nick);
loop { loop {
let inp: String = input!("\n[{}]:", active_room); let mut inp = String::new();
if active_room.is_empty() {
inp = input!("");
} else {
inp = input!("\n[{}]:", active_room);
}
let mut args: std::str::SplitWhitespace<'_> = inp.split_whitespace(); let mut args: std::str::SplitWhitespace<'_> = inp.split_whitespace();
let command: Option<&str> = args.next(); let command: Option<&str> = args.next();

View File

@ -25,6 +25,7 @@ pub mod codes {
pub const NOT_YET_REGISTERED: u8 = 0x14; pub const NOT_YET_REGISTERED: u8 = 0x14;
pub const MALFORMED: u8 = 0x15; pub const MALFORMED: u8 = 0x15;
pub const ALREADY_IN_ROOM: u8 = 0x16; pub const ALREADY_IN_ROOM: u8 = 0x16;
pub const NOT_IN_ROOM: u8 = 0x17;
} }
} }

View File

@ -84,7 +84,7 @@ fn message(room: &str, msg: &str, sender: &str, server: &Arc<Mutex<Server>>) {
} }
fn broadcast(op: u8, server: &Arc<Mutex<Server>>, message: &str) { fn broadcast(op: u8, server: &Arc<Mutex<Server>>, message: &str) {
let size = message.len() + 1; let size: usize = message.len() + 1;
let mut out_buf: Vec<u8> = vec![0; size]; let mut out_buf: Vec<u8> = vec![0; size];
out_buf[0] = op; out_buf[0] = op;
@ -191,7 +191,29 @@ fn handle_client(
let params: Option<(&str, &str)> = p.split_once(" "); let params: Option<(&str, &str)> = p.split_once(" ");
match params { match params {
Some((room, msg)) => { Some((room, msg)) => {
message(room, msg, nickname, server); let unlocked_server: std::sync::MutexGuard<'_, Server> = server.lock().unwrap();
let users_in_room: Option<&Vec<String>> = unlocked_server.rooms.get(room);
match users_in_room {
Some(users) => {
let is_user_in_room: Option<&String> =
users.iter().find(|&u| u.eq(nickname));
match is_user_in_room {
Some(_) => {
message(room, msg, nickname, server);
}
None => {
stream
.write_all(&[codes::ERROR, codes::error::NOT_IN_ROOM])
.unwrap();
}
}
}
None => {
stream
.write_all(&[codes::ERROR, codes::error::INVALID_ROOM])
.unwrap();
}
}
} }
_ => { _ => {
stream stream
@ -217,7 +239,7 @@ fn remove_user(server: &Arc<Mutex<Server>>, nickname: &str, stream: &mut TcpStre
let server: &mut Server = guard.deref_mut(); let server: &mut Server = guard.deref_mut();
let mut rooms: &mut HashMap<String, Vec<String>> = &mut server.rooms; let mut rooms: &mut HashMap<String, Vec<String>> = &mut server.rooms;
rooms.values_mut().for_each(|room: &mut Vec<String>| { rooms.values_mut().for_each(|room: &mut Vec<String>| {
room.retain(|u| !u.eq(nickname)); room.retain(|u: &String| !u.eq(nickname));
}); });
let users: &mut HashMap<String, TcpStream> = &mut server.users; let users: &mut HashMap<String, TcpStream> = &mut server.users;
users.remove(nickname); users.remove(nickname);
@ -234,8 +256,8 @@ fn register_nick(server: &Arc<Mutex<Server>>, nickname: &str, stream: &mut TcpSt
.unwrap(); .unwrap();
} else { } else {
// Add the user to the user list // Add the user to the user list
let clone = stream.try_clone().expect("fail to clone"); let clone: TcpStream = stream.try_clone().expect("fail to clone");
let addr = clone.peer_addr().unwrap().to_string(); let addr: String = clone.peer_addr().unwrap().to_string();
unlocked_server.users.insert(nickname.to_string(), clone); unlocked_server.users.insert(nickname.to_string(), clone);
// Send response ok // Send response ok
@ -391,8 +413,8 @@ pub fn start() {
1 => println!("Users: {:?}", server.lock().unwrap().users), 1 => println!("Users: {:?}", server.lock().unwrap().users),
2 => println!("Rooms: {:?}", server.lock().unwrap().rooms), 2 => println!("Rooms: {:?}", server.lock().unwrap().rooms),
3 => { 3 => {
let inp = input!("Enter message: "); let inp2 = input!("Enter message: ");
broadcast(codes::client::MESSAGE, &server, &inp) broadcast(codes::client::MESSAGE, &server, &inp2);
} }
_ => println!("Invalid Input"), _ => println!("Invalid Input"),
}, },