I have 2 programs: a client and a server.
The server creates a ServerSocket and the client connects using:
address = InetAddress.getByName(host);
conn = new Socket(address, port);
this works, but here is the problem: void mousePressed() { gets called once the mouse is clicked, executing this: (client side)
void mousePressed() {
try {
BufferedOutputStream os = new BufferedOutputStream(conn.getOutputStream());
OutputStreamWriter osw = new OutputStreamWriter(os, "US-ASCII");
osw.write("123");
osw.flush();
} catch (Exception e) {
e.printStackTrace();
}
}
the server should receive the input using:
BufferedReader reader = new BufferedReader(
new InputStreamReader(new BufferedInputStream(conn.getInputStream())));
StringBuilder result = new StringBuilder();
for (String line = null; (line = reader.readLine()) != null;) {
result.append(line);
}
reader.close();
println(result.toString());
The server only receives the input after the socket has been closed with: conn.close(); on the client side or quitting the client. As i want to be able to click the mouse multiple times, i can't close the socket.
What can i do to send input without closing the socket?
Edit: connection code:
Server:
// init
ServerSocket socket1;
int main_port = 5204;
// in main
try {
socket1 = new ServerSocket(main_port);
Socket conn = socket1.accept();
} catch (Exception e) {
e.printStackTrace();
}
Client:
// init
String host = "localhost";
int port = 5204;
Socket conn;
InetAddress address;
// in main
try {
address = InetAddress.getByName(host);
conn = new Socket(address, port);
} catch (Exception e) {
e.printStackTrace();
}
My solution (based on other answers and comments):
1) Changing osw.write("123"); to osw.write("123\n"); in the client.
2) Replacing
BufferedReader reader = new BufferedReader(new InputStreamReader(new
BufferedInputStream(thread_cnn.getInputStream())));
StringBuilder result = new StringBuilder();
for (String line = null; (line = reader.readLine()) != null;) {
result.append(line);
}
println(result);
reader.close();
with
BufferedReader reader = new BufferedReader(new InputStreamReader(new BufferedInputStream(conn.getInputStream())));
String result = reader.readLine().toString();
println(result);
reader = null;
result = null;
on the server.
You are writing an incomplete line, and trying to read complete lines. Terminate the text you send with a line break so it can be read when it arrives.
Also, do not catch and ignore exceptions. If something goes wrong you will want to know about it.
try {
BufferedOutputStream os = new BufferedOutputStream(conn.getOutputStream());
OutputStreamWriter osw = new OutputStreamWriter(os, "US-ASCII");
osw.write("123\n");
osw.flush();
} catch (Exception e) {
e.printStackTrace();
}
Related
My server is not sending a response with BufferedWriter out to the client. It seems as if the code stops at int amountOfNumbersToBeGenerated = Integer.parseInt(bufferedReader.readLine()); I believe the bufferedreader.readline() call on the client side is causing and issue and blocking the connection in some sense.
import java.io.*;
import java.net.Socket;
import java.util.ArrayList;
public class ThreadedConnection implements Runnable {
private Socket connection;
private InputStream in;
private OutputStream out;
public ThreadedConnection(Socket connection) {
this.connection = connection;
try {
this.in = this.connection.getInputStream();
this.out = this.connection.getOutputStream();
} catch (IOException e) {
e.printStackTrace();
}
}
#Override
public void run() {
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(in));
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(out));
try {
String lotteryType = bufferedReader.readLine(); //reads first line of input stream
int amountOfNumbersToBeGenerated = Integer.parseInt(bufferedReader.readLine());
System.out.println("3"+amountOfNumbersToBeGenerated);
switch (lotteryType) {
case "LuckyForLife":
generateLotteryNumbers(amountOfNumbersToBeGenerated, 48, 18, bufferedWriter);
break;
case "MegaMillions":
generateLotteryNumbers(amountOfNumbersToBeGenerated, 70, 25, bufferedWriter);
break;
case "PowerBall":
generateLotteryNumbers(amountOfNumbersToBeGenerated, 69, 26, bufferedWriter);
break;
default:
break;
}
bufferedWriter.flush();
} catch (IOException e) {
e.printStackTrace();
}finally {
try {
connection.close();
bufferedReader.close();
bufferedWriter.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public void generateLotteryNumbers(int amountOfNumbersToBeGenerated, int upperLimitOfGeneratedNumbers, int upperLimitOfExtraNumber, BufferedWriter bufferedWriter){
RandomNumberGenerator randomNumbers = new RandomNumberGenerator(amountOfNumbersToBeGenerated,upperLimitOfGeneratedNumbers);
RandomNumberGenerator extraNumber = new RandomNumberGenerator(1,upperLimitOfExtraNumber);
ArrayList randomNumbersArrayList = randomNumbers.NumberGenerator();
ArrayList extraNumberArrayList = extraNumber.NumberGenerator();
String randomNumbersString = randomNumbersArrayList.toString();
randomNumbersString = randomNumbersString.substring(1, randomNumbersString.length()-1);
String extraNumberString = extraNumberArrayList.toString();
extraNumberString = extraNumberString.substring(1, extraNumberString.length()-1);
try {
bufferedWriter.write(randomNumbersString);
bufferedWriter.newLine();
bufferedWriter.write(extraNumberString);
bufferedWriter.newLine();
bufferedWriter.flush();
} catch (IOException e) {
e.printStackTrace();
}
// System.out.println(randomNumbersString);
// System.out.println(extraNumberString);
}
}
Here is the code for the client side. I think the first String gerneretedNumber = bufferedReader.readLine(); is causing the issue. Almost as if it is called to read when there is nothing being written out from the server and then messing with the server side read. If I block both of the readline() calls the code on the server then works and I can get something to print out on console.
static void runClient(){
OutputStream outputStream;
InputStream inputStream;
Socket client;
BufferedWriter bufferedWriter;
BufferedReader bufferedReader;
try {
System.out.println("Creating client socket ");
client = new Socket("127.0.0.1", 5000);
outputStream = client.getOutputStream();
inputStream = client.getInputStream();
bufferedWriter = new BufferedWriter(new
OutputStreamWriter(outputStream));
//bufferedReader = new BufferedReader(new
InputStreamReader(System.in));
bufferedReader = new BufferedReader(new
InputStreamReader(inputStream));
bufferedWriter.write("LuckyForLife");
bufferedWriter.newLine();
bufferedWriter.write("5");
bufferedWriter.flush();
String generetedNumber = bufferedReader.readLine();
String extraNumber = bufferedReader.readLine();
System.out.println(gerneretedNumber);
System.out.println(extraNumber);
System.out.println("Guess its null");
bufferedReader.close();
bufferedWriter.close();
client.close();
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
If anymore information is needed I am happy to post it.
your client never sends the 2nd newline.
Given your protocol, client doesn't half close (output close) so the server cannot either detect end of stream.
BTW, try to close streams (tcp FIN) before close socket (tcp RST); it's more "ethical" ! Kidding aside, the tcp rst is a kill, and pending bytes might not be flushed out (although you have plenty of flushes here, it's just good practice).
I'm trying to make a basic client <-> server connection in Java. When trying to write to the server, the client sends the details correctly, and the server stalls on reading it until the client output stream is closed. Though, once the output stream is closed it apparently closes the socket, and due to that the server can't reply to the client. Here's the main snippet of code that handles this interaction.
Client:
private void sendCmd(String cmd) {
String infoToSend = cmd;
try {
socket = new Socket(hostname, port);
System.out.println("Trying to send: " + com.sun.org.apache.xml.internal.security.utils.Base64.encode(infoToSend.getBytes()));
out = new DataOutputStream(socket.getOutputStream());
out.writeBytes(com.sun.org.apache.xml.internal.security.utils.Base64.encode(infoToSend.getBytes()));
out.flush();
System.out.println("Socket is flushed");
System.out.println("Waiting for Data");
InputStream is = socket.getInputStream();
System.out.println("Trying to get data");
BufferedReader input = new BufferedReader(
new InputStreamReader(is)
);
String line;
while((line = input.readLine()) != null) {
System.out.println(line);
}
socket.close();
} catch (IOException e) { e.printStackTrace(); }
}
Server:
public void run() {
System.out.println("Got Connection");
try {
BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
out = new DataOutputStream(socket.getOutputStream());
String response;
System.out.println("Response:");
String decode = "";
while ((response = in.readLine()) != null) {
try {
decode = new String(Base64.decode(response));
} catch (Base64DecodingException e) {
e.printStackTrace();
}
}
System.out.println("Decoded: " + decode);
out.writeBytes("We got your message!");
out.flush();
out.close();
} catch (IOException e) { System.out.println("Fail"); e.printStackTrace(); }
Would anyone be able to guide me on how to fix this error. Sorry if it's super easy and I'm just unable to see it.
Sending
socket.shutdownOutput();
solved the issue.
I'm delving into sockets for the first time.
The point of the project is for the client to be able to get access to a contact list (CSV) in the server by writing "getall" and exit the program through just that command ("Exit").
The problem is that the client can only write the command and receive the list once and then the server doesn't respond to the client's input anymore.
Here is the socket code for the server and client respectively:
Server:
public class CatalogueServer extends CatalogueLoader {
ServerSocket serverSocket;
ArrayList<CatalogueEntry> catalogue;
public void startServer(int port, String catalogueFile) {
catalogue = loadLocalCatalogue(catalogueFile);
try {
serverSocket = new ServerSocket(port);
while (true) {
Socket clientSocket = serverSocket.accept();
new Thread(
new Runnable() {
public void run() {
try {
InputStream inputStream = clientSocket.getInputStream();
InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "UTF-8");
BufferedReader BR = new BufferedReader(inputStreamReader);
OutputStream outputStream = clientSocket.getOutputStream();
PrintWriter PW = new PrintWriter(outputStream);
String clientInput;
while ((clientInput = BR.readLine()) != null) {
System.out.println(clientInput);
if (clientInput.equals("getall")) {
System.out.println(printCatalogue(catalogue));
PW.println(printCatalogue(catalogue));
PW.flush();
break;
} else if (clientInput.equals("exit")) {
clientSocket.close();
BR.close();
PW.close();
break;
} else {
PW.flush();
break;
}
}
PW.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
).start();
}
} catch (Exception i) {
i.printStackTrace();
}
}
}
Client:
public class TestClient {
public static void main(String[] args) {
try {
Socket socket = new Socket("localhost", 5253);
OutputStream outputStream = socket.getOutputStream();
InputStream inputStream = socket.getInputStream();
InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
BufferedReader BR = new BufferedReader(inputStreamReader);
while (true) {
String clientInput;
String serverFeedback;
PrintWriter PW = new PrintWriter(outputStream);
Scanner inputScan = new Scanner(System.in, "UTF-8");
clientInput = inputScan.nextLine();
PW.println(clientInput);
PW.flush();
while ((serverFeedback = BR.readLine()) != null) {
System.out.println(serverFeedback);
}
if (clientInput.equals("exit")) {
PW.close();
socket.close();
break;
}
PW.close();
}
}
catch (IOException e){
e.printStackTrace();
}
}
}
I have tried alternating the position and renewal of the readers and writers. But I'm uncertain of where exactly the problem starts.
When you do
while ((serverFeedback = BR.readLine()) != null) {
System.out.println(serverFeedback);
}
You are reading until you reach the end of the stream, i.e. until there is nothing left. As such there is nothing after this.
If you want to reuse the connection, you have to write the code which doesn't use this pattern and only reads until it should stop reading.
I am executing shell commands from my Android APP. I am able to execute the command but unable to read the response from Server.
My code is as follows :
public String executeThroughSocket(int portNo, String portAddress, String command) throws IOException {
StringBuilder responseString = new StringBuilder();
PrintWriter writer = null;
BufferedReader bufferedReader = null;
Socket clientSocket = null;
try {
clientSocket = new Socket(portAddress, portNo);
if (!clientSocket.isConnected())
throw new SocketException("Could not connect to Socket");
clientSocket.setKeepAlive(true);
writer = new PrintWriter(clientSocket.getOutputStream(), true);
writer.println(command);
writer.flush();
bufferedReader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
String str;
while ((str = bufferedReader.readLine()) != null) {
responseString.append(str);
}
} finally {
if (writer != null)
writer.close();
if (bufferedReader != null)
bufferedReader.close();
if (clientSocket != null)
clientSocket.close();
}
return responseString.toString();
}
There is nothing wrong with my code. It was the server that was not sending any response.
You have to set timeout for socket
clientSocket .setSoTimeout(5000); // milisekundy
I would like to create a Java server socket application that receives a TCP packet and reads the content of it. Based on the contents of the packet it will perform several actions. I managed to get to the point where it reads some content and prints a string System.out.println(sb.toString());
But (a) not all the content is printed and (b) I am not sure how to process the content as they arrive in network order. An example would be to receive an HTTP packet and from the header to report the "Content-Length" or the "User-Agent". Any example would be appreciated.
public static void main(String[ ] args){
PrintWriter out = null;
BufferedReader in = null;
int bufferSize = 0;
try{
String message = args[0];
int count = 0;
ServerSocket connectionSocket = null;
try {
connectionSocket = new ServerSocket(4444);
System.out.println("Server started");
} catch (IOException e) {
System.err.println("Could not listen on port: 4444.");
System.exit(1);
}
Socket clientSocket = null;
try {
while(true){
count++;
clientSocket = connectionSocket.accept();
System.out.println("TCP packet received… " + count);
InputStream is = clientSocket.getInputStream();
out = new PrintWriter(clientSocket.getOutputStream());
in = new BufferedReader(new InputStreamReader(is));
StringBuilder sb = new StringBuilder();
String line = null;
while ((line = in.readLine()) != null) {
sb.append(line + "\n");
}
System.out.println(sb.toString());
clientSocket.close();
}
} catch (IOException e) {
System.err.println("Accept failed.");
System.exit(1);
}
}
catch(Exception e){
e.printStackTrace();
}
}