Initial codebase basically copied from https://github.com/tensor-programming/Rust_client-server_chat unsure how much of that will remain though

Main
Johannes Hendrik Gerard van der Weide 2024-04-12 23:28:35 +02:00
parent c8bf78ea5d
commit ed4602ad21
2 changed files with 114 additions and 1 deletions

7
Cargo.lock generated Normal file
View File

@ -0,0 +1,7 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 3
[[package]]
name = "hermit-chat"
version = "0.1.0"

View File

@ -1,3 +1,12 @@
use std::env;
use std::io::{self, ErrorKind, Read, Write};
use std::net::{TcpStream, TcpListener};
use std::sync::mpsc::{self, TryRecvError};
use std::thread;
const LOCAL_HOST: &str = "127.0.0.1:6000";
const MESSAGE_SIZE: usize = 32;
fn main() { fn main() {
let args: Vec<String> = env::args().collect(); let args: Vec<String> = env::args().collect();
let query = &args[args.len() - 1]; let query = &args[args.len() - 1];
@ -7,12 +16,61 @@ fn main() {
} else if query == "--bridge"{ } else if query == "--bridge"{
launch_bridge(); launch_bridge();
} else { } else {
launch_client();
} }
} }
fn sleep() {
thread::sleep(::std::time::Duration::from_millis(100));
}
// Yup thats uh a "server" uhuh it sure serves it's purpose I think I hope // Yup thats uh a "server" uhuh it sure serves it's purpose I think I hope
fn launch_server() { fn launch_server() {
let server = TcpListener::bind(LOCAL_HOST).expect("Listener failed to bind");
server.set_nonblocking(true).expect("Failed to initialize non-blocking");
let mut clients = vec![];
let (tx, rx) = mpsc::channel::<String>();
loop {
if let Ok((mut socket, address)) = server.accept() {
println!("Client {} connected", address);
let tx = tx.clone();
clients.push(socket.try_clone().expect("Failed to clone client"));
thread::spawn(move || loop {
let mut buffer = vec![0; MESSAGE_SIZE];
match socket.read_exact(&mut buffer) {
Ok(_) => {
let message = buffer.into_iter().take_while(|&x| x != 0).collect::<Vec<_>>();
let message = String::from_utf8(message).expect("Invalid utf8 message");
println!("{}: {:?}", address, message);
tx.send(message).expect("Failed to send message to rx");
},
Err(ref error) if error.kind() == ErrorKind::WouldBlock => (),
Err(_) => {
println!("Closing connection with: {}", address);
break;
}
}
sleep();
});
}
if let Ok(message) = rx.try_recv() {
clients = clients.into_iter().filter_map(|mut client| {
let mut buffer = message.clone().into_bytes();
buffer.resize(MESSAGE_SIZE, 0);
client.write_all(&buffer).map(|_| client).ok()
}).collect::<Vec<_>>();
}
sleep();
}
} }
// A bridge is basically the same as a client but can also be connected to on the local computer // A bridge is basically the same as a client but can also be connected to on the local computer
@ -23,4 +81,52 @@ fn launch_bridge() {
//I can yap in comments all I want if you want to complain use this function to talk to me on my //I can yap in comments all I want if you want to complain use this function to talk to me on my
//hermitchat server k thx //hermitchat server k thx
fn launch_client() { fn launch_client() {
let mut client = TcpStream::connect(LOCAL_HOST).expect("Stream failed to connect");
client.set_nonblocking(true).expect("Failed to initiate non-blocking");
let (tx, rx) = mpsc::channel::<String>();
thread::spawn(move || loop {
let mut buffer = vec![0; MESSAGE_SIZE];
match client.read_exact(&mut buffer) {
Ok(_) => {
let message = buffer.into_iter().into_iter().take_while(|&x| x != 0).collect::<Vec<_>>();
println!("Message recv {:?}", message);
}
Err(ref error) if error.kind() == ErrorKind::WouldBlock => (),
Err(_) => {
println!("Connection with server was severed");
break;
}
}
match rx.try_recv() {
Ok(message) => {
let mut buffer = message.clone().into_bytes();
buffer.resize(MESSAGE_SIZE, 0);
client.write_all(&buffer).expect("Writing to socket failed");
println!("Message sent {:?}", message);
},
Err(TryRecvError::Empty) => (),
Err(TryRecvError::Disconnected) => break
}
sleep();
});
println!("Write a message:");
loop {
let mut buffer = String::new();
io::stdin().read_line(&mut buffer).expect("Line could not be read");
let message = buffer.trim().to_string();
if message == "/exit" {
println!("Quiting!");
break;
}
if tx.send(message).is_err() {
println!("Could not send message");
break;
}
}
} }