在nodejs中使用WebSocket實現聊天效果(簡易實現)
安裝
npm i ws
實現
創建 server.js
/*** 創建一個 WebSocket 服務器,監聽指定端口,并處理客戶端連接和消息。** @param {Object} WebSocket - 引入的 WebSocket 模塊,用于創建 WebSocket 服務器。** 功能步驟:* 1. 創建一個 WebSocket 服務器,監聽端口 1024。* 2. 維護一個消息列表 `list`,用于存儲客戶端發送的消息。* 3. 當客戶端發送消息時,解析消息內容并將其添加到消息列表中。* 4. 將更新后的消息列表發送回客戶端。*/const WebSocket = require('ws')// 消息列表,用于存儲所有客戶端發送的消息
let list = []// 創建 WebSocket 服務器,監聽端口 1024
const wss = new WebSocket.Server({port: 1024},() => {console.log('Server is listening on port 1024')}
)// 監聽客戶端連接事件
wss.on('connection', function (ws) {// 監聽客戶端發送的消息事件ws.on('message', function (msg) {// console.log('收到客戶端消息', JSON.parse(msg))try {// 解析客戶端發送的消息if (msg) {// 如果消息沒有錯誤,將消息內容添加到消息列表中list.push(JSON.parse(msg).netName + ' 說: ' + JSON.parse(msg).msg)}} catch (error) {}// 將更新后的消息列表發送回客戶端ws.send(JSON.stringify(list))})
})
創建 client.js 測試
/*** 創建一個WebSocket客戶端,用于連接指定的WebSocket服務器。** 參數:* - 'ws://192.168.8.183:1024': WebSocket服務器的URL地址。*/
const WebSocket = require('ws')const ws = new WebSocket('ws://192.168.8.183:1024')// 當WebSocket連接成功打開時觸發
ws.on('open', function () {console.log('Client is listening on port 1024') // 打印日志,表示客戶端已成功連接到服務器ws.send(JSON.stringify('Hello World')) // 向服務器發送消息
})// 當接收到服務器發送的消息時觸發
ws.on('message', function (msg) {console.log('收到服務器消息', JSON.parse(msg))// ws.send(msg) // 將接收到的消息原樣返回給服務器
})// 當WebSocket連接關閉時觸發
ws.on('close', function () {console.log('Client close') // 打印日志,表示客戶端連接已關閉
})
?分別運行以上兩個文件,如果互相能收到消息表示服務運行正常
?創建 index.html 文件
<!DOCTYPE html>
<html lang="zh"><head><meta charset="UTF-8" /><meta name="viewport" content="width=device-width, initial-scale=1.0" /><meta http-equiv="X-UA-Compatible" content="ie=edge" /><title>WebSocket 消息發送</title><style>/* 消息輸入框樣式 */#text {width: 350px;height: 30px;}/* 用戶名輸入框樣式 */#netName {width: 150px;height: 30px;}</style></head><body><!-- 消息顯示區域 --><textarea id="msg" cols="80" rows="30" readonly></textarea><br /><!-- 用戶名輸入框 --><input id="netName" type="text" placeholder="名稱" /><!-- 消息輸入框 --><input id="text" type="text" placeholder="消息" /><!-- 發送按鈕 --><button id="sendButton">發送</button><script>let ws = null // WebSocket 連接對象/*** 初始化 WebSocket 連接*/function initWebSocket() {if (ws) return // 避免重復連接ws = new WebSocket('ws://192.168.8.183:1024')ws.onopen = () => {console.log('WebSocket 連接已建立')}ws.onmessage = (evt) => {try {const receivedData = JSON.parse(evt.data)msg.value = Array.isArray(receivedData) ? receivedData.join('\n') : JSON.stringify(receivedData, null, 2)} catch (error) {console.error('解析接收到的數據失敗:', error)}}ws.onerror = (error) => {console.error('WebSocket 錯誤:', error)}ws.onclose = () => {console.log('WebSocket 連接已關閉,嘗試重新連接...')ws = nullsetTimeout(initWebSocket, 5000) // 5 秒后重連}setInterval(() => {ws.send('')}, 1000)}/*** 發送消息到 WebSocket 服務器* @param {Object} data - 要發送的數據對象*/function sendMessage(data) {if (!ws || ws.readyState !== WebSocket.OPEN) {console.warn('WebSocket 未打開,嘗試重新連接...')initWebSocket()return}if (!data) {data = { err: 1 }} else if (typeof data !== 'object' || Array.isArray(data)) {console.error('數據格式無效')return}ws.send(JSON.stringify(data))}/*** 處理發送按鈕點擊或回車鍵事件*/function handleSend() {const netNameValue = netName.value.trim()const textValue = text.value.trim()if (!netNameValue || !textValue) {alert('用戶名和消息不能為空')return}const message = {netName: netNameValue,msg: textValue}sendMessage(message)text.value = '' // 清空消息輸入框}// 初始化 WebSocket 連接initWebSocket()// 綁定發送按鈕點擊事件document.getElementById('sendButton').addEventListener('click', handleSend)// 監聽回車鍵事件document.addEventListener('keyup', (e) => {if (e.key === 'Enter') {handleSend()}})</script></body>
</html>
用兩個瀏覽器打開此文件,就可以互相發送消息
靜態文件服務?
或者創建一個 static.js 靜態服務訪問 index.html
// static.jsconst express = require('express')
const app = express()
const path = require('path')app.use('/main', express.static(path.join(__dirname, 'index.html'))) // 設置靜態文件夾// 端口號不能與socket監聽的端口號一樣
app.listen(2048, () => {console.log('static 2048 Server Start~')
})
啟動服務
node static.js
訪問:?http://127.0.0.1:2048/main
?以上所有文件放在同一目錄