Echo Server with New Thread for each Client

This version of the echo client-server application has a new thread for each client to allow concurrent operations of clients, each with unlimited echoes.

Code of Server

namespace echo_server03;

interface

uses
  java.io.*, java.net.*;
  
type
  ConnectionHandler = class(Runnable)
  private
    cs : Socket := nil;
    pw : PrintWriter := nil;
    br : BufferedReader := nil;
    isr : InputStreamReader := nil;
    msg : String;
  public
    constructor Create(s : Socket);
    method run;   
  end;  

implementation

const
  MAX_CLIENTS = 5;
  SERVER_PORT = 1717;
var
  serverSocket : ServerSocket := nil;
  clientSocket : Socket := nil;
  connectionHandler : ConnectionHandler;
  t : Thread;      
    
method ReportError(E : Exception);
begin
  writeln (E.toString);
  System.in.read;
  System.exit(0);
end;    

constructor ConnectionHandler.Create(s : Socket);
begin
  cs := s;
  try    
    isr := new InputStreamReader(cs.getInputStream);
    br := new BufferedReader(isr);
    pw := new PrintWriter(cs.getOutputStream, true);
  except  
    on E : Exception do
      ReportError(E);
    end;  
end;

method ConnectionHandler.run;
begin
  repeat
    msg := br.readLine;
    if (msg <> 'quit') and (msg <> 'end')  then
      begin
        pw.println(msg);
        writeln('Echoing: ' + msg);  
      end;
  until (msg = 'end') or (msg = 'quit');
  pw.close;
  isr.close;
  br.close;
  cs.close;
  if msg = 'quit' then
    System.exit(0);
end;

begin
  try
    serverSocket := new ServerSocket(SERVER_PORT, MAX_CLIENTS);  
  except
    on E : Exception do
      ReportError(E);
  end;  
  writeln('Waiting');    
  repeat
    try
      clientSocket := serverSocket.accept;
    except  
      on E : Exception do
        ReportError(E);
    end;  
    connectionHandler := ConnectionHandler.Create(clientSocket);
    t := new Thread(connectionHandler);
    t.start;    
  until false;
end.

Code of Client

This code is the same as that of echo_client02, but we reproduce it here for convenience.
namespace echo_client03;

interface

uses
  java.io.*, java.net.*;

implementation

const
  SERVER_PORT = 1717;
var
  sourceString, echoedString, ip_string : String;
  pw : PrintWriter := nil;
  br : BufferedReader := nil;
  isr : InputStreamReader := nil;
  clientSocket : Socket := nil;
  ip : array[0 .. 20] of SByte;
  msg : array[0 .. 20] of SByte;  
begin  
  writeln('Please enter IP address of server (127.0.0.1 for same machine as client).');
  System.in.read(ip);
  ip_string := new String(ip).trim;
  try
    clientSocket := new Socket(InetAddress.getByName(ip_string), SERVER_PORT);
    pw := new PrintWriter(clientSocket.getOutputStream, true);
    isr := new InputStreamReader(clientSocket.getInputStream);  
    br := new BufferedReader(isr);
  except
    on E : Exception do
      begin
        writeln(E.toString);
        System.in.read;
        System.exit(0);  
      end;  
  end;    
  repeat 
    writeln('Please enter short string to be echoed.');
    writeln('Enter quit to quit the server and end to quit the client.');
    msg := [32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32];
    System.in.read(msg);
    sourceString := new String(msg).trim;
    pw.println(sourceString);  
    if (sourceString <> 'quit') and (sourceString <> 'end') then
      begin
        echoedString := br.readLine;
        writeln('The echoed string: ' + echoedString);
      end;
  until (sourceString = 'quit') or (sourceString = 'end');  
  pw.close;
  br.close;
  isr.close;
  clientSocket.close;
end.

Equivalent Code of Server in RemObjects C# for Java

using java.util;
using java.io; 
using java.net;

