use std::io::{Read, Write}; use std::net::{TcpListener, TcpStream}; use std::sync::{Arc, Mutex}; use std::thread; #[derive(Debug, Deserialize)] struct MessageOuter { auth: Option, message: Message, to: String, } #[derive(Debug, Deserialize)] struct Message { body: String, from: Option, } fn parse_message(input: &str) -> MessageOuter { let mut auth: Option = None; let mut body = String::new(); let mut from = None; let mut to = String::new(); for line in input.lines() { let mut parts = line.split_whitespace(); if let Some(field) = parts.next() { if let Some(value) = parts.next() { match field { "AUTH" => auth = Some(value.to_string()), "BODY" => body = value.to_string(), "FROM" => from = Some(value.to_string()), "TO" => to = value.to_string(), _ => {} } } } } let message_outer = MessageOuter { auth, message: Message { body, from }, to, }; message_outer } fn read_from(mut stream: TcpStream) -> MessageOuter { let mut buf = Vec::new(); let mut message_outer = MessageOuter { auth: None, message: Message { body: "".to_string(), from: None, }, to: "".to_string(), }; while let Ok(bytes_read) = stream.read_to_end(&mut buf) { if bytes_read == 0 { break; } message_outer = parse_message( String::from_utf8(buf.clone()).as_ref().unwrap() ); } message_outer.message.from = Some( message_outer.message.from.unwrap_or_else(|| "anon".to_string()) ); message_outer } fn main() { let listener = TcpListener::bind("127.0.0.1:8080") .expect("Failed to bind address"); println!("Server listening on 127.0.0.1:8080"); let client_list: Arc>> = Arc::new( Mutex::new(vec![]) ); for stream in listener.incoming() { match stream { Ok(stream) => { let client_list = Arc::clone(&client_list); thread::spawn(move || { // Add the client's stream to the client list client_list.lock().unwrap().push(stream.try_clone().unwrap()); let message = read_from(stream); // Send the received message to all connected clients let serialized_message = serde_json::to_string(&message).unwrap(); let client_list = client_list.lock().unwrap(); for client in &*client_list { if let Err(e) = client.write_all(serialized_message.as_bytes()) { eprintln!("Failed to write to client: {}", e); } if let Err(e) = client.flush() { eprintln!("Failed to flush stream: {}", e); } } // Remove the client's stream from the client list client_list .lock() .unwrap() .retain(|client| client .peer_addr() .unwrap() != stream.peer_addr().unwrap()); }); } Err(err) => { eprintln!("Error accepting client connection: {}"); } } } }