Custom Text and Binary Payloads using WebSocket (TOTD #186)


TOTD #185 explained how to process text and binary payloads in a WebSocket endpoint. In summary, a text payload may be received as

public void receiveTextMessage(String message) {
    . . .
}

And binary payload may be received as:

public void recieveBinaryMessage(ByteBuffer message) {
    . . .
}

As you realize, both of these methods receive the text and binary data in raw format. However you may like to receive and send the data using a POJO. This marshaling and unmarshaling can be done in the method implementation but JSR 356 API provides a cleaner way. For encoding and decoding text payload into POJO, Decoder.Text (for inbound payload) and Encoder.Text (for outbound payload) interfaces need to be implemented.

A sample implementation below shows how text payload consisting of JSON structures can be encoded and decoded.
public class MyMessage implements Decoder.Text<MyMessage>, Encoder.Text<MyMessage> {
    private JsonObject jsonObject;

    @Override
    public MyMessage decode(String string) throws DecodeException {
        this.jsonObject = new JsonReader(new StringReader(string)).readObject();      
        return this;
    }

    @Override
    public boolean willDecode(String string) {
        return true;
    }

    @Override
    public String encode(MyMessage myMessage) throws EncodeException {
        return myMessage.jsonObject.toString();
    }

public JsonObject getObject() { return jsonObject; }
}
In this implementation, the decode method decodes incoming text payload to MyMessage, the encode method encodes MyMessage for the outgoing text payload, and the willDecode method returns true or false if the message can be decoded.

The encoder and decoder implementation classes need to be specified in the WebSocket endpoint as:
@WebSocketEndpoint(value="/endpoint",
encoders={MyMessage.class},
decoders={MyMessage.class}) public class MyEndpoint { public MyMessage receiveMessage(MyMessage message) { . . . } }
Notice the updated method signature where the application is working with MyMessage instead of the raw string.

Note that the encoder and decoder implementations just illustrate the point and provide no validation or exception handling. Similarly Encooder.Binary and Decoder.Binary interfaces need to be implemented for encoding and decoding binary payload.

Here are some references for you:
Subsequent blogs will discuss the following topics (not necessary in that order) ...
  • Error handling
  • Interface-driven WebSocket endpoint
  • Java client API
  • Client and Server configuration
  • Security
  • Subprotocols
  • Extensions
  • Other topics from the API
Comments:

Glassfish 4 Nightly b65 seems to ignore the ws-protocol. It deploys, but a call to the ws://..../websocket comes back with a 404. It feels like GF doesn't do the protocol upgrade although the WebSocket-checkbox is checked in the http-listener-panel.

I have the feeling that the Tyrus-part just ain't starting correctly. I've placed a breakpoint on the @WebSocketOpen-method and it is not being executed at all. Do you have a tip?

thanks
Jan

Posted by Jan on December 03, 2012 at 05:21 AM PST #

I'm using 64 and that is working fine. In particular, the app described at https://blogs.oracle.com/arungupta/entry/collaborative_whiteboard_using_websocket_in is built using 64.

Can you try 64 first ? If it works there then file a regression at http://java.net/jira/secure/CreateIssue.jspa?pid=10231&issuetype=1

Posted by Arun Gupta on December 03, 2012 at 05:29 AM PST #

Yes, the nightly (!) 65 build seems to be corrupt. It work in promoted build 64.

Could you also blog about the threading-model behind WebSockets in Glassfish? How many request-threads do you need etc? What about scaling in the cloud? Can you send messages from more than one node in a cluster, or how does that function? (scenario: my websocket is in server A but server B has a message for me, but I am not in his peerslist)

Thanks,
Jan

Posted by Jan on December 03, 2012 at 06:52 AM PST #

Jan, definitely a bug in that case. Can you file an issue with P1 ? This seems to be a regression.

Thanks for suggestions on future blogs, will add them to my TODO list.

Posted by Arun Gupta on December 03, 2012 at 01:10 PM PST #

Post a Comment:
Comments are closed for this entry.
About

profile image
Arun Gupta is a technology enthusiast, a passionate runner, author, and a community guy who works for Oracle Corp.


Java EE 7 Samples

Stay Connected

Search

Archives
« April 2014
SunMonTueWedThuFriSat
  
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
   
       
Today