The implementation is relatively straightforward, but bear in mind all I am going to say applies to Jetty only. We start with adding custom event listeners and implement the interface WebSocket.OnTextMessage:
..
import org.eclipse.jetty.websocket.WebSocket.OnTextMessage;
import org.eclipse.jetty.websocket.WebSocket.Connection;
import java.util.Set;
..
private Connection connection;
private Set<ChatWebSocket> users;
public class ChatWebSocket implements OnTextMessage {
..
public void onClose(int closeCode, String message) {
users.remove(this);
}
public void onOpen(Connection connection) {
this.connection = connection;
users.add(this);
}
public void onMessage(String data) {
for (ChatWebSocket user : users) {
try {
user.connection.sendMessage(data);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
..
}
There is not much to talk about. We merely register new subscriptions to the channel and broadcast incoming messages to all connected users. We certainly could make our solution highly sophisticated by interpreting incoming data and reacting upon their significance. But let's keep it simple for a start.
Now, when we have the customized event listeners in place we we need a servlet capable of upgrading to WebSocket:
..
import org.eclipse.jetty.websocket.WebSocket;
import org.eclipse.jetty.websocket.WebSocketServlet;
import java.util.concurrent.CopyOnWriteArraySet;
..
public class WebSocketChatServlet extends WebSocketServlet {
private Set<ChatWebSocket> users =
new CopyOnWriteArraySet<ChatWebSocket>();
public WebSocket doWebSocketConnect(
HttpServletRequest request, String arg) {
return new ChatWebSocket(users);
}
}
Finally, we configure the servlet in web.xml, no surprises here:
<servlet>
<servlet-name>WebSocketChat</servlet-name>
<servlet-class>
org.zezutom.wschat.WebSocketChatServlet
</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>WebSocketChat</servlet-name>
<url-pattern>/talk/*</url-pattern>
</servlet-mapping>
That's it for the server-side. Our client code centers around the HTML5 WebSocket object.
// JQuery + custom javascript, unimportant here..
// HTML5 WebSocket: initialization and custom handlers
// as a front-end counterpart to our server-side code
var _ws = new WebSocket('ws://localhost:8080/wschat/talk');
_ws.onopen = function(event) {
// show that a new user joined the chatroom
// and request a connection
};
_ws.onclose = function(event) {
// notify that the user has left
// and release the connection
};
_ws.onmessage = function(event) {
// extract event data and display them as a new message
// do all the fancy stuff (colors, highlighting,
// smooth scrolling etc.)
};
To conclude, I found it unusually easy to get the application's bare bones up and running and had great fun when testing my very own chat.
On the down side, the new technology has raised several concerns. One of the most discussed area is, as usual, security. WebSocket does not use HTTP headers which impacts firewalls and virus scanners relying on them. Many exciting articles and discussions can be searched out, above all: