場景:在B/S結構的系統中,有時客戶端須要實時的得到服務器反饋的消息,可是HTTP協議只支持請求響應模式,因此咱們常常經過輪詢(polling)、長輪詢(Long polling)、長鏈接、WebSocket等方式來完成實時消息的推送功能。web
HTTP請求響應模式: 優勢:簡化Web服務器,減小服務器的負擔,加快響應速度,由於服務器不須要與客戶端長時間創建一個通訊連接。 缺點:不容易直接完成實時消息的推送功能,如聊天室、實時更新數據等功能。 輪詢:客戶端定時向服務器發送Ajax請求,服務器接到請求後立刻返回響應信息並關閉鏈接。 優勢:後端程序編寫比較容易。 缺點:大多數的請求都是無用的,浪費帶寬和服務器資源。 長輪詢:客戶端向服務器發送Ajax請求,服務器接到請求後一直持有(hold住)鏈接,直到有新消息才返回響應信息並關閉鏈接,客戶端處理完響應信息後再向服務器發送新的請求。 優勢:在無消息的狀況下不會頻繁的請求,耗費資小。 缺點:服務器hold鏈接會消耗資源,返回數據順序無保證,難於管理維護。 長鏈接:在頁面裏嵌入一個隱蔵iframe,將這個隱蔵iframe的src屬性設爲對一個長鏈接的請求或是採用xhr請求,服務器端就能源源不斷地往客戶端輸入數據。 優勢:消息即時到達,不發無用請求,管理起來也相對便。 缺點:服務器維護一個長鏈接會增長開銷。 Websocket 1)概念:WebSocket是HTML5開始提供的一種瀏覽器與服務器間進行全雙工通信(即容許服務器主動發送信息給客戶端)的網絡技術,基於TCP協議,能夠實現客戶端和服務器端的長鏈接,雙向實時通訊。 2)特色:事件驅動、異步。 3)WebSocket客戶端: 概念: 1)websocket容許瀏覽器經過JavaScript與遠程服務器創建鏈接,從而實現客戶端與服務器間雙向的通訊。 2)websocket採用的協議是ws(若是須要ssl加密則使用wss),當咱們調用websocket的構造方法構建一個websocket對象以後,瀏覽器就能夠和服務器進行實時通訊了。 websocket中的方法: send() 向遠程服務器發送數據 close() 關閉與服務器之間的websocket連接 onopen 當網絡鏈接創建時觸發該事件 onerror 當網絡發生錯誤時觸發該事件 onclose 當websocket被關閉時觸發該事件 onmessage 當websocket接收到服務器發來的消息的時觸發的事件,也是通訊中最重要的一個監聽事件。 websocket中的屬性: readyState 這個屬性表示websocket所處的狀態: CONNECTING(0) websocket正嘗試與服務器創建鏈接 OPEN(1) websocket與服務器已經創建鏈接 CLOSING(2) websocket正在關閉與服務器的鏈接 CLOSED(3) websocket已經關閉了與服務器的鏈接 4)WebSocket服務器端: 概念: 1)@ServerEndpoint註解修飾的類做爲WebSocket服務器的端點。 2)@ServerEndpoint註解修飾的類必須有一個公共的無參數構造函數。 舉例: /** * 1)該註解表示:咱們能夠在客戶端瀏覽器上經過訪問如下地址來與服務器創建長鏈接,從而進行實時通訊。 * 2)訪問地址:ws://[服務器IP]:[服務器端口]/項目名/websocket/task/{name} */ @ServerEndpoint(value = "/websocket/task/{name}") public class WebSocketServer { /** * 鏈接打開時執行 */ @OnOpen public String onOpen(@PathParam("name") String taskName, Session session) { } /** * 客戶端調用socket.send()方法,服務器收到消息時執行該方法,該方法的返回值即:返回給客戶端的信息。 */ @OnMessage public String onMessage(String message, Session session) { } /** * 鏈接關閉時執行 */ @OnClose public void onClose(Session session, CloseReason closeReason) { } /** * 鏈接錯誤時執行 * 說明:若是客戶端直接關閉了瀏覽器,則服務器先調用OnError方法,後調用OnClose方法。 */ @OnError public void onError(Throwable t) { t.printStackTrace(); } }