Socket server that waits for message from client to read
Asked Answered
G

3

7

I have the following socket server in java,

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 MiddleSocket {
    private ServerSocket middleman;
    private int port = 1027;
    private Socket client;


    protected void createSocketServer()
    {
        try
        {
            middleman = new ServerSocket(port);
            client = middleman.accept();
            middleman.close();
            PrintWriter out = new PrintWriter(client.getOutputStream(),true);
            BufferedReader in = new BufferedReader(new InputStreamReader(client.getInputStream()));
            BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
            while(true)
            {
                System.out.println("echo: " + in.readLine());
                out.println("test");
            }
        }
        catch(IOException e)
        {
            System.out.println(e);
        }
    }

}

It works correctly in how it reads from the client and everything. However, I want the socket server to only try and read when there is a message from the client since in the loop it keeps reading even when no messages from the client are received this outputs a bunch of

echo: null

Is there some mechanism short of a wait() to have the while loop to know to just sit and wait and then fire when a message is sent from the client to read that message and once that message is read and a reply is sent, to then just sit idle until the next message from the client is received?

Gintz answered 20/10, 2014 at 16:11 Comment(0)
T
5

You can simply do something like as follows:

String line;
while ((line = in.readLine()) != null) {
   \\Do stuff
}

This should have the expected behaviour.

Edit:

here's a full example of what I was talking about in the comments using your code:

package javaapplication12;

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 SocketExample {
    private ServerSocket middleman;
    private int port = 8080;
    private Socket client;


    protected void createSocketServer()
    {
        try
        {
            while (true){
                middleman = new ServerSocket(port);
                client = middleman.accept();
                middleman.close();
                PrintWriter out = new PrintWriter(client.getOutputStream(),true);
                BufferedReader in = new BufferedReader(new InputStreamReader(client.getInputStream()));
                BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
                String line;
                while((line = in.readLine()) != null)
                {
                    System.out.println("echo: " + line);
                    out.println("test");
                }
            }
        }
        catch(IOException e)
        {
            System.out.println(e);
        }
    }

    public static void main(String[] args){
        SocketExample test = new SocketExample();
        test.createSocketServer();
    }
}
Ting answered 20/10, 2014 at 16:18 Comment(10)
However I want the loop to not exit since I want the Socket server running all the time.Gintz
Then you should loop on the .accept command, which should then handle whatever input is received from the connecting client, and then closes the connection, and waits for a new one. I'll modify my answer with an example.Ting
edited my answer to reflect what I mentioned above. Of course keep in mind, this can only handle a single connection at a time, but it's a functional example. Notice that the while(true) loops around a different portion of the code, which allows it to accept an infinite number of connections, but has a finite amount of time spent handling each connection, which is what you want.Ting
so what happens if i want n connections at a time? will it buffer the other messages then and send those after the last message is recieved from the previous client?Gintz
for n connections, you will need n threads, which will then require a more complicated version of this program. As it stands with a single-threaded socket server, any subsequent connections while it is processing information from one connection will simply get rejected by your serverTing
gotcha, so make a threaded version of this to handle multiple connections basically?Gintz
pretty much! essentially everything inside of the while(true) loop (not the loop itself) would be the 'content' of the thread, and you would have some other class with the 'while(true)' loop which has the .accept() method and spawns off a thread to handle the connection, then goes right back to listening for new connections. Check out this link: baptiste-wicht.com/posts/2010/09/…Ting
It does make a difference. The ready() test must be removed, otherwise the loop exits as soon as the socket receive buffer is empty. There are few if any correct uses of this facility.Encyclopedic
fair enough, I took it out.Ting
@BoJackHorseman no particular reason, must just have been a copy/paste error, I'll nuke the last oneTing
H
2

You can use InputStream.read(), or InputStream.read(byte[]). Both will block

Here is an example

Hereto answered 20/10, 2014 at 16:18 Comment(0)
E
1

I want the socket server to only try and read when there is a message from the client since in the loop it keeps reading even when no messages from the client are received this outputs a bunch of

echo: null

That's because you're ignoring end of stream, which is what the null means. It doesn't mean there are no messages from the client at all. It means the peer has closed the connection.

Encyclopedic answered 21/10, 2014 at 2:49 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.