Why does my Socket client only receive 1 packet? - java

I have a chess server and client that I made in Java that transfers packets to each other. When a client connects, the server sends a packet back to the client. My program always detects this packet. After that when I try to move a piece, a packet is sent to the server and the server detects it. It prints the packet string to the client which the client uses to move the piece, but the client never reads it. How do I fix this?
Connection superclass:
public class ChessConnection {
protected Socket socket;
protected PrintWriter output;
protected BufferedReader input;
public void listen() {
try {
String line;
while ((line = input.readLine()) != null) {
this.inputReceived(line);
}
} catch (SocketException e) {
System.out.println("SocketException: " + e.getMessage());
} catch (IOException e) {
System.out.println("IOException: " + e.getMessage());
e.printStackTrace();
}
}
public void sendPacket(Packet packet) {
output.println(packet.serialize());
};
public void inputReceived(String input) {}
}
ClientConnection (Client side):
public class ClientConnection extends ChessConnection {
public ClientConnection() {
try {
socket = new Socket("localhost", 4141);
output = new PrintWriter(socket.getOutputStream(), true);
input = new BufferedReader(new InputStreamReader(socket.getInputStream()));
} catch (HeadlessException e) {
e.printStackTrace();
} catch (UnknownHostException e) {
System.out.println("Host is unknown");
} catch (IOException e) {
e.printStackTrace();
}
new Thread(this::listen).start();
}
#Override
public void listen() {
try {
String line;
while ((line = input.readLine()) != null) {
System.out.println("client received input: " + line); // This doesn't print the move piece packet, but it does print the connection packet
this.inputReceived(line);
}
} catch (SocketException e) {
System.out.println("SocketException: " + e.getMessage());
} catch (IOException e) {
System.out.println("IOException: " + e.getMessage());
e.printStackTrace();
}
}
}
ServerConnection (Server side):
public class ServerConnection extends ChessConnection {
private static int NEXT_ID = 1;
private static ArrayList<ServerConnection> clients = new ArrayList<ServerConnection>();
public int connectionId;
public ServerHandler handler;
public ServerConnection(ServerHandler handler, Socket socket) {
this.connectionId = NEXT_ID++;
this.handler = handler;
try {
this.socket = socket;
this.output = new PrintWriter(socket.getOutputStream(), true);
this.input = new BufferedReader(new InputStreamReader(socket.getInputStream()));
} catch (Exception e) {
e.printStackTrace();
}
new Thread(this::listen).start(); // Starts listening to client
System.out.println("Client " + this.connectionId + " connected");
sendPacket(new ConnectionPacket());
}
#Override
public void listen() {
try {
String line;
while ((line = input.readLine()) != null) {
this.inputReceived(line);
}
} catch (SocketException e) {
System.out.println("SocketException: " + e.getMessage());
handler.broadcastPacket(new DisconnectionPacket());
System.out.println("Client " + this.getId() + " disconnected");
} catch (IOException e) {
System.out.println("IOException: " + e.getMessage());
e.printStackTrace();
}
}
#Override
public void inputReceived(String input) {
System.out.println("server received input: " + input);
Packet packet = Packet.toPacket(input);
switch (packet.getType()) {
case Packet.DISCONNECTION:
break;
case Packet.CONNECTION:
break;
case Packet.PIECE_MOVE:
System.out.println("sending move piece");
handler.broadcastPacket(packet);
break;
case Packet.PAWN_REPLACEMENT:
break;
default:
System.out.println("Received malformed packet: " + input);
break;
}
}
public int getId() {
return this.connectionId;
}
public static ServerConnection getClientFromId(int clientId) {
for (ServerConnection client : clients) {
if (client.getId() == clientId) {
return client;
}
}
return null;
}
}

Related

Not getting muliple instances of multithreaded datastream

I am using a data generator which uses ports for streaming data. I use multiple ports mfor receiving data. The software I am writing makes a new socket for each port. Every socket should make an instance of a class called 'Interpreter'.
The problem I have is the following: I am able to make multiple instances of Interpreter, but I think the data is all being parsed to only one of the instances. I think this happens because the data is 'merged' in the output.
This is the most important snipet of the code:
public class Main {
public static void main (String[] args) {
Socket socket;
ServerSocket serverSocket=null;
System.out.println("Server Listening..");
try{
serverSocket = new ServerSocket(7789);
}
catch(IOException e){
e.printStackTrace();
System.out.println("Error");
}
while(true){
try{
socket= serverSocket.accept();
Interpreter interp = new Interpreter();
ServerThread serverThr=new ServerThread(socket, interp);
serverThr.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, Interpreter interp) {
this.interp = interp;
this.s = s;
System.out.println("interp "+interp);
System.out.println("s: "+s);
System.out.println("poort: "+s.getPort());
}
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();
Interpreter.interpreter(line);
line = is.readLine();
}
} catch (IOException e) {
line = this.getName();
System.out.println("IO Error/ Client " + line + " terminated abruptly");
} catch (NullPointerException e) {
line = this.getName();
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");
}
}
}
}
This is the 'important' part of Interpreter:
public class Interpreter{
static AtomicInteger nextId = new AtomicInteger();
int id = nextId.incrementAndGet();
public Interpreter(){
System.out.println("ID of demo "+id);
}
}

Java: How to set timeout on client socket connection and disconnect idle users?

can you tell me how to set timeout on client socket connection? I've downloaded the example and I don't understand Java at all, so please help. I hope I won't get a bunch of hateful comments.
Here is my "Client" class:
import java.net.*;
import java.io.*;
import java.util.*;
public class Client {
private ObjectInputStream sInput;
private ObjectOutputStream sOutput;
private Socket socket;
private ClientGUI cg;
private String server, username;
private int port;
Client(String server, int port, String username) {
this(server, port, username, null);
}
Client(String server, int port, String username, ClientGUI cg) {
this.server = server;
this.port = port;
this.username = username;
this.cg = cg;
}
public boolean start() {
try {
Socket socket = new Socket();
}
catch(Exception ec) {
display("Error connectiong to server:" + ec);
return false;
}
String msg = "Connection accepted " + socket.getInetAddress() + ":" + socket.getPort();
display(msg);
try
{
sInput = new ObjectInputStream(socket.getInputStream());
sOutput = new ObjectOutputStream(socket.getOutputStream());
}
catch (IOException eIO) {
display("Exception creating new Input/output Streams: " + eIO);
return false;
}
new ListenFromServer().start();
try
{
sOutput.writeObject(username);
}
catch (IOException eIO) {
display("Exception doing login : " + eIO);
disconnect();
return false;
}
return true;
}
private void display(String msg) {
if(cg == null)
System.out.println(msg);
else
cg.append(msg + "\n");
}
void sendMessage(ChatMessage msg) {
try {
sOutput.writeObject(msg);
}
catch(IOException e) {
display("Exception writing to server: " + e);
}
}
private void disconnect() {
try {
if(sInput != null) sInput.close();
}
catch(Exception e) {}
try {
if(sOutput != null) sOutput.close();
}
catch(Exception e) {}
try{
if(socket != null) socket.close();
}
catch(Exception e) {}
if(cg != null)
cg.connectionFailed();
}
public static void main(String[] args) {
int portNumber = 1500;
String serverAddress = "localhost";
String userName = "Anonymous";
switch(args.length) {
case 3:
serverAddress = args[2];
case 2:
try {
portNumber = Integer.parseInt(args[1]);
}
catch(Exception e) {
System.out.println("Invalid port number.");
System.out.println("Usage is: > java Client [username] [portNumber] [serverAddress]");
return;
}
case 1:
userName = args[0];
case 0:
break;
default:
System.out.println("Usage is: > java Client [username] [portNumber] {serverAddress]");
return;
}
Client client = new Client(serverAddress, portNumber, userName);
if(!client.start())
return;
Scanner scan = new Scanner(System.in);
while(true) {
System.out.print("> ");
String msg = scan.nextLine();
if(msg.equalsIgnoreCase("LOGOUT")) {
client.sendMessage(new ChatMessage(ChatMessage.LOGOUT, ""));
break;
}
else if(msg.equalsIgnoreCase("WHOISIN")) {
client.sendMessage(new ChatMessage(ChatMessage.WHOISIN, ""));
}
else {
client.sendMessage(new ChatMessage(ChatMessage.MESSAGE, msg));
}
}
client.disconnect();
}
class ListenFromServer extends Thread {
public void run() {
while(true) {
try {
String msg = (String) sInput.readObject();
if(cg == null) {
System.out.println(msg);
System.out.print("> ");
}
else {
cg.append(msg);
}
}
catch(IOException e) {
display("Server has close the connection: " + e);
if(cg != null)
cg.connectionFailed();
break;
}
catch(ClassNotFoundException e2) {
}
}
}
}
}
To set a timeout you can use
socket.setSoTimeout(timeInMillis);
Note: if this timeout is reached you get a SocketTimeoutException on the read, and you will need to close the connection.

