Is it possible to know how many clients are connected to ServerSocket?

6

How do I see how many clients are connected in my ServerSocket in java?

    
asked by anonymous 28.12.2014 / 16:47

1 answer

5

I do not know if there is any ID per user that helps identify who the clients are, but in the case of TCP servers, what can always be counted is the connection made by a client and from this connection we can get data and try to create an identity to be able to distinguish.

Counting connections

Within the while loop we use ServerSocket.accept(); to determine when the connection was made, so the account would look something like:

int i = 0;
ServerSocket ss = new ServerSocket(8088);
while (true) {
    Socket socket = ss.accept();
    i += 1;
    ...
}

Because the loop is "infinite", you can use a Thread to show i using System.out for example. If you are looking to count connections made right now, this should help you.

Counting remote addresses

But this only counts the connections made. Usually the client connects, receives the data, and disconnects. If it is a web page, then each image, js, css, within the page can generate a new connection, ie a client generates multiple connections.

  

Note: Web browsers typically use the Connection: keep-alive statement in the request headers, which should do so indicating that the browser should keep the connection open for the elements on the page, but this connection is not always going to stay open.

We have been able to count the number of connections made, now what we need is to give an identity to each client.

An example of identifying the client is to use socket.getRemoteSocketAddress(); (which may not be 100% guaranteed, but this is another story) combined with a list. The code should look something like this:

List<String> clientes = new ArrayList<String>();
...
ServerSocket ss = new ServerSocket(8088);
while (true) {
    Socket socket = ss.accept();
    String addr = ss.getRemoteSocketAddress().toString();
    if (!clientes.contains(addr)) {
        clientes.add(addr);
    }
}

In this way we will save all connected addresses (remember in these cases it is always necessary to use a Thread, or your socket is on a separate Thread) and to count would just use clientes.size() .

Real-time counter

The example I passed counts the connections, but does not clear the list, so that the number will never decrease, it will only increase. In this case, if what you need is a "realtime" counter, you can use HashMap to create a list where expires items (similar to what online counters do).

Create a HashMap like this:

Map<String, Date> clientes = new HashMap<String, Date>();
  • String will have the "address".
  • Date will be used to check if the data should expire.

The "Server" should look like this:

Map<String, Date> clientes = new HashMap<String, Date>();

ServerSocket ss = new ServerSocket(8088);
while (true) {
    Socket socket = ss.accept();
    String addr = ss.getRemoteSocketAddress().toString();

    // Atualiza o horário de um endereço existente ou adiciona um novo endereço.
    clientes.put(addr, new Date());
}

And in another method (which must have access to clientes variable), you must create a check to detect if the client time has expired (does not have to be a long time, 30 seconds is more than good ).

First we create a HashMap to relist:

Map<String, Date> relista;

Then we create a loop to check what is still within the timeout:

relista = new HashMap<String, Date>(); // Limpa relista para aproveitá-la novamente.

Date agora = new Date();
agora.add(Calendar.SECOND, -30); // 30 segundos mencionado anteriormente, edite conforme necessidade.

for (String key : clientes.keySet()) {
    Date timer = clientes.get(key);
    if (!agora.after(timer)) {
       // Se o item ainda está dentro dos 30 segundos então "mantém na lista".
       relista.put(key, timer);
    }
}

clientes = relista; // Atualiza a lista de clientes conectados.

Sessions

The last example I cited is just a simple way to understand how to list, but the use of getRemoteSocketAddress is not accurate because IP can change (both on a private network and on the internet). The most guaranteed way would be to use session, however you will need external libraries to make the job easier (it is possible to do without, but it requires a lot of time to develop something). There are libraries that can help you, such as javax.servlet.http.HttpSession (of course if it is used for HTTP).

    
29.12.2014 / 14:26