Skip to main content
added 69 characters in body; edited tags; edited title
Source Link
200_success
  • 145.7k
  • 22
  • 191
  • 481

Simple multithreaded chat server in rustRust

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}
import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}

Simple multithreaded chat server in rust

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}

Simple multithreaded chat server in Rust

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}
fix typos; selective code highlight directives; other minor style and punctuation improvements
Source Link
Calak
  • 2.4k
  • 12
  • 19

I'm trying to develop a simple Rust chat server. I'm nonot a Rust expert and come from Java and Kotlin. 

This same server in Kotlin is:

After many attempts I've come up with a working Rust implementation that at least works:

I'm trying to develop a simple Rust chat server. I'm no Rust expert and come from Java and Kotlin. This same server in Kotlin is:

After many attempts I've come up with a Rust implementation that at least works:

I'm trying to develop a simple Rust chat server. I'm not a Rust expert and come from Java and Kotlin. 

This same server in Kotlin is:

After many attempts I've come up with a working Rust implementation :

fix typos; selective code highlight directives; other minor style and punctuation improvements
Source Link

simple Simple multithreaded chat severserver in rust

I'm trying to develop a simple RustRust chat server. I'm no RustRust expert and come from Java/KotlinJava and Kotlin. This same server in KotlinKotlin is:

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}
import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}

After many attempts I've come up with a RustRust implementation that at least works:

use std::env;
use std::io;
use std::io::Write;
use std::io::{LineWriter, BufReader, BufRead};
use std::net::{TcpListener, TcpStream};
use std::sync::{Arc, Mutex};
use std::collections::HashMap;
use std::thread;
use std::ops::DerefMut;

fn main() -> io::Result<()> {
    let args: Vec<String> = env::args().collect();
    let server_socket = TcpListener::bind(&*format!("localhost:{}", args[1]))?;
    let users: Arc<Mutex<HashMap<String, LineWriter<TcpStream>>>> = Arc::new(Mutex::new(HashMap::new()));
    
    for socket in server_socket.incoming() {
        let users = users.clone();
        thread::spawn(move || -> io::Result<()> {
            let socket = socket?;
            let socket_copy = socket.try_clone()?;
            let mut inp = BufReader::new(socket);
            let out = LineWriter::new(socket_copy);
            
            // read nick
            let mut nick = String::new();
            inp.read_line(&mut nick)?;
            nick.pop(); // discard '\n'
            let nick_copy = nick.clone();
            {
                let mut users = users.lock().unwrap();
                users.insert(nick, out);
            }
            
            for line in inp.lines() {
                {
                    let line = line?;
                    let mut users = users.lock().unwrap();
                    for (nick, peer) in users.deref_mut() {
                        if *nick == nick_copy { continue; }
                        writeln!(peer, "{}", line)?;
                    }
                }
            }
            
            // remove nick
            {
                let mut users = users.lock().unwrap();
                users.remove(&nick_copy);
            }
            Ok(())
        });
    }
    Ok(())
}
use std::env;
use std::io;
use std::io::Write;
use std::io::{LineWriter, BufReader, BufRead};
use std::net::{TcpListener, TcpStream};
use std::sync::{Arc, Mutex};
use std::collections::HashMap;
use std::thread;
use std::ops::DerefMut;

fn main() -> io::Result<()> {
    let args: Vec<String> = env::args().collect();
    let server_socket = TcpListener::bind(&*format!("localhost:{}", args[1]))?;
    let users: Arc<Mutex<HashMap<String, LineWriter<TcpStream>>>> = Arc::new(Mutex::new(HashMap::new()));
    
    for socket in server_socket.incoming() {
        let users = users.clone();
        thread::spawn(move || -> io::Result<()> {
            let socket = socket?;
            let socket_copy = socket.try_clone()?;
            let mut inp = BufReader::new(socket);
            let out = LineWriter::new(socket_copy);
            
            // read nick
            let mut nick = String::new();
            inp.read_line(&mut nick)?;
            nick.pop(); // discard '\n'
            let nick_copy = nick.clone();
            {
                let mut users = users.lock().unwrap();
                users.insert(nick, out);
            }
            
            for line in inp.lines() {
                {
                    let line = line?;
                    let mut users = users.lock().unwrap();
                    for (nick, peer) in users.deref_mut() {
                        if *nick == nick_copy { continue; }
                        writeln!(peer, "{}", line)?;
                    }
                }
            }
            
            // remove nick
            {
                let mut users = users.lock().unwrap();
                users.remove(&nick_copy);
            }
            Ok(())
        });
    }
    Ok(())
}

I'd prefer to use for peer in users.values_mut() instead of for (nick, peer) in users.deref_mut() but then I've problems when comparing LineWriter references to discard sender.

I'd also prefer to use RwLock instead of Mutex.

Any pointers to simplify/enhance code will be greatly apreciatedappreciated.

simple multithreaded chat sever in rust

I'm trying to develop a simple Rust chat server. I'm no Rust expert and come from Java/Kotlin. This same server in Kotlin is:

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}

After many attempts I've come up with a Rust implementation that at least works:

use std::env;
use std::io;
use std::io::Write;
use std::io::{LineWriter, BufReader, BufRead};
use std::net::{TcpListener, TcpStream};
use std::sync::{Arc, Mutex};
use std::collections::HashMap;
use std::thread;
use std::ops::DerefMut;

fn main() -> io::Result<()> {
    let args: Vec<String> = env::args().collect();
    let server_socket = TcpListener::bind(&*format!("localhost:{}", args[1]))?;
    let users: Arc<Mutex<HashMap<String, LineWriter<TcpStream>>>> = Arc::new(Mutex::new(HashMap::new()));
    
    for socket in server_socket.incoming() {
        let users = users.clone();
        thread::spawn(move || -> io::Result<()> {
            let socket = socket?;
            let socket_copy = socket.try_clone()?;
            let mut inp = BufReader::new(socket);
            let out = LineWriter::new(socket_copy);
            
            // read nick
            let mut nick = String::new();
            inp.read_line(&mut nick)?;
            nick.pop(); // discard '\n'
            let nick_copy = nick.clone();
            {
                let mut users = users.lock().unwrap();
                users.insert(nick, out);
            }
            
            for line in inp.lines() {
                {
                    let line = line?;
                    let mut users = users.lock().unwrap();
                    for (nick, peer) in users.deref_mut() {
                        if *nick == nick_copy { continue; }
                        writeln!(peer, "{}", line)?;
                    }
                }
            }
            
            // remove nick
            {
                let mut users = users.lock().unwrap();
                users.remove(&nick_copy);
            }
            Ok(())
        });
    }
    Ok(())
}

I'd prefer to use for peer in users.values_mut() instead of for (nick, peer) in users.deref_mut() but then I've problems when comparing LineWriter references to discard sender

I'd prefer to use RwLock instead of Mutex

Any pointers to simplify/enhance code will be greatly apreciated

Simple multithreaded chat server in rust

I'm trying to develop a simple Rust chat server. I'm no Rust expert and come from Java and Kotlin. This same server in Kotlin is:

import java.io.*
import java.net.*
import kotlin.concurrent.thread
import java.util.concurrent.ConcurrentHashMap

fun main(args: Array<String>) {
    val serv = ServerSocket(Integer.parseInt(args[0]))
    //val users = ConcurrentHashMap<String, PrintWriter>()
    val users = Collections.synchronizedMap(HashMap<String, PrintWriter>())

    while (true) {
        val s = serv.accept()
        thread {
            var sin = s.getInputStream().bufferedReader()
            val sout = PrintWriter(s.getOutputStream(), true)
            
            // read nick
            val nick = sin.readLine()
            users.put(nick, sout)
            
            sin.forEachLine {
                for (peer in users.values) {
                    if (peer == sout) continue
                    peer.println(it)
                }
            }
            users.remove(nick)
        }
    }
}

After many attempts I've come up with a Rust implementation that at least works:

use std::env;
use std::io;
use std::io::Write;
use std::io::{LineWriter, BufReader, BufRead};
use std::net::{TcpListener, TcpStream};
use std::sync::{Arc, Mutex};
use std::collections::HashMap;
use std::thread;
use std::ops::DerefMut;

fn main() -> io::Result<()> {
    let args: Vec<String> = env::args().collect();
    let server_socket = TcpListener::bind(&*format!("localhost:{}", args[1]))?;
    let users: Arc<Mutex<HashMap<String, LineWriter<TcpStream>>>> = Arc::new(Mutex::new(HashMap::new()));
    
    for socket in server_socket.incoming() {
        let users = users.clone();
        thread::spawn(move || -> io::Result<()> {
            let socket = socket?;
            let socket_copy = socket.try_clone()?;
            let mut inp = BufReader::new(socket);
            let out = LineWriter::new(socket_copy);
            
            // read nick
            let mut nick = String::new();
            inp.read_line(&mut nick)?;
            nick.pop(); // discard '\n'
            let nick_copy = nick.clone();
            {
                let mut users = users.lock().unwrap();
                users.insert(nick, out);
            }
            
            for line in inp.lines() {
                {
                    let line = line?;
                    let mut users = users.lock().unwrap();
                    for (nick, peer) in users.deref_mut() {
                        if *nick == nick_copy { continue; }
                        writeln!(peer, "{}", line)?;
                    }
                }
            }
            
            // remove nick
            {
                let mut users = users.lock().unwrap();
                users.remove(&nick_copy);
            }
            Ok(())
        });
    }
    Ok(())
}

I'd prefer to use for peer in users.values_mut() instead of for (nick, peer) in users.deref_mut() but then I've problems when comparing LineWriter references to discard sender.

I'd also prefer to use RwLock instead of Mutex.

Any pointers to simplify/enhance code will be greatly appreciated.

Source Link
Loading