Server not receiving input from client

I have a server and client. My problem is that when the client writes messages, the server is not receiving the messages.
Server code
public class BankServer {
private int port;
private BufferedReader reader = null;
private PrintWriter writer = null;
public BankServer(int port)
{
this.port = port;
}
public void startServer() {
print("Contact server at: " + getServerAddress() + ": port: " + port);
while(true) {
try {
ServerSocket ss = new ServerSocket(port);
Socket client = ss.accept();
if(client != null) {
print("Client connected");
}
reader = new BufferedReader(new InputStreamReader(client.getInputStream()));
writer = new PrintWriter(client.getOutputStream(), true);
String msg = null;
print("Server waiting for input");
while((msg = reader.readLine()) != null) {
print("Printer: " + msg);
writer.write(msg);
}
client.close();
ss.close();
closeStreams();
} catch (IOException e) {
e.printStackTrace();
}
}
}
private void closeStreams() {
if(reader != null) {
try {
reader.close();
} catch (IOException e) {
e.printStackTrace();
} }
if(writer != null) {
writer.close();
}
}
private String getServerAddress() {
InetAddress inetAdr = null;
try {
inetAdr = InetAddress.getLocalHost();
} catch (UnknownHostException e) {
e.printStackTrace();
}
String host = inetAdr.getHostAddress();
return host;
}
public void print(String msg) {
System.out.println(msg);
}
public static void main(String[] args) {
new BankServer(2222).startServer();
}
}
I have this code, where the Server waits for input:
ServerSocket ss = new ServerSocket(port);
Socket client = ss.accept();
if(client != null) {
print("Client connected");
}
From this code, I can see that a connection is made. But when client sends messages, they are not printed by the server
Here is the client code:
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Scanner;
public class BankClient {
private PrintWriter writer = null;
private BufferedReader reader = null;
private Socket socket;
private int port;
private String adr;
public BankClient(String address, int port)
{
adr = address;
this.port = port;
try {
socket = new Socket(adr, this.port);
reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
writer = new PrintWriter(socket.getOutputStream());
} catch (IOException e) {
e.printStackTrace();
}
}
public void writeMsg(String msg) {
try {
while((msg = reader.readLine()) != null) {
writer.print("From client: " + msg);
}
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
BankClient client = new BankClient("127.0.0.1", 2222);
Scanner scanner = new Scanner(System.in);
System.out.println("Waiting for input");
while(true) {
String msg = scanner.nextLine();
client.writeMsg(msg);
if(msg.equals("quit")) {
System.out.println("Bye");
break;
}
}
scanner.close();
}
}
This is the first time I work with streams, and I am also pretty new to programming. I have found a lot of help on stackoverflow, and google, but I just can't figure this out.
Thanks for any help you can provide
Replace :
public void writeMsg(String msg) {
try {
while((msg = reader.readLine()) != null) {
writer.print("From client: " + msg);
}
} catch (IOException e) {
e.printStackTrace();
}
}
By :
public void writeMsg(String msg) {
try {
DataOutputStream outToServer = new DataOutputStream(socket.getOutputStream());
outToServer.writeBytes("From client: " + msg + "\n");
} catch (IOException e) {
e.printStackTrace();
}
}
Client Side:
Server Side :
Change
writer.print("From client: " + msg);
to
writer.println("From client: " + msg);
and remove the while((msg = reader.readLine()) != null) at the client.
EDIT: And you have to add writer.flush();. That worked for me.
EDIT2: The complete solution. Change BankClient here:
public void writeMsg(String msg) {
writer.println("From client: " + msg);
writer.flush();
}

how to detect client's Internet speed from the response headers in java?

I have a server to get a response headers through which I detect the type of device. Is there any way I can get the Internet speed through response headers or any other method ?
Server_X:
public class Server_X {
static int count = 0;
public static void main(String args[]) {
Socket s = null;
ServerSocket ss2 = null;
System.out.println("Server Listening......");
try {
// can also use static final PORT_NUM, when defined
ss2 = new ServerSocket(4445);
} 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);
count++;
System.out.println("total connections :" + count);
st.start();
}
catch (Exception e) {
e.printStackTrace();
System.out.println("Connection Error");
}
}
}
}
ServerThread:
class ServerThread extends Thread {
static String uagent, uaccept;
static String[] b;
static String[] c;
Server_X obj = new Server_X();
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(line);
line = is.readLine();
b = line.split(":");
if (b[0].equals("User-Agent")) {
uagent = b[1];
// System.out.println(uagent);
}
c = line.split(":");
if (c[0].equals("Accept")) {
uaccept = c[1];
// System.out.println(uaccept);
}
UAgentInfo detect = new UAgentInfo(uagent, uaccept);
}
} 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");
obj.count--;
System.out.println("Toatal connections (after closing):"
+ obj.count);
}
} catch (IOException ie) {
// System.out.println("Socket Close Error");
}
}// end finally
}
}
You didn't specify what protocol the server is using; I suppose is HTTP since you're catching "User-Agent" and "Accept". If I'm correct, there's no header with the information you're looking for, as you can check on https://en.wikipedia.org/wiki/List_of_HTTP_header_fields.

