First version with separated clients and a server
This commit is contained in:
		
						commit
						5335b4c76b
					
				
							
								
								
									
										4
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@ -0,0 +1,4 @@
 | 
			
		||||
 | 
			
		||||
/target
 | 
			
		||||
**/*.rs.bk
 | 
			
		||||
*.lock
 | 
			
		||||
							
								
								
									
										6
									
								
								Cargo.toml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								Cargo.toml
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,6 @@
 | 
			
		||||
[package]
 | 
			
		||||
name = "chat-reseau"
 | 
			
		||||
version = "0.1.0"
 | 
			
		||||
authors = ["Phuntsok Drak-pa <drakpa@drakpa.fr>"]
 | 
			
		||||
 | 
			
		||||
[dependencies]
 | 
			
		||||
							
								
								
									
										177
									
								
								src/main.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										177
									
								
								src/main.rs
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,177 @@
 | 
			
		||||
use std::env;
 | 
			
		||||
use std::net::{TcpListener, TcpStream};
 | 
			
		||||
use std::thread;
 | 
			
		||||
#[allow(unused_imports)]
 | 
			
		||||
use std::io::{stdin, stdout, Read, Write};
 | 
			
		||||
#[allow(unused_imports)]
 | 
			
		||||
use std::sync::{Arc, Mutex};
 | 
			
		||||
 | 
			
		||||
///////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
//                                                                           //
 | 
			
		||||
//                                   Client                                  //
 | 
			
		||||
//                                                                           //
 | 
			
		||||
///////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
 | 
			
		||||
fn get_entry() -> String {
 | 
			
		||||
    let mut buf = String::new();
 | 
			
		||||
 | 
			
		||||
    stdin().read_line(&mut buf).unwrap();
 | 
			
		||||
    buf.replace("\n", "").replace("\r", "")
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
fn exchange_with_server(mut stream: TcpStream) {
 | 
			
		||||
    let stdout = std::io::stdout();
 | 
			
		||||
    let mut io = stdout.lock();
 | 
			
		||||
    let buf = &mut [0; 3];
 | 
			
		||||
 | 
			
		||||
    println!("Enter `quit` when you want to leave");
 | 
			
		||||
    loop {
 | 
			
		||||
        write!(io, "> ").unwrap();
 | 
			
		||||
        io.flush().unwrap();
 | 
			
		||||
        match &*get_entry() {
 | 
			
		||||
            "quit" => {
 | 
			
		||||
                println!("bye!");
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
            "exit" => {
 | 
			
		||||
                println!("bye!");
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
            line => {
 | 
			
		||||
                write!(stream, "{}\n", line).unwrap();
 | 
			
		||||
                match stream.read(buf) {
 | 
			
		||||
                    Ok(received) => {
 | 
			
		||||
                        if received < 1 {
 | 
			
		||||
                            println!("Perte de la connexion avec le serveur");
 | 
			
		||||
                            return;
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    Err(_) => {
 | 
			
		||||
                        println!("Perte de la connexion avec le serveur");
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                // println!("Réponse du serveur : {:?}", buf);
 | 
			
		||||
                let reponse = String::from_utf8(buf.to_vec()).unwrap();
 | 
			
		||||
                println!("Réponse du serveur : {}", reponse);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
fn client(server_address: String) {
 | 
			
		||||
    println!("Tentative de connexion a serveur...");
 | 
			
		||||
    match TcpStream::connect(server_address) {
 | 
			
		||||
        Ok(stream) => {
 | 
			
		||||
            println!("Connexion au serveur réussie !");
 | 
			
		||||
            exchange_with_server(stream);
 | 
			
		||||
        }
 | 
			
		||||
        Err(e) => {
 | 
			
		||||
            println!("La connection au serveur a échoué : {}", e);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
///////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
//                                                                           //
 | 
			
		||||
//                                   Server                                  //
 | 
			
		||||
//                                                                           //
 | 
			
		||||
///////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
 | 
			
		||||
fn handle_client(mut stream: &TcpStream, adresse: &str) {
 | 
			
		||||
    let mut msg: Vec<u8> = Vec::new();
 | 
			
		||||
    loop {
 | 
			
		||||
        let buf = &mut [0; 10];
 | 
			
		||||
 | 
			
		||||
        match stream.read(buf) {
 | 
			
		||||
            Ok(received) => {
 | 
			
		||||
                // si on a reçu 0 octet, ça veut dire que le client s'est déconnecté
 | 
			
		||||
                if received < 1 {
 | 
			
		||||
                    println!("Client disconnected {}", adresse);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                let mut x = 0;
 | 
			
		||||
 | 
			
		||||
                for c in buf {
 | 
			
		||||
                    // si on a dépassé le nombre d'octets reçus, inutile de continuer
 | 
			
		||||
                    if x >= received {
 | 
			
		||||
                        break;
 | 
			
		||||
                    }
 | 
			
		||||
                    x += 1;
 | 
			
		||||
                    if *c == '\n' as u8 {
 | 
			
		||||
                        println!(
 | 
			
		||||
                            "message reçu {} : {}",
 | 
			
		||||
                            adresse,
 | 
			
		||||
                            // on convertit maintenant notre buffer en String
 | 
			
		||||
                            String::from_utf8(msg).unwrap()
 | 
			
		||||
                        );
 | 
			
		||||
 | 
			
		||||
                        stream.write(b"ok\n").unwrap();
 | 
			
		||||
 | 
			
		||||
                        msg = Vec::new();
 | 
			
		||||
                    } else {
 | 
			
		||||
                        msg.push(*c);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            Err(_) => {
 | 
			
		||||
                println!("Client disconnected {}", adresse);
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
fn serveur(port: String) {
 | 
			
		||||
    println!("Port: {}", port);
 | 
			
		||||
    let mut serv = String::from("127.0.0.1:");
 | 
			
		||||
    serv.push_str(&port);
 | 
			
		||||
    let listener = TcpListener::bind(serv.to_string()).unwrap();
 | 
			
		||||
 | 
			
		||||
    println!("En attente d’un client...");
 | 
			
		||||
 | 
			
		||||
    // Multi-client ///////////////////////////////////////////////////////////
 | 
			
		||||
    for stream in listener.incoming() {
 | 
			
		||||
        match stream {
 | 
			
		||||
            Ok(stream) => {
 | 
			
		||||
                let adresse = match stream.peer_addr() {
 | 
			
		||||
                    Ok(addr) => format!("[adresse : {}]", addr),
 | 
			
		||||
                    Err(_) => "inconnue".to_owned(),
 | 
			
		||||
                };
 | 
			
		||||
 | 
			
		||||
                println!("Nouveau client {}", adresse);
 | 
			
		||||
                thread::spawn(move || handle_client(&stream, &*adresse));
 | 
			
		||||
            }
 | 
			
		||||
            Err(e) => {
 | 
			
		||||
                println!("La connexion du client a échoué : {}", e);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        println!("En attente d’un autre client...");
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
fn main() {
 | 
			
		||||
    let args: Vec<String> = env::args().collect();
 | 
			
		||||
    if args.len() == 2 {
 | 
			
		||||
        ///////////////////////////////////////////////////////////////////////
 | 
			
		||||
        //                           Server opened                           //
 | 
			
		||||
        ///////////////////////////////////////////////////////////////////////
 | 
			
		||||
        println!("Opening server on port {}", args[1]);
 | 
			
		||||
        serveur(args[1].clone());
 | 
			
		||||
    } else if args.len() == 3 {
 | 
			
		||||
        ///////////////////////////////////////////////////////////////////////
 | 
			
		||||
        //                           Client opened                           //
 | 
			
		||||
        ///////////////////////////////////////////////////////////////////////
 | 
			
		||||
        println!("Client connecting on server {}:{}", args[1], args[2]);
 | 
			
		||||
        let mut serv = if args[1] == String::from("localhost") {
 | 
			
		||||
            String::from("127.0.0.1")
 | 
			
		||||
        } else {
 | 
			
		||||
            args[1].clone()
 | 
			
		||||
        };
 | 
			
		||||
        serv.push(':');
 | 
			
		||||
        serv.push_str(&args[2]);
 | 
			
		||||
        client(serv);
 | 
			
		||||
    } else {
 | 
			
		||||
        println!("Usage: {} [server ip] port", args[0]);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user