Java WebSocket InstancesWebsocket 2015-04-11 14:11:54 release
Collection6 Collection
Introduced
Many web sites are now polling (polling) for instant messaging. Polling is at a specific time interval (such as every 1 seconds), the browser sends an HTTP request to the server, and the server returns the latest data to the client's browser. This traditional HTTP request pattern has obvious drawbacks – the browser needs to constantly make requests to the server, but the header of the HTTP request is very long, and the data contained in it may be a small value, which consumes a lot of bandwidth.
And the most new technology to do polling effect is comet– using AJAX. However, although this technology can reach full-duplex communication, it still needs to make a request.
In the WebSocket API, browsers and servers only need to do a handshake, and then a fast channel is formed between the browser and the server. The data can be transmitted to each other directly between the two.
Depend on:
Tomcat 7 or J2ee7
<dependency><groupid>org.apache.tomcat</groupid><artifactid>tomcat-websocket-api</ artifactid><version>7.0.47</version><scope>provided</scope></dependency>< Dependency><groupid>javax</groupid><artifactid>javaee-api</artifactid><version >7.0</version><scope>provided</scope></dependency>
Note: The previous industry did not have a unified standard, each server has its own implementation, now J2EE7 JSR356 has defined a unified standard, please try to use to support the latest common standards of the server.
See: http://www.oracle.com/technetwork/articles/java/jsr356-1937161.html
http://jinnianshilongnian.iteye.com/blog/1909962
I'm using tomcat 7.0.57 + Java7.
Must be Tomcat 7.0.47 or more
See: http://www.iteye.com/news/28414
PS: We were the first to use the Tomcat 7 to bring the implementation, and later to upgrade Tomcat 8, the results of the original implementation is not supported in Tomcat 8, we had to switch to support WebSocket 1.0 version of Tomcat.
The mainstream Java Web server has a version that supports the JSR365 standard, please Google yourself.
With Nginx to do reverse proxy needs attention, socket request needs to do special configuration, remember!
The way Tomcat is handled is recommended to change to NIO, while modifying the number of connections to the appropriate parameters, please google! yourself
Service side
The server does not need to make additional configuration in Web. XML, and Tomcat can connect directly after booting.
import com.dooioo.websocket.utils.sessionutils;import org.apache.commons.logging.log;import org.apache.commons.logging.logfactory;import javax.websocket.*;import javax.websocket.server.pathparam;import javax.websocket.server.serverendpoint;/** * Function Description: WebSocket processing class, use J2EE7 standard * avoid adding business process code directly to the connection processing class * liuxing (2014-11-14&NBSP;04:20) *///relationid and Usercode are my business identity parameters, websocket.ws is the path to the connection and can be defined @serverendpoint ("/websocket.ws/{relationid}/{ Usercode} ") public class websocketendpoint { private static log log = logfactory.getlog (websocketendpoint.class);/** * trigger * @param when open connection relationid * @param userCode * @param session*/@OnOpen public void onopen (@ Pathparam ("Relationid") String relationId, @PathParam ("Usercode") int userCode, session session) { log.info ("Websocket start coNnecting: "+ sessionutils.getkey (Relationid, usercode)); sessionutils.put (relationId, usercode, session);} /** * Trigger * @param relationId * @param usercode * @ When a client message is received param message * @return */@OnMessage public string onmessage (@PathParam (" Relationid ") String relationId, @PathParam (" Usercode ") int usercode, string message) { return "got your message (" + message + "). Thanks ! ";} Trigger * @param relationId * @param userCode * @param/** * exception session*/@OnError public void onerror (@PathParam ("Relationid") String relationid, @PathParam ("Usercode") int usercode, throwable throwable, session session) { log.info ("Websocket connection exception:" + sessionutils.getkey ( Relationid, usercode); log.info (Throwable.getmessage (), throwable); sessionutils.remove (Relationid, usercode) ;} /** * Trigger * @param relationId * @param userCode * @param When a connection is closed session*/@OnClose public void onclose (@PathParam ("Relationid") String relationid, @PathParam ("Usercode") int usercode, session session) { Log.info ("Websocket close connection:" + sessionutils.getkey (Relationid, usercode)); Sessionutils.remove (Relationid, usercode);}}
Tool classes are used to store unique keys and connections
This is my business needs, my business is that the server has a corresponding action triggered when the push data to the client, do not receive client data operations.
import javax.websocket.session;import java.util.map;import java.util.concurrent.concurrenthashmap;/** * function Description: The correspondence between SessionID and connections used to store business definitions * Take advantage of the SessionID that are assembled in the business logic to get a valid connection for subsequent operations * liuxing (2014-12-26&NBSP;02:32) */public class Sessionutils { public static map<string, session> clients = new ConcurrentHashMap<> (); public static void put (String relationid, int usercode, session session) { clients.put (GetKey (Relationid, usercode), Session);} public static session get (string relationid, int usercode) { return clients.get (GetKey (Relationid, usercode));} public static void remove (String relationid, int usercode) { Clients.remove (GetKey (Relationid, usercode));} /** * determine if there is connectivity * @param relationId * @param usercode * @return */ public static boolean hasconnection (String relationId, int usercode) { return clients.containskey (GetKey (Relationid, usercode));} /** * assembled uniquely identified key * @param relationId * @param usercode * @ Return*/ public static string getkey (String relationid, int usercode) { return relationid + "_" + usercode;}}
Push data to Client
Called in other business methods
/** * Send data back to client * Async Way * @param relationid * @param usercode * @param message*/public void Broadcast (String Relationid, I NT Usercode, String message) {if (Telsocketsessionutils.hasconnection (Relationid, Usercode)) { Telsocketsessionutils.get (Relationid, Usercode). Getasyncremote (). SendText (message); } else {throw new NullPointerException (Telsocketsessionutils.getkey (Relationid, Usercode) + "Connection does not exist") ;}}
I'm using asynchronous methods to push data, and synchronous methods.
See: http://docs.oracle.com/javaee/7/api/javax/websocket/Session.html
Client
var websocket = null;var trytime = 0;$ (function () {initSocket (); window.onbeforeunload = function () {//other actions when leaving the page}; ** * Initialize WebSocket, establish connection */function initsocket () { if (!window. WebSocket) {alert ("Your browser does not support websocket! "); return false;} websocket = new websocket ("ws://127.0.0.1:8080/websocket.ws/" + relationId + "/" + usercode); // receive the service-side message webSocket.onmessage = function (msg) { Console.log (msg);}; // exception webSocket.onerror = function (event) {console.log (event);}; // Establish connection webSocket.onopen = function (event) {console.log (event);}; // Wire Break re-connect webSocket.onclose = function () { // retry 10 times, interval 10 seconds between each if (trytime < 10) { settimeout (function () { websocket = Null;trytime++;initsocket (); }, 500); } else { trytime = 0;}};}
Other Debugging Tools
Java implementation of a WebSocket client
<dependency><groupid>org.java-websocket</groupid><artifactid>java-websocket</ Artifactid><version>1.3.0</version></dependency>
Import java.io.IOException; Import Javax.websocket.ClientEndpoint; Import Javax.websocket.OnError; Import Javax.websocket.OnMessage; Import Javax.websocket.OnOpen; Import javax.websocket.Session; @ClientEndpoint public class MyClient {@OnOpen public void OnOpen (session session) {SYSTEM.OUT.PRINTLN ("Connected to EN Dpoint: "+ session.getbasicremote ()); try {session.getbasicremote (). SendText ("Hello"),} catch (IOException ex) {}} @OnMessage public void OnMessage (String mes Sage) {System.out.println (message);} @OnError public void OnError (Throwable t) {t.printstacktrace ();}}
import java.io.bufferedreader; import java.io.ioexception; import java.io.inputstreamreader; import java.net.uri; import javax.websocket.containerprovider; import javax.websocket.deploymentexception; import javax.websocket.session; import javax.websocket.websocketcontainer; public class myclientapp { public session session; protected void start () { WebSocketContainer container = Containerprovider.getwebsocketcontainer (); string uri = "ws://127.0.0.1:8080/websocket.ws/ relationid/12345 "; system.out.println (" Connecting to "+ uri); try { session = container.connecttoserver (Myclient.class, uri.create (URI)); } catch (deploymentexception e) { e.printstacktrace (); } catch (ioexception e) { e.printstacktrace ();}} public static void main (string args[]) { myclientapp client = new myclientapp (); client.start (); bufferedreader br = new BufferedReader (New inputstreamreader (system.in)); string input = ""; try { do{ input = br.readline (); if (!input.equals ("Exit")) Client.session.getBasicRemote (). SendText (input);} while (!input.equals ("Exit")); } catch (ioexception e) { // TODO Auto-generated catch block e.printstacktrace ();}}}
Chrome installs a WebSocket emulation client
At last
For a unified operating experience, for some browsers that do not support websocket, use SOCKETJS Technology for client development.
WebSocket Server 4