namespace echo_server03cs_java
{
  public void ReportError(Exception E)
  {
    System.@out.println (E.toString());
    System.@in.read();
    System.exit(0);
  } 

  public class ConnectionHandler: Runnable
  {
    private Socket cs = null;
    private PrintWriter pw = null;
    private BufferedReader br = null;
    private InputStreamReader isr = null;
    private String msg ="";
    public ConnectionHandler(Socket s)
    {
      cs = s;
      try
      {    
        isr = new InputStreamReader(cs.getInputStream());
        br = new BufferedReader(isr);
        pw = new PrintWriter(cs.getOutputStream(), true);
      }
      catch(Exception E) 
      {
        ReportError(E);
      }  
    }

    public void run()
    {
      while ((msg != "end") && (msg != "quit"))
      {
        msg = br.readLine();
        if ((msg != "quit") && (msg != "end"))
        {
          pw.println(msg);
          System.@out.println("Echoing " + msg);  
        }
      }
      pw.close();
      isr.close();
      br.close();
      cs.close();
      if (msg == "quit")
        System.exit(0);
      
    }
  }

  static class Program
  { 
    public static void Main(string[] args)
    {
      const Integer  MAX_CLIENTS = 5;
      const Integer SERVER_PORT = 1718;
      ServerSocket  serverSocket = null;
      Socket  clientSocket = null;
      ConnectionHandler connectionHandler;
      Thread t; 
      try
      {
        serverSocket = new ServerSocket(SERVER_PORT, MAX_CLIENTS);
      }
      catch(Exception E)
      {
        ReportError(E);
      }   
      System.@out.println("Waiting");    
      while(true)
      {
        try
        {
          clientSocket = serverSocket.accept();
        }

        catch(Exception E)
        {
          ReportError(E);
        }

        connectionHandler = new ConnectionHandler(clientSocket);
        t = new Thread(connectionHandler);
        t.start();    
      }
    }
  }
}

Equivalent Code of the Client in RemObjects C# for Java

using java.util;
using java.io;
using java.net;

namespace echo_client03cs
{
  static class Program
  {
    public static void Main(string[] args)
    {
      const Integer SERVER_PORT = 1718;
      String sourceString, echoedString, ip_string;
      PrintWriter pw = null;
      BufferedReader br = null;
      InputStreamReader isr = null;
      Socket clientSocket = null;
      SByte[] ip = new SByte[20]; //ip[0] .. ip[19]
      SByte[] msg = new SByte[20];
      sourceString ="";
      System.@out.println("Please enter IP address of server" +
                          " (127.0.0.1 for same machine as client).");
      System.@in.read(ip);
      ip_string = new String(ip).trim();
      try
      {
        clientSocket = new Socket(InetAddress.getByName(ip_string),
                                   SERVER_PORT);
        pw = new PrintWriter(clientSocket.getOutputStream(), true);
        isr = new InputStreamReader(clientSocket.getInputStream());  
        br = new BufferedReader(isr);
      }

      catch(Exception E)
      {
        System.@out.println(E.toString());
        System.@in.read();
        System.exit(0);        
      }
    
      while ((sourceString != "quit") && (sourceString != "end"))
      { 
        System.@out.println("Please enter short string to be echoed.");
        System.@out.println("Enter quit to quit the server and " +
                       "end to quit the client.");
        msg = {32, 32, 32, 32, 32, 32, 32, 32, 32, 32,
                32, 32, 32, 32, 32, 32, 32, 32, 32, 32};
        System.@in.read(msg);
        sourceString = new String(msg).trim();
        pw.println(sourceString);
        if ((sourceString != "quit") && (sourceString != "end"))
        {
          echoedString = br.readLine();
          System.@out.println("The echoed string " + echoedString);
        }
      }  
      pw.close();
      br.close();
      isr.close();
      clientSocket.close();
    }
  }
}
Programming - a skill for life!

How to write client-server applications using TCP Sockets in Oxygene for Java