首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 綜合教學

WebSocket 實戰:基於 Tomcat 7+ 實現瀏覽器與服務器全雙工通信

     編輯:Java 綜合教學

WebSocket 核心優勢

WebSocket 是 HTML5 規範定義的新協議,實現瀏覽器與服務器**全雙工通信**。相比 HTTP 輪詢/長連接,優勢顯著:

  • 單次握手建立持久連接,後續雙向數據幀無需 HTTP 頭開銷。
  • 服務器可主動推送數據到客戶端,適合即時通訊、協作編輯、股票行情等場景。
  • 基於 TCP,瀏覽器原生支持(現代瀏覽器),無需插件。

環境準備

  • Tomcat 7.0+(內置 WebSocket API 實現)
  • 將 tomcat7-websocket.jar、websocket-api.jar 加入 classpath(Tomcat lib 目錄下即有)

服務端實現(註解式)

1. 配置類:WebSocketConfig

import javax.websocket.Endpoint;
import javax.websocket.server.ServerApplicationConfig;
import javax.websocket.server.ServerEndpointConfig;
import java.util.Set;

public class WebSocketConfig implements ServerApplicationConfig {
    @Override
    public Set getEndpointConfigs(Set> scanned) {
        return null; // 使用註解掃描,無需程序化配置
    }
    @Override
    public Set> getAnnotatedEndpointClasses(Set> scanned) {
        return scanned; // 返回所有掃描到的 @ServerEndpoint 類
    }
}

2. 端點類:EchoSocket

import javax.websocket.*;
import javax.websocket.server.ServerEndpoint;

@ServerEndpoint("/zqq/echo")
public class EchoSocket {
    @OnOpen
    public void onOpen(Session session) {
        System.out.println("新連接建立,Session ID: " + session.getId());
    }

    @OnMessage
    public void onMessage(Session session, String msg) {
        System.out.println("收到消息 [" + session.getId() + "]: " + msg);
        // 業務邏輯處理後可主動推送回客戶端
        // session.getBasicRemote().sendText("Server Echo: " + msg);
    }

    @OnClose
    public void onClose(Session session) {
        System.out.println("連接關閉: " + session.getId());
    }

    @OnError
    public void onError(Session session, Throwable throwable) {
        System.err.println("連接異常: " + throwable.getMessage());
    }
}

客戶端頁面:echo.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
    <title>WebSocket Demo</title>
    <script type="text/javascript">
        var ws;
        // ws:// 協議,自動拼接當前主機、端口、上下文路徑
        var target = "ws://${pageContext.request.remoteHost}:8080${pageContext.request.contextPath}/zqq/echo";

        function subOpen() {
            if ('WebSocket' in window) {
                ws = new WebSocket(target);
            } else if ('MozWebSocket' in window) { // 兼容老式 Firefox
                ws = new MozWebSocket(target);
            } else {
                alert('當前瀏覽器不支持 WebSocket');
                return;
            }
            ws.onmessage = function(event) {
                console.log('收到服務器消息:', event.data);
                document.getElementById("h1").innerHTML += event.data + " ";
            };
            ws.onopen = function() { console.log("連接已建立"); };
            ws.onclose = function() { console.log("連接已關閉"); };
            ws.onerror = function(err) { console.error("連接錯誤:", err); };
        }

        function subSend() {
            var input = document.getElementById("input");
            var text = input.value;
            if (text && ws && ws.readyState === WebSocket.OPEN) {
                ws.send(text);
                input.value = "";
            }
        }
    </script>
</head>
<body>
    <button onclick="subOpen()">點擊開啟連接</button><br/>
    <input id="input" type="text" placeholder="輸入發送內容"><br/>
    <button onclick="subSend()">發送消息</button>
    <div id="h1">接收區域: </div>
</body>
</html>

部署與測試

  1. 將項目打包為 WAR 部署到 Tomcat webapps 目錄。
  2. 啟動 Tomcat,瀏覽器訪問 https://localhost:8080/項目名/echo.jsp。
  3. 點擊「開啟連接」,控制台顯示連接成功。
  4. 輸入文字點擊「發送」,服務端控制台打印收到消息,頁面顯示回顯。

常見坑與避雷指南

  • 版本不匹配:Tomcat 6 不支持 WebSocket,必須 7.0+。
  • JAR 衝突:不要將 WebSocket API JAR 打包進 WAR,避免與容器提供類衝突,標記為 provided 作用域。
  • 跨域/代理:Nginx 反向代理需配置 proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; 支持 WebSocket 升級。
  • 心跳機制:生產環境必須實現客戶端/服務端雙向心跳(Ping/Pong),防止連接被防火牆/負載均衡器靜默斷開。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved