I have a Java application that has a TCP Server and It handles the client requests. Now I want to create a TCP backup Server, so that when the TCP Server Fails, the backup server continues from the point the TCP Server failed and Handle the client request.
How this can be done?
I have a client and a server.
This is my code for TCP Server for now..
import java.net.*;
import java.io.*;
import javax.script.ScriptEngineManager;
import javax.script.ScriptEngine;
import javax.script.ScriptException;
public class TCPServer {
static ScriptEngineManager mgr;
static ScriptEngine engine;
public static void main(String args[]) {
mgr = new ScriptEngineManager();
engine = mgr.getEngineByName("js");
try {
int serverPort = 7896; // the server port
ServerSocket listenSocket = new ServerSocket(serverPort);
while (true) {
System.out.println("Server is ready and waiting for requests .... ");
Socket clientSocket = listenSocket.accept();
System.out.println("request received from client with IP : " + clientSocket.getInetAddress());
System.out.println("port of client : " + clientSocket.getPort());
Thread c = new Connection(clientSocket);
}
} catch (IOException e) {
//if already in use then redirect the request to backup server
System.out.println("Listen socket:" + e.getMessage());
}
}
}
class Connection extends Thread {
DataInputStream in;
DataOutputStream out;
Socket clientSocket;
public Connection(Socket aClientSocket) {
try {
clientSocket = aClientSocket;
in = new DataInputStream(clientSocket.getInputStream());
out = new DataOutputStream(clientSocket.getOutputStream());
this.start();
} catch (IOException e) {
System.out.println("Connection:" + e.getMessage());
}
}
public void run() {
//send client request to bacckup server, with client IP adddress and port number
//BackupTCPServer bus = new BackupTCPServer();
//bus.clientIP = clientSocket.getInetAddress();
//bus.clientPort = clientSocket.getPort();
//System.out.println(bus);
try {
String s = in.readUTF();
//bus.Expressionsbackup.add(s);
String exp = "";
int res = 0;
while (s != null) {
TCPServer.engine.put("i", 2);
TCPServer.engine.put("j", 4);
exp =s;
Object result = TCPServer.engine.eval(exp);
double st = (Double)result;
out.writeUTF(Double.toString(st));
//bus.expressionevaluated++;
s = in.readUTF();
}
}
catch (ScriptException se) {
System.out.println("SE:" + se.getMessage());
}
catch (EOFException e) {
System.out.println("EOF:" + e.getMessage());
} catch (IOException e) {
System.out.println("readline:" + e.getMessage());
} finally {
try {
clientSocket.close();
} catch (Exception e) {
/*close failed*/
}
}
}
}
Related
I am building a multithreaded chat server application which broadcasts a message sent by one client to all the clients.On most of the examples on internet and on Oracle's website too broadcasting is done using udp (Multicast Socket)but i am using tcp .
Does anyone know how to send a message to all the connected clients in a tcp conection?
Here is my current code which works fine and sends the message receieved from a client to that client only:
EchoServer
import java.net.*;
import java.io.*;
public class EchoServer
{
public static void main(String[] args)
throws IOException
{
if (args.length != 1) {
System.err.println("Usage: java EchoServer <port number>");
System.exit(1);
}
int portNumber = Integer.parseInt(args[0]);
ServerSocket serverSocket = new ServerSocket(Integer.parseInt(args[0]));
while (true) {
try {
Thread t = new Thread(new MultiServer(serverSocket.accept()));
t.start();
} catch(IOException e) {
System.out.println("Accept Failed:");
System.exit(-1);
}
}
}
}
EchoClient
import java.io.*;
import java.util.Scanner;
import java.net.*;
public class EchoClient
{
public static void main(String[] args) throws IOException
{
if (args.length != 2) {
System.err.println("Usage: java EchoClient <host name><portnumber>");
System.exit(1);
}
String hostName = "localhost";
int portNumber = Integer.parseInt(args[1]);
try (
Socket echoSocket = new Socket(hostName, portNumber);
PrintWriter out = new PrintWriter(echoSocket.getOutputStream(), true);
BufferedReader in = new BufferedReader(new InputStreamReader(echoSocket.getInputStream()));
BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
) {
String userInput;
while ((userInput = stdIn.readLine()) != null) {
out.println(userInput);
System.out.println("echo::" + in.readLine());
}
} catch (UnknownHostException e) {
System.err.println("Don't know about host " + hostName);
System.exit(1);
} catch (IOException e) {
System.err.println("Couldn't get I/O for the connection to " + hostName);
System.exit(1);
}
}
}
MultiServer
import java.io.*;
import java.net.*;
public class MultiServer implements Runnable
{
private Socket client;
public MultiServer(Socket m)
{
this.client = m;
}
#Override
public void run()
{
BufferedReader in = null;
PrintWriter out = null;
try {
out = new PrintWriter(client.getOutputStream(), true);
in = new BufferedReader(new InputStreamReader(client.getInputStream()));
} catch(IOException ignored) {
}
while (true) {
String line;
try {
while ((line = in.readLine()) != null)
out.println(line);
} catch (IOException e) {
System.out.println("Read Failed");
System.exit(-1);
}
}
}
}
Use the concurrent hashmap and maintain your list of clients in that.
The concurrent hashmap is safe and you won't need to use synchronization while adding / iterating / removing
// Create and main list of active clients based on their host name / ip address
ConcurrentHashMap<String, Socket> activeClients = new ConcurrentHashMap<String, Socket>();
// message received
activeClients.put(clientsocket.getInetAddress().getHostAddress(), clientsocket);
// broadcast message to all available clients
for(String clientHost : activeClients.keySet()) {
// get each socket here and send a message to them.
}
Vector is basically a thread safe one so you don't need to worry about that one.
There are many tutorials where explains about socket server/client sides, but all them are very trivial. Is there any tutorial for production ready code? I'm new in sockets. There is a client, that sends strings to server. I must create the server side. in server side I read string from client and after some manipulation saves them in db. I must response to client only IF I get string like "Error" for example. and if there are no any daya from client in 30 secs, I must close client connection, but server side must works. this is my test Client side:
public class ClientSideSocket2 {
public static void main(String[] args) {
String serverName = "localhost";
int port = 5555;
String line = "";
Socket client = null;
try {
System.out.println("Connecting to " + serverName + " on port " + port);
client = new Socket(serverName, port);
System.out.println("Just connected to " + client.getRemoteSocketAddress());
PrintWriter toServer = new PrintWriter(client.getOutputStream(), true);
BufferedReader fromServer = new BufferedReader(new InputStreamReader(client.getInputStream()));
List<String> messages = new ArrayList<>();
for (int i = 0; i < 6; i++) {
messages.add("Message " + i+1);
}
messages.add("abc");
for (int i = 0; i < messages.size(); i++) {
toServer.println(messages.get(i));
if ((line = fromServer.readLine()) != null) {
System.out.println("Responce from server: " + line);
}
}
toServer.close();
fromServer.close();
} catch (IOException ex) {
ex.printStackTrace();
} finally {
try {
client.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
and my server side:
public class TRSServerInterface implements Runnable {
private ServerSocket serverSocket = null;
private Socket socket = null;
boolean runner = true;
String message = "";
public TRSServerInterface() {}
#Override
public void run() { // default run method of Thread class and Runnable interface
try {
int serverPort = 5555;
ServerSocket serverSocket = new ServerSocket(serverPort);
while(true) {
System.out.println("Waiting for connection...");
socket = serverSocket.accept();
System.out.println("Connected to " + socket.getRemoteSocketAddress());
//get the input and output streams
PrintWriter toClient = new PrintWriter(socket.getOutputStream(), true);
BufferedReader fromClient = new BufferedReader(new InputStreamReader(socket.getInputStream()));
do {
message = fromClient.readLine();
System.out.println("From client > " + message);
if (message.equals("abc")) {
toClient.println("Message from server");
}
else {
toClient.println("");
}
} while (!message.equals(""));
}
} catch (IOException ex) {
ex.printStackTrace();
} finally {
// try {
// objectOut.close();
// objectIn.close();
// socket.close();
// } catch (IOException e) {
// e.printStackTrace();
// }
}
}
}
is my solution corrent and how I can close connection with client if there are no any data in 30 secs.
There are several production ready frameworks that should be used instead of rolling your own. Socket timeouts can be used to control how long different operations are allowed to take before an exception is thrown.
I have a problem using sockets in Java: the server doesn't respond and no exception is thrown.
Server Code:
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Scanner;
class Server {
public static void main(String args[]) {
final int time = 75;
//boolean CHAT_SESSION_ALIVE = false;
int port = 9999;
try {
System.out.println("Starting chat server using the port : " + port);
ServerSocket srvr = new ServerSocket(port);
Socket skt = srvr.accept();
System.out.println("Server has connected with client " + skt.getInetAddress());
//CHAT_SESSION_ALIVE = true;
PrintWriter out = new PrintWriter(skt.getOutputStream(), true);
BufferedReader in = new BufferedReader(new InputStreamReader(skt.getInputStream()));
new Thread(new Runnable() {
#Override
public void run() {
while (true) {
try {
if (in.ready()) {
String msg = in.readLine();
System.out.println("receive message: '" + msg + "'");
Thread.sleep(time);
}
} catch (Exception e) {
System.out.println(e);
}
}
}
}).start();
new Thread(new Runnable() {
#Override
public void run() {
while (true) {
try {
Thread.sleep(time);
String msg = new Scanner(System.in).nextLine();
System.out.println("Sending message: '" + msg + "'");
out.print(msg);
} catch (Exception e) {
System.out.println(e);
}
}
}
}).start();
//in.close();
//out.close();
//skt.close();
//srvr.close();
} catch (Exception e) {
System.out.print(e);
}
}
}
Client Code:
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Scanner;
class Client {
public static void main(String args[]) {
final int time = 75;
//boolean CHAT_SESSION_ALIVE = false;
int port = 9999;
String hostIP = "127.0.0.1";
try {
Socket skt = new Socket(hostIP, port);
System.out.println("Client has connected with server " + hostIP + ":" + port);
//CHAT_SESSION_ALIVE = true;
PrintWriter out = new PrintWriter(skt.getOutputStream(), true);
BufferedReader in = new BufferedReader(new InputStreamReader(skt.getInputStream()));
new Thread(new Runnable() {
#Override
public void run() {
while (true) {
try {
if (in.ready()) {
String msg = in.readLine();
System.out.println("receive message: '" + msg + "'");
Thread.sleep(time);
}
} catch (Exception e) {
System.out.println(e);
}
}
}
}).start();
new Thread(new Runnable() {
#Override
public void run() {
while (true) {
try {
String msg = new Scanner(System.in).nextLine();
System.out.println("Sending message: '" + msg + "'");
out.print(msg);
Thread.sleep(time);
} catch (Exception e) {
System.out.println(e);
}
}
}
}).start();
//in.close();
//out.close();
//skt.close();
} catch (Exception e) {
System.out.print(e);
}
}
}
The server output:
Starting chat server using the port : 9999
Server has connected with client /127.0.0.1
The client output:
Client has connected with server 127.0.0.1:9999
simple message
Sending message: 'simple message'
Please explain why the server isn't working correctly.
Scanner.nextLine returns the line without the new line delim. The server is using BufferedReader.readLine, which expects a new line (or may block if it does not receive one). Solution: append the delimiter when sending messages. If using print, you must explicitly flush:
out.print(msg + "\n");
out.flush();//explicitly flush the stream
or use the println method to have it add the new line for you (and makes use of autoflush true flag passed to the PrintWriter constructor):
out.println(msg);//auto flushing
In both codes, put an out.flush() just right after the instanciation of PrintWriter out
I am trying to forward a message from a client to a server and again from that server to another server. For the first time it works fine but when I type second message its say "Unexpected exception: Connection refused" why is it so?
Here is the code
Client.java
import java.net.*;
import java.io.*;
public class Client {
private Socket socket = null;
private DataInputStream console = null;
private DataOutputStream streamOut = null;
#SuppressWarnings("deprecation")
public Client(String serverName, int serverPort) {
System.out.println("Establishing connection. Please wait ...");
try {
socket = new Socket(serverName, serverPort);
System.out.println("Connected: " + socket);
start();
} catch (UnknownHostException uhe) {
System.out.println("Host unknown: " + uhe.getMessage());
} catch (IOException ioe) {
System.out.println("Unexpected exception: " + ioe.getMessage());
}
String line = "";
while (!line.equals("exit")) {
try {
line = console.readLine();
streamOut.writeUTF(line);
streamOut.flush();
} catch (IOException ioe) {
System.out.println("Sending error: " + ioe.getMessage());
}
}
}
public void start() throws IOException {
console = new DataInputStream(System.in);
streamOut = new DataOutputStream(socket.getOutputStream());
}
public void stop() {
try {
if (console != null)
console.close();
if (streamOut != null)
streamOut.close();
if (socket != null)
socket.close();
} catch (IOException ioe) {
System.out.println("Error closing ...");
}
}
public static void main(String args[]) {
#SuppressWarnings("unused")
Client client = null;
if (args.length != 2)
System.out.println("Usage: java Client host port");
else
client = new Client(args[0], Integer.parseInt(args[1]));
}
}
AuServer.java
import java.net.*;
import java.io.*;
public class AuServer {
private Socket socket = null;
private Socket publishingsocket = null;
private ServerSocket server = null;
private DataInputStream streamIn = null;
private String line = null;
private DataOutputStream streamOut = null;
public AuServer(int port) {
try {
System.out.println("Binding to port " + port + ", please wait ...");
server = new ServerSocket(port);
System.out.println("Server started: " + server);
System.out.println("Waiting for a client ...");
socket = server.accept();
System.out.println("Client accepted: " + socket);
open();
boolean done = false;
while (!done) {
try {
line = streamIn.readUTF();
System.out.println(line);
done = line.equals("exit");
} catch (IOException ioe) {
done = true;
}
forward(line, 50090);
}
close();
} catch (IOException ioe) {
System.out.println(ioe);
}
}
public void forward(String line, int port) {
try {
publishingsocket = new Socket("localhost", port);
streamOut = new DataOutputStream(publishingsocket.getOutputStream());
streamOut.writeUTF(line);
streamOut.flush();
} catch (UnknownHostException uhe) {
System.out.println("Host unknown: " + uhe.getMessage());
} catch (IOException ioe) {
System.out.println("Unexpected exception: " + ioe.getMessage());
} finally {
try {
publishingsocket.close();
} catch (IOException e) {
System.out.println(e.getMessage());
}
}
}
public void open() throws IOException {
streamIn = new DataInputStream(new BufferedInputStream(
socket.getInputStream()));
}
public void close() throws IOException {
if (socket != null)
socket.close();
if (streamIn != null)
streamIn.close();
}
public static void main(String args[]) {
#SuppressWarnings("unused")
AuServer server = null;
if (args.length != 1)
System.out.println("Usage: java Server port");
else
server = new AuServer(Integer.parseInt(args[0]));
}
}
AppServer.java
import java.net.*;
import java.io.*;
public class AppServer {
private Socket socket = null;
private ServerSocket server = null;
private DataInputStream streamIn = null;
public AppServer(int port) {
try {
System.out.println("Binding to port " + port + ", please wait ...");
server = new ServerSocket(port);
System.out.println("Server started: " + server);
System.out.println("Waiting for a client ...");
socket = server.accept();
System.out.println("Client accepted: " + socket);
open();
boolean done = false;
while (!done) {
try {
String line = streamIn.readUTF();
System.out.println(line);
done = line.equals("exit");
} catch (IOException ioe) {
done = true;
}
}
close();
} catch (IOException ioe) {
System.out.println(ioe);
}
}
public void open() throws IOException {
streamIn = new DataInputStream(new BufferedInputStream(
socket.getInputStream()));
}
public void close() throws IOException {
if (socket != null)
socket.close();
if (streamIn != null)
streamIn.close();
}
public static void main(String args[]) {
#SuppressWarnings("unused")
AppServer server = null;
server = new AppServer(50090);
}
}
Pls help............
A typically socket server would require some kind of loop where in the server socket would accept incoming connections and spawn a new Thread which would be responsible for actually handling the new Socket connection, leaving the current thread free to continue processing any new incoming connections, for example...
server = new ServerSocket(port);
while (continueAccpetingConnections) {
Socket socket = server.accept();
Thread thread = new Thread(new SocketHandler(socket));
thread.start();
}
The SocketHandler would implement Runnable and provide a constructor that would accept a Socket variable.
It would then be the responsibility of the SocketHandler to actually perform the communications required by the server.
Now, if you wanted to have only one active connection, you might use
while (continueAccpetingConnections) {
Socket socket = server.accept();
process(socket);
}
Which would prevent any new connections until process returned...
Your server is written to accept exactly one connection, process it in the same thread, and then exit. If you want to keep accepting connections, do so, in a loop. If you want to handle clients concurrently, start a new thread to handle each accepted socket.
The code below should allow the user to enter a URL and have it return the ip address of that website but it's not working.
The application is a console application. I had it working at one time but I don't know why it won't work now.
Here is the error i am getting when the users enters a website to get the ip address from
IOException: java.net.SocketException: Connection reset
HERE IS MY CLIENT CODE
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
public class Client {
public static void main(String[] args) {
String hostname = "localhost";
int port = 6052;
if (args.length > 0) {
hostname = args[0];
}
Socket clientSocket = null;
PrintWriter os = null;
BufferedReader is = null;
try {
clientSocket = new Socket(hostname, port);
os = new PrintWriter(clientSocket.getOutputStream(), true);
is = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
} catch (UnknownHostException e) {
System.err.println("Don't know about host: " + hostname);
} catch (IOException e) {
System.err.println("Couldn't get I/O for the connection to: " + hostname);
}
if (clientSocket == null || os == null || is == null) {
System.err.println("Something is really wrong. ");
return;
}
try {
if (args.length != 2) {
System.out.print("Enter a www web address (must have www!) ");
BufferedReader br = new BufferedReader(new InputSreamReader(Sy.in))
String keyboardInput = br.readLine();
os.println(keyboardInput);
} else {
os.println(args[1]);
}
String responseLine = is.readLine();
System.out.println("The IP address of " + args[1] + "is" + responseLine);
} catch (UnknownHostException e) {
System.err.println("Trying to connect to host: " + e);
} catch (IOException e) {
System.err.println("IOException: " + e);
}
}
}
HERE IS MY SERVER CODE
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
public class Server {
public static void main(String args[]) {
int port = 6052;
Server server = new Server(port);
server.startServer();
}
ServerSocket echoServer = null;
Socket clientSocket = null;
int numConnections = 0;
int port;
public Server(int port) {
this.port = port;
}
public void stopServer() {
System.out.println("Server working hold on a min.");
System.exit(0);
}
public void startServer() {
try {
echoServer = new ServerSocket(port);
} catch (IOException e) {
e.printStackTrace();
}
System.out.println("Server is now started and is waiting for Clients.");
while (true) {
try {
clientSocket = echoServer.accept();
numConnections++;
new Thread(new ServerConnection(clientSocket, numConnections,
this)).start();
} catch (IOException e) {
System.out.println(e);
}
}
}
}
class ServerConnection implements Runnable {
private static BufferedReader is;
private static PrintStream os;
private static Socket clientSocket;
private static int id;
private static Server server;
public ServerConnection(Socket clientSocket, int id, Server server) {
this.clientSocket = clientSocket;
this.id = id;
this.server = server;
System.out.println( "Connection " + id + " established with: " + clientSocket );
try {
is = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
os = new PrintStream(clientSocket.getOutputStream());
} catch (IOException e) {
System.out.println(e);
}
}
public void run() {
String line;
try {
boolean serverStop = false;
line = is.readLine();
System.out.println( "Received " + line + " from Connection " + id + "." );
InetAddress hostAddress = InetAddress.getByName(line);
String IPaddress = hostAddress.getHostAddress();
os.println(IPaddress);
is.close();
os.close();
clientSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
With no arguments, host will be localhost, user will be propted for a website. ArrayOutOfBoundsException because you didn't check the arguments.
With one argument, it is the host. Passing a site will not work because the site won't work as expected.
Running with two arguments, it works if the first argument is localhost.