Java IO socket not sending outputstream

When debugging my code, the code stops here:
while (( msg = reader.readLine()) != null) {
writer.write("From server: " + msg);
}
I am sending input from a client class, but I can't figure out where I am wrong, since the server never receives the message.
Here is my entire sever class:
import java.io.*;
import java.net.*;
public class Server {
private BufferedReader reader;
private PrintWriter writer;
private int port;
public Server(int port)
{
this.port = port;
}
private String getSeverAddress() {
String host = null;
try {
InetAddress adr = InetAddress.getLocalHost();
host = adr.getHostAddress();
} catch (UnknownHostException e) {
e.printStackTrace();
}
return host;
}
public void startServer() {
print("Contact this sever on address: " + getSeverAddress() + " port: " + port);
ServerSocket ss = null;
Socket socket = null;
try {
ss = new ServerSocket(port);
socket = ss.accept();
reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
writer = new PrintWriter(socket.getOutputStream(), true);
String msg = null;
while (( msg = reader.readLine()) != null) {
writer.write("From server: " + msg);
print(msg);
if(msg.toLowerCase().equals("Bye")) {
print("Client left");
break;
}
}
ss.close();
socket.close();
reader.close();
writer.close();
} catch(SocketException e) {
e.printStackTrace();
} catch (IOException i ) {
i.printStackTrace();
return;
}
}
private void print(String msg) {
System.out.println(msg);
}
public static void main(String[] args) {
Server server = new Server(1111);
server.startServer();
}
}
And here is the client class:
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Scanner;
public class Client {
private Socket client;
private BufferedReader reader;
private PrintWriter writer;
public Client(Socket socket)
{
client = socket;
try{
reader = new BufferedReader(new InputStreamReader(client.getInputStream()));
writer = new PrintWriter(client.getOutputStream(), true);
} catch (Exception e) {
e.printStackTrace();
}
}
public void writeToServer() {
print("Write message to server");
String msg = null;
try {
while((msg = reader.readLine()) != null) {
writer.write("From client: " + msg);
print(msg);
if(msg.toLowerCase().equals("quit")) {
break;
}
}
reader.close();
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
private void print(String msg) {
System.out.println(msg);
}
public static void main(String[] args) {
Socket socket = null;
try {
socket = new Socket("localhost", 1111);
} catch (Exception e) {
e.printStackTrace();
}
Client client = new Client(socket);
client.writeToServer();
}
}
Your mistake is server and client both sending/receiving messages background without printing anything. Like when you send message from client, Server received it and again write to the client and it become infinite loop.
Following things are wrong:
Server.java
try {
while (( msg = reader.readLine()) != null) {
print(msg);
if(msg.toLowerCase().equals("bye")) {
print("Client left");
break;
}
writer.write("From server: " + msg);
}
Should be the last statement of loop writer.write("From client: " + msg); and if(msg.toLowerCase().equals("Bye")) should bye
Client.java
try {
while((msg = reader.readLine()) != null) {
print(msg);
if(msg.toLowerCase().equals("quit")) {
break;
}
writer.write("From client: " + msg);
}
It should be last in loop writer.write("From client: " + msg);
You're reading lines but you aren't sending lines. You need to send a line terminator.

Categories