7

Is there a way to use the facilities provided by Spring to have a webSocket connection without using SockJS and STOMP? I need to implement a proprietary webSocket protocol so I cannot use either one at the moment.

I have implemented/hacked together the solution from the following answer, but it requires me to reimplement things that I feel I should not be worrying about.

I guess my question boils down to: is there a way for me to use the nice features of 2.(below), specifically the MessageBroker, without using STOMP?

A bit of background:

I need to do the following:

  • Be able to inject a reference to my persistence provider in each instance of the websocket handler
  • Handle each webSocket session in a separate instance of my handler object
  • Re-transmit the messages I receive on one endpoint to multiple clients on a different endpoint.
  • Implement my own protocol over a standard Text WebSocket connection.

What I have tried so far is:

  1. Use javax.websocket, where I can handle each request on a separate instance. However, I need to iterate over the open sessions and retransmit on the ones connected to the correct endpoint. Also, I can't use Spring to inject my persistence provider. This was what I was using so far and it seems too hacky.

I.e. (pseudo-code)

@ServerEndpoint("/trade/{id}")
public String handleMessage(@PathParam(id) String id, webSocketSession session){
 if(id.equalsIgnoreCase("foo"){
      for(Session s: session.getOpenSessions(){
      //do things}
  } else if(id.equalsIgnoreCase("bar")){
      //do other things
  }
 }
}
  1. Use the Spring websocket implementation with @MessageMapping("/trade") and @SendTo("/queue/position-updates"). This requires me to use, as a minimum, STOMP. This would mean breaking other applications in the process, which I can't do at the moment. Also, there is the question of the proprietary protocol I need to implement.

I.e. (pseudo-code)

@MessageMapping("/trade/{id}")
@SendTo("/trades/all")
public Greeting greeting(String message){
    //do things, return message
}
  1. A the moment, I am using the Spring websocket implementation by implementing the WebSocketConfigurer class and registering endpoints. This allows me to have each session in a separate handler class and inject the persistence provider. However, I can't seem to get some of the nice things about Spring working:
    • I cannot get the parameter {id} from the registry.addHandler(WebsocketHandlerPool(), "/trade/{id}") into the WebsocketHandlerPool(), so I have to parse the path when I create each individual WebsocketHandler. Ideally, I would like to not have to do this.
    • I have to implement my own message broker if I don't want to iterate over all the sessions inside the code of the websocket message handler. There is no support (as far as I can tell) for @MessageMapping and @SendTo.

I.e. (pseudo-code for handler:)

@Override
public void afterConnectionEstablished(WebSocketSession s){
    //parses the String of the Path URL and sets it as a field
    idFromSessionPath = getIdFromSessionPath(s);
}
@Override
public String handleTextMessage(WebSocketSession session, TextMessage message
{
    If(idFromSessionPath.equals("foo"){
     //do things
    } else {
     //do other things
    }
}

(pseudo-code for config)

@Override
public void registerWebSocketHandlers(WebSocketHandlerRegistry  registry){
    registry.addHandler(threadPool(), "/trade/{id}");
}

@Bean
public WebSocketHandler threadPool(){
    return new PerConnectionWebSocketHandler(TradeStreamingHandler.class);

}
Community
  • 1
  • 1
Kaloyan Pashov
  • 155
  • 2
  • 11
  • I am currently in a very similar situation as you were when you wrote this, and I am sad to see that there has not been a reply. Were you able to come up with a solution or did you have what you showed in your pseudo-code for handler? I am definitely interested in how you solved this as I'm currently doing what you're showing in your pseudo-code handler. – Flippi Sep 23 '19 at 15:33

0 Answers0