WebSocket 从入门到进阶实战

好记忆不如烂笔头,能记下点东西,就记下点,有时间拿出来看看,也会发觉不一样的感受.

聊天系统是WebSocket的最佳实践,以下是使用WebSocket技术实现的一个聊天系统的关键代码,可以通过这些关键代码,更加清晰的了解 WebSocket 在项目中的使用情况(本实战将以springboot框架进行展开)。

目录

一、前端代码(HTML + JavaScript)

前端页面:chat.html

二、Java 后端代码(Spring Boot)

1. 添加依赖

2. 配置 WebSocket

3. 创建 WebSocket 服务端类

4. 创建 Spring Boot 应用主类

三、异常处理和性能优化

1. 异常处理

2. 性能优化

四、运行和测试

五、总结


一、前端代码(HTML + JavaScript)

前端页面:chat.html
 
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>实时聊天室</title><style>body {font-family: Arial, sans-serif;margin: 0;padding: 0;display: flex;flex-direction: column;align-items: center;justify-content: center;height: 100vh;background-color: #f4f4f4;}#chat-container {width: 80%;max-width: 600px;background: white;border-radius: 8px;box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);overflow: hidden;}#chat-header {background: #007bff;color: white;padding: 10px;text-align: center;font-size: 1.5em;}#chat-body {height: 300px;overflow-y: auto;padding: 10px;border-bottom: 1px solid #ddd;}#chat-footer {display: flex;padding: 10px;}#chat-footer input {flex: 1;padding: 8px;border: 1px solid #ddd;border-radius: 4px;margin-right: 10px;}#chat-footer button {padding: 8px 16px;border: none;background: #007bff;color: white;border-radius: 4px;cursor: pointer;}#chat-footer button:hover {background: #0056b3;}.message {margin-bottom: 10px;}.message .username {font-weight: bold;}</style>
</head>
<body><div id="chat-container"><div id="chat-header">实时聊天室</div><div id="chat-body"></div><div id="chat-footer"><input type="text" id="message-input" placeholder="输入消息..."><button onclick="sendMessage()">发送</button></div></div><script>const chatBody = document.getElementById('chat-body');const messageInput = document.getElementById('message-input');let webSocket = null;// 连接 WebSocket 服务器function connect() {if ('WebSocket' in window) {webSocket = new WebSocket("ws://localhost:8080/chat");webSocket.onopen = function() {console.log("已连接到服务器");};webSocket.onmessage = function(event) {const message = JSON.parse(event.data);displayMessage(message);};webSocket.onclose = function() {console.log("连接已关闭");};webSocket.onerror = function(error) {console.error("WebSocket 发生错误:", error);};} else {alert("您的浏览器不支持 WebSocket!");}}// 发送消息function sendMessage() {const messageText = messageInput.value.trim();if (messageText) {const message = {username: "用户" + Math.floor(Math.random() * 100), // 模拟用户名text: messageText};webSocket.send(JSON.stringify(message));messageInput.value = '';}}// 显示消息function displayMessage(message) {const messageElement = document.createElement('div');messageElement.classList.add('message');messageElement.innerHTML = `<span class="username">${message.username}:</span> ${message.text}`;chatBody.appendChild(messageElement);chatBody.scrollTop = chatBody.scrollHeight; // 滚动到底部}// 页面加载时连接 WebSocketwindow.onload = connect;</script>
</body>
</html>

二、Java 后端代码(Spring Boot)

1. 添加依赖

pom.xml 文件中添加 WebSocket 依赖:
 

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
2. 配置 WebSocket

创建一个配置类 WebSocketConfig
 

package com.example.websocket.config;import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.socket.server.standard.ServerEndpointExporter;@Configuration
public class WebSocketConfig {@Beanpublic ServerEndpointExporter serverEndpointExporter() {return new ServerEndpointExporter();}
}
3. 创建 WebSocket 服务端类

创建一个 WebSocket 服务端类 ChatServer
 

package com.example.websocket.server;import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;import javax.websocket.*;
import javax.websocket.server.ServerEndpoint;
import java.io.IOException;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;@ServerEndpoint("/chat")
@Component
public class ChatServer {private static final Logger log = LoggerFactory.getLogger(ChatServer.class);private static final Set<Session> sessions = Collections.synchronizedSet(new HashSet<>());@OnOpenpublic void onOpen(Session session) {sessions.add(session);log.info("新用户连接: " + session.getId());sendMessageToAll("系统通知: 有新用户加入了聊天室!");}@OnMessagepublic void onMessage(String message, Session session) {log.info("收到来自用户的消息: " + message);sendMessageToAll(message);}@OnClosepublic void onClose(Session session) {sessions.remove(session);log.info("用户断开连接: " + session.getId());sendMessageToAll("系统通知: 有用户离开了聊天室!");}@OnErrorpublic void onError(Session session, Throwable throwable) {log.error("WebSocket 发生错误: " + throwable.getMessage());sessions.remove(session);}// 向所有用户发送消息private void sendMessageToAll(String message) {synchronized (sessions) {for (Session session : sessions) {if (session.isOpen()) {try {session.getBasicRemote().sendText(message);} catch (IOException e) {log.error("发送消息时发生错误: " + e.getMessage());}}}}}
}
4. 创建 Spring Boot 应用主类

创建一个主类 ChatApplication

package com.example.websocket;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
public class ChatApplication {public static void main(String[] args) {System.out.println("聊天系统正在启动");SpringApplication.run(ChatApplication.class, args);System.out.println("聊天系统启动完成");}
}

三、异常处理和性能优化

1. 异常处理
  • onError 方法中记录错误日志,并从会话集合中移除异常的会话。

  • 在发送消息时捕获 IOException,避免因单个会话异常导致整个应用崩溃。

2. 性能优化
  • 使用 CopyOnWriteArraySet 存储会话集合,确保线程安全。

  • 在发送消息时,通过同步块确保线程安全,避免并发问题。

四、运行和测试

  1. 启动后端服务:运行 ChatApplication 类启动 Spring Boot 应用。

  2. 打开前端页面:在浏览器中打开 chat.html 文件。

  3. 测试聊天功能:在多个浏览器窗口中打开 chat.html,输入消息并发送,观察消息是否实时同步到其他窗口。

五、总结

以上代码实现了一个简单的实时聊天系统,前端使用 HTML 和 JavaScript,后端使用 Spring Boot 和 WebSocket。代码中包含了异常处理和性能优化的措施,确保系统的稳定性和高效性。通过 WebSocket 的实时通信能力,用户可以即时发送和接收消息,提升用户体验。

关注我,带你了解更多IT知识
搜索codingba 或 “码出精彩” ,和我一起探讨软件研发的那些事。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/82034.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

边缘云的定义、实现与典型应用场景!与传统云计算的区别!

一、什么是边缘云&#xff1f;‌ 边缘云是一种‌分布式云计算架构‌&#xff0c;将计算、存储和网络资源部署在‌靠近数据源或终端用户的网络边缘侧‌&#xff08;如基站、本地数据中心或终端设备附近&#xff09;&#xff0c;而非传统的集中式云端数据中心。 ‌核心特征‌&…

【爬虫】12306自动化购票

上文&#xff1a; 【爬虫】12306查票-CSDN博客 下面是简单的自动化进行抢票&#xff0c;只写到预定票&#xff0c;没有写完登陆&#xff0c; 跳出登陆后与上述代码同理修改即可。 感觉xpath最简单&#xff0c;复制粘贴&#xff1a; 还有很多写法&#xff1a; 官网地址&#…

Docker 推出强化镜像以增强容器安全性

Docker 推出了Docker Hardened Images&#xff0c;这是一个企业级、安全强化的容器镜像目录&#xff0c;旨在防御软件供应链威胁。Docker 表示&#xff0c;通过减轻 DevOps 团队自行保护容器安全的繁琐工作&#xff0c;强化镜像提供了一种更简便的方式来满足企业级安全和合规性…

SQLMesh 宏操作符详解:@IF 的条件逻辑与高级应用

SQLMesh 的 IF 宏提供了一种在 SQL 查询中嵌入条件逻辑的方法&#xff0c;允许根据运行时条件动态调整查询结构。本文深入探讨 IF 的语法、使用场景及实际案例&#xff0c;帮助开发者构建更灵活、可维护的 SQL 工作流。 1. IF 宏简介 IF 是 SQLMesh 提供的条件逻辑宏&#xff…

SpringBoot为什么要禁止循环依赖?

大家好&#xff0c;我是锋哥。今天分享关于【SpringBoot为什么要禁止循环依赖?】面试题。希望对大家有帮助&#xff1b; SpringBoot为什么要禁止循环依赖? 1000道 互联网大厂Java工程师 精选面试题-Java资源分享网 Spring Boot&#xff08;以及Spring框架&#xff09;禁止循…

塔能科技:工厂能耗精准节能全方位解决方案

在工业生产中&#xff0c;工厂能耗管理是企业运营的关键环节。随着制造业的快速发展&#xff0c;工厂对能源的需求持续攀升&#xff0c;然而能耗监测与管理难题却成为众多企业实现节能增效的阻碍。塔能科技凭借在智慧物联节能领域的深厚积累&#xff0c;为工厂能耗精准节能打造…

无人机避障——深蓝学院浙大Ego-Planner规划部分

ESDF-free&#xff1a; 被这种类型的障碍物死死卡住的情况&#xff1a; 在一定范围内建立ESDF&#xff1a; Ego-Planner框架&#xff1a; 找到{p,v} pair&#xff1a; 【注意】&#xff1a;首先根据在障碍物内航迹上的点Q&#xff0c;以及与它相邻但不在障碍物内的两个点&#…

CentOS7挂载hgfs文件夹(VMware 共享文件夹)及网卡的自启动。

1、设置网卡自启动 # 启用网络服务 systemctl enable network # 修改网卡配置 # eth0 为网卡名称&#xff0c;修改那个网卡就改那个网卡&#xff0c;格式&#xff1a;ifcfg-网卡名 vim /etc/sysconfig/network-scrips/ifcfg-eth0 # 把ONBOOT设置为 yes&#xff0c;&#xf…

【LLIE专题】基于事件相机照度估计的暗光增强方案

Low-Light Image Enhancement using Event-Based Illumination Estimation&#xff08;2025&#xff0c;CVPR&#xff09; 专题介绍一、研究背景二、RETINEV方法1.事件相机2. 本文方案2.1 事件时间戳与光照的物理关系2.2 总体架构&#xff1a;Retinex 理论驱动的分解2.3 时间到…

腾讯云媒体AI解码全球视频出海智能密码

当短剧平台撞上多语种字幕困境&#xff0c;当直播电商遭遇文化审核危机&#xff0c;当经典影视困于格式壁垒——这些内容出海的难题&#xff0c;正被腾讯云媒体AI的智能引擎逐个破解。从东南亚的直播卡顿到中东的宗教符号雷区&#xff0c;从老片的低清画质到元宇宙的渲染瓶颈&a…

Spring Boot 多租户架构实现:基于上下文自动传递的独立资源隔离方案

一、核心设计思想 通过线程上下文自动传递租户ID&#xff0c;结合动态数据源路由和中间件连接工厂&#xff0c;实现MySQL、Redis、RocketMQ的完全自动化资源隔离。关键设计如下&#xff1a; #mermaid-svg-ZjXCGSWoCuNFMIch {font-family:"trebuchet ms",verdana,aria…

参与开发的注意事项

1.开发期间&#xff0c;不要擅自修改架构的内容 使用技术官发的项目文件夹来开发&#xff0c;而不是自己建立项目&#xff0c; 否则会导致环境不统一 架构内容&#xff1a;&#xff08;不能更改&#xff09; 1.类型定义&#xff0c;全局变量声明 2.函数申明&#xff08;函数名称…

产业互联网+三融战略:重构企业增长密码

产业互联网时代&#xff1a;用"三融"重构企业增长飞轮 在产业互联网浪潮下&#xff0c;企业面临资源分散、资金短缺、人才难聚的三重挑战。本文提出的"融人、融资、融资源"顶层设计&#xff0c;正为新时代企业构建增长新引擎。 一、三级合伙人体系&#x…

【JavaScript异步编程终极指南】从回调地狱到Async/Await的实战突围

目录 &#x1f30d; 前言&#xff1a;技术背景与价值&#x1f494; 当前技术痛点&#x1f6e0; 解决方案概述&#x1f465; 目标读者说明&#x1f50d; 一、技术原理剖析&#x1f9e0; 核心作用讲解&#x1f9e9; 关键技术模块说明⚖️ 技术选型对比 &#x1f4bb; 二、实战演示…

国标GB28181设备管理软件EasyGBS视频监控系统打造工厂可视化监管场景解决方案

一、引言​ 随着工厂规模扩大、生产流程复杂化&#xff0c;传统管理模式已难以满足精细化运营需求。当前部分工厂视频监控系统存在设备协议不兼容、功能分散等问题。EasyGBS视频监控系统基于GB28181标准协议&#xff0c;以高兼容性架构实现设备统一接入&#xff0c;集成视频全…

# 终端执行 java -jar example.jar 时(example.jar为项目jar包)报错:“没有主清单属性” 的解决方法

终端执行 java -jar example.jar 时&#xff08;example.jar为项目jar包&#xff09;报错&#xff1a;“没有主清单属性” 的解决方法 在Java中&#xff0c;一个JAR文件必须包含一个主清单属性&#xff08;Main-Class属性&#xff09;才能在命令行中直接运行。如果你在尝试运行…

使用 mutt 发送邮件:Linux 下轻量高效的命令行邮件工具

文章目录 一、安装 mutt二、配置 .muttrc三、发送一封简单邮件四、发送给多个收件人五、发送附件六、临时设置发件人七、脚本示例&#xff1a;八.结语 在 Linux 或类 Unix 系统中&#xff0c;mutt 是一款经典且强大的命令行邮件客户端&#xff08;MUA&#xff0c;邮件用户代理&…

OceanBase 开发者大会,拥抱 Data*AI 战略,构建 AI 数据底座

5 月 17 号以“当 SQL 遇见 AI”为主题的 OceanBase 开发者大会在广州举行&#xff0c;因为行程的原因未能现场参会&#xff0c;仍然通过视频直播观看了全部的演讲。总体来说&#xff0c;这届大会既有对未来数据库演进方向的展望&#xff0c;也有 OceanBase 新产品的发布&#…

为 Spring Boot 应用程序构建 CI/CD 流水线

为 Spring Boot 应用程序创建构建/部署流水线涉及多个步骤,而 Jenkins 可以作为强大的工具来自动化这些流程。在本教程中,我们将指导您为托管在 GitHub 上的 Spring Boot 应用程序设置流水线,使用 Jenkins 构建该应用程序,并将其部署到 Amazon Elastic Kubernetes Service …

BI是什么意思?一文讲清BI的概念与应用!

目录 一、BI 是什么意思 1. BI 的定义 2. BI 的发展历程 3. BI 的核心组件 二、BI 的应用场景 1. 销售与市场营销 2. 财务管理 ​编辑3. 人力资源管理 4. 生产与运营管理 ​编辑三、选择合适的 BI 工具 1. 考虑企业的需求和规模 2. 评估工具的功能和性能 3. 关注工…