How do you handle multiple client to connect to one server? I have this LogServer.java
import javax.net.ssl.*;
import javax.net.*;
import java.io.*;
import java.net.*;
public class LogServer {
private static final int PORT_NUM = 5000;
public static void main(String args[]) {
ServerSocketFactory serverSocketFactory =
ServerSocketFactory.getDefault();
ServerSocket serverSocket = null;
try {
serverSocket =
serverSocketFactory.createServerSocket(PORT_NUM);
} catch (IOException ignored) {
System.err.println("Unable to create server");
System.exit(-1);
}
System.out.printf("LogServer running on port: %s%n", PORT_NUM);
while (true) {
Socket socket = null;
try {
socket = serverSocket.accept();
InputStream is = socket.getInputStream();
BufferedReader br = new BufferedReader(
new InputStreamReader(is, "US-ASCII"));
String line = null;
while ((line = br.readLine()) != null) {
System.out.println(line);
}
} catch (IOException exception) {
// Just handle next request.
} finally {
if (socket != null) {
try {
socket.close();
} catch (IOException ignored) {
}
}
}
}
}
}
and an embedded applet with part of the code like this e.g
import java.io.*;
import java.util.logging.*;
public class LogTest
{
private static Logger logger = Logger.getAnonymousLogger();
public static void main(String argv[]) throws IOException
{
Handler handler = new SocketHandler("localhost", 5000);
logger.addHandler(handler);
logger.log(Level.SEVERE, "Hello, World");
logger.log(Level.SEVERE, "Welcome Home");
logger.log(Level.SEVERE, "Hello, World");
logger.log(Level.SEVERE, "Welcome Home");
}
}
now the question is if I run "java LogServer" on the server, it will open the application and waiting for input stream and if I open my site, it will start streaming the log. But if I open one more using other computer/network, the second site does not log the stream. seems like it's because the first one still bind to port 5000.
How do I handle this? How does socket actually work with multiple client / one server?
This is the echo server handling multiple clients... Runs fine and good using Threads
// echo server
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;
public class Server_X_Client {
public static void main(String args[]){
Socket s=null;
ServerSocket ss2=null;
System.out.println("Server Listening......");
try{
ss2 = new ServerSocket(4445); // can also use static final PORT_NUM , when defined
}
catch(IOException e){
e.printStackTrace();
System.out.println("Server error");
}
while(true){
try{
s= ss2.accept();
System.out.println("connection Established");
ServerThread st=new ServerThread(s);
st.start();
}
catch(Exception e){
e.printStackTrace();
System.out.println("Connection Error");
}
}
}
}
class ServerThread extends Thread{
String line=null;
BufferedReader is = null;
PrintWriter os=null;
Socket s=null;
public ServerThread(Socket s){
this.s=s;
}
public void run() {
try{
is= new BufferedReader(new InputStreamReader(s.getInputStream()));
os=new PrintWriter(s.getOutputStream());
}catch(IOException e){
System.out.println("IO error in server thread");
}
try {
line=is.readLine();
while(line.compareTo("QUIT")!=0){
os.println(line);
os.flush();
System.out.println("Response to Client : "+line);
line=is.readLine();
}
} catch (IOException e) {
line=this.getName(); //reused String line for getting thread name
System.out.println("IO Error/ Client "+line+" terminated abruptly");
}
catch(NullPointerException e){
line=this.getName(); //reused String line for getting thread name
System.out.println("Client "+line+" Closed");
}
finally{
try{
System.out.println("Connection Closing..");
if (is!=null){
is.close();
System.out.println(" Socket Input Stream Closed");
}
if(os!=null){
os.close();
System.out.println("Socket Out Closed");
}
if (s!=null){
s.close();
System.out.println("Socket Closed");
}
}
catch(IOException ie){
System.out.println("Socket Close Error");
}
}//end finally
}
}
Also here is the code for the client.. Just execute this code for as many times as you want to create multiple client..
// A simple Client Server Protocol .. Client for Echo Server
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.InetAddress;
import java.net.Socket;
public class NetworkClient {
public static void main(String args[]) throws IOException{
InetAddress address=InetAddress.getLocalHost();
Socket s1=null;
String line=null;
BufferedReader br=null;
BufferedReader is=null;
PrintWriter os=null;
try {
s1=new Socket(address, 4445); // You can use static final constant PORT_NUM
br= new BufferedReader(new InputStreamReader(System.in));
is=new BufferedReader(new InputStreamReader(s1.getInputStream()));
os= new PrintWriter(s1.getOutputStream());
}
catch (IOException e){
e.printStackTrace();
System.err.print("IO Exception");
}
System.out.println("Client Address : "+address);
System.out.println("Enter Data to echo Server ( Enter QUIT to end):");
String response=null;
try{
line=br.readLine();
while(line.compareTo("QUIT")!=0){
os.println(line);
os.flush();
response=is.readLine();
System.out.println("Server Response : "+response);
line=br.readLine();
}
}
catch(IOException e){
e.printStackTrace();
System.out.println("Socket read Error");
}
finally{
is.close();os.close();br.close();s1.close();
System.out.println("Connection Closed");
}
}
}
Here is code for Multiple Client to one Server Working Fine .. Give it a try :)
Server.java:
import java.io.DataInputStream;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.logging.Level;
import java.util.logging.Logger;
class Multi extends Thread{
private Socket s=null;
DataInputStream infromClient;
Multi() throws IOException{
}
Multi(Socket s) throws IOException{
this.s=s;
infromClient = new DataInputStream(s.getInputStream());
}
public void run(){
String SQL=new String();
try {
SQL = infromClient.readUTF();
} catch (IOException ex) {
Logger.getLogger(Multi.class.getName()).log(Level.SEVERE, null, ex);
}
System.out.println("Query: " + SQL);
try {
System.out.println("Socket Closing");
s.close();
} catch (IOException ex) {
Logger.getLogger(Multi.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
public class Server {
public static void main(String args[]) throws IOException,
InterruptedException{
while(true){
ServerSocket ss=new ServerSocket(11111);
System.out.println("Server is Awaiting");
Socket s=ss.accept();
Multi t=new Multi(s);
t.start();
Thread.sleep(2000);
ss.close();
}
}
}
Client1.java:
import java.io.DataOutputStream;
import java.io.ObjectInputStream;
import java.net.Socket;
public class client1 {
public static void main(String[] arg) {
try {
Socket socketConnection = new Socket("127.0.0.1", 11111);
//QUERY PASSING
DataOutputStream outToServer = new DataOutputStream(socketConnection.getOutputStream());
String SQL="I am client 1";
outToServer.writeUTF(SQL);
} catch (Exception e) {System.out.println(e); }
}
}
Client2.java
import java.io.DataOutputStream;
import java.net.Socket;
public class client2 {
public static void main(String[] arg) {
try {
Socket socketConnection = new Socket("127.0.0.1", 11111);
//QUERY PASSING
DataOutputStream outToServer = new DataOutputStream(socketConnection.getOutputStream());
String SQL="I am Client 2";
outToServer.writeUTF(SQL);
} catch (Exception e) {System.out.println(e); }
}
}
See O'Reilly "Java Cookbook", Ian Darwin - recipe 17.4 Handling Multiple Clients.
Pay attention that accept()
is not thread safe, so the call is wrapped within synchronized
.
64: synchronized(servSock) {
65: clientSocket = servSock.accept();
66: }
I guess the problem is that you need to start a separate thread for each connection and call serverSocket.accept()
in a loop to accept more than one connection.
It is not a problem to have more than one connection on the same port.
Source: Stackoverflow.com