简体   繁体   中英

Broadcasting websocket message from other thread in jetty

I'm creating a chat-like service.

When user opens the page, he connects to websocket endpoint and waits for some incoming messages.

On the server side, Java application using jetty is waiting for connections. Whenever the user sends a message, it broadcasts it to all clients. There are also some system messages that are sent from time to time from separate thread.

The problem is I'm really concerned about thread safety of this solution. From what I understand, jetty uses thread pool with x worker threads, so multiple connections may be handled by multiple threads. My system message service is also going to run on another thread, even outside jetty thread pool.

The broadcast function is most likely going to look like this (generic function names):

for(Connection connection : server.getWebSocketConnections())
    connection.sendMessage(message);

Depending on which thread calls it:

  1. collection returned by the getWebSocketConnections may be changed during iteration.
  2. connection may be already closed / deleted / disposed when doing sendMessage
  3. there might be some internal buffer race condition etc

So the question is:

How to safely broadcast a message to all open websocket connections from external thread using jetty?

Funny thing, i've been working on the same thing the past weeks. As you said, you need the broadcast to be thread safe. This is how i do it:

public void broadcast(String message, AnnotatedSocket excludedClient) {
    logger.debug("Sending to all clients:{} ", message);
    synchronized (clients) { 
        for (AnnotatedSocket as : clients) {
            if (!as.equals(excludedClient) && as.getSession().isOpen()) {
                try {
                    as.getSession().getRemote().sendStringByFuture(message);
                } catch (Exception e) {
                    logger.error("Error{} when broadcasting to {} {} ",e,as.getId(),as.getAddress());                                       
                }
            }
        }
    }
}

Clients is a synchronized list owned by the server, and is used by all sockets whenever a broadcast is needed, but it is kept thread safe, from what I understood. It does work, however there might be a better way, as I am quite new to this. I also implemented multicast if that does interest you. If you need any more information on how i proceeded, let me know.

Cheers.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM