一、后端

1.在Springboot项目的pom.xml中添加依赖

<!--websocket协议-->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
<!--hutool-->
<dependency><groupId>cn.hutool</groupId><artifactId>hutool-all</artifactId><version>5.4.3</version>
</dependency>

2.要想使用WebSocket配置config配置类

package com.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 {/*** 注入ServerEndpointExporter bean对象,他会自动注册使用@ServerEndpoint* @return*/@Beanpublic ServerEndpointExporter serverEndpointExporter(){return new ServerEndpointExporter();}
}

3.新建component问价夹,下方新建WebSocketServer核心代码

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FJo3rH5s-1675864417091)(C:\Users\86155\Desktop\websocket实现聊天室\image-20230208193030259.png)]

package com.websocket.component;import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;import javax.websocket.*;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;/*** @author websocket服务*/
@ServerEndpoint(value = "/imserver/{username}")
@Component
public class WebSocketServer {private static final Logger log = LoggerFactory.getLogger(WebSocketServer.class);/*** 记录当前在线连接数*/public static final Map<String, Session> sessionMap = new ConcurrentHashMap<>();/*** 连接建立成功调用的方法*/@OnOpenpublic void onOpen(Session session, @PathParam("username") String username) {sessionMap.put(username, session);log.info("有新用户加入,username={}, 当前在线人数为:{}", username, sessionMap.size());JSONObject result = new JSONObject();JSONArray array = new JSONArray();result.set("users", array);for (Object key : sessionMap.keySet()) {JSONObject jsonObject = new JSONObject();jsonObject.set("username", key);// {"username", "zhang", "username": "admin"}array.add(jsonObject);}
//        {"users": [{"username": "zhang"},{ "username": "admin"}]}sendAllMessage(JSONUtil.toJsonStr(result));  // 后台发送消息给所有的客户端}/*** 连接关闭调用的方法*/@OnClosepublic void onClose(Session session, @PathParam("username") String username) {sessionMap.remove(username);log.info("有一连接关闭,移除username={}的用户session, 当前在线人数为:{}", username, sessionMap.size());}/*** 收到客户端消息后调用的方法* 后台收到客户端发送过来的消息* onMessage 是一个消息的中转站* 接受 浏览器端 socket.send 发送过来的 json数据* @param message 客户端发送过来的消息*/@OnMessagepublic void onMessage(String message, Session session, @PathParam("username") String username) {log.info("服务端收到用户username={}的消息:{}", username, message);JSONObject obj = JSONUtil.parseObj(message);String toUsername = obj.getStr("to"); // to表示发送给哪个用户,比如 adminString text = obj.getStr("text"); // 发送的消息文本  hello// {"to": "admin", "text": "聊天文本"}Session toSession = sessionMap.get(toUsername); // 根据 to用户名来获取 session,再通过session发送消息文本if (toSession != null) {// 服务器端 再把消息组装一下,组装后的消息包含发送人和发送的文本内容// {"from": "zhang", "text": "hello"}JSONObject jsonObject = new JSONObject();jsonObject.set("from", username);  // from 是 zhangjsonObject.set("text", text);  // text 同上面的textthis.sendMessage(jsonObject.toString(), toSession);log.info("发送给用户username={},消息:{}", toUsername, jsonObject.toString());} else {log.info("发送失败,未找到用户username={}的session", toUsername);}}@OnErrorpublic void onError(Session session, Throwable error) {log.error("发生错误");error.printStackTrace();}/*** 服务端发送消息给客户端*/private void sendMessage(String message, Session toSession) {try {log.info("服务端给客户端[{}]发送消息{}", toSession.getId(), message);toSession.getBasicRemote().sendText(message);} catch (Exception e) {log.error("服务端发送消息给客户端失败", e);}}/*** 服务端发送消息给所有客户端*/private void sendAllMessage(String message) {try {for (Session session : sessionMap.values()) {log.info("服务端给客户端[{}]发送消息{}", session.getId(), message);session.getBasicRemote().sendText(message);}} catch (Exception e) {log.error("服务端发送消息给客户端失败", e);}}
}

4.如果有拦截就放开拦截

​ 我没有设置拦截,全部都是放开的


二、Websocket

1.Websocket 属性

属性 描述
Socket.readyState 只读属性 ready State 表示连接状态,可以是以下值:
0 - 表示连接尚未建立
1 - 表示连接已经建立,可以进行通信。
2 - 表示连接正在关闭
3 - 表示连接已经关闭或者连接不能打开
Socket.buffereAmount 只读属性 buffereAmount 已被 send()放入队列中等待传输,但是还没有发出的utf-8文本字节数

2.WebSocket 事件

事件 事件处理程序 描述
open Socket.onopen 连接建立时触发
message Socket.onmessage 客户端接受服务端数据时触发
error Socket.onerror 通信发生错误时触发
close Socket.onclose 连接关闭时触发

3.WebSocket 方法—一下是 WebSocket对象的相关方法,假定我们使用了以上代码创建Socket 对象

方法 描述
Socket.send() 使用连接发送数据
Socket.close() 关闭连接

三、前端

<template><div style="padding: 10px; margin-bottom: 50px"><el-row><el-col :span="4"><el-card style="width: 300px; height: 300px; color: #333"><div style="padding-bottom: 10px; border-bottom: 1px solid #ccc">在线用户<span style="font-size: 12px">(点击聊天气泡开始聊天)</span></div><div style="padding: 10px 0" v-for="user in users" :key="user.username"><span>{{ user.username }}</span><i class="el-icon-chat-dot-round" style="margin-left: 10px; font-size: 16px; cursor: pointer"@click="chatUser = user.username"></i><span style="font-size: 12px;color: limegreen; margin-left: 5px" v-if="user.username === chatUser">chatting...</span></div></el-card></el-col><el-col :span="20"><div style="width: 800px; margin: 0 auto; background-color: white;border-radius: 5px; box-shadow: 0 0 10px #ccc"><div style="text-align: center; line-height: 50px;">Web聊天室({{ chatUser }})</div><div style="height: 350px; overflow:auto; border-top: 1px solid #ccc" v-html="content"></div><div style="height: 200px"><textarea v-model="text" style="height: 160px; width: 100%; padding: 20px; border: none; border-top: 1px solid #ccc;border-bottom: 1px solid #ccc; outline: none"></textarea><div style="text-align: right; padding-right: 10px"><el-button type="primary" size="mini" @click="send">发送</el-button></div></div></div></el-col></el-row></div>
</template><script>import request from "@/utils/request";let socket;export default {name: "Im",data() {return {circleUrl: 'https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png',user: {},isCollapse: false,users: [],chatUser: '',text: "",messages: [],content: ''}},created() {this.init()},methods: {send() {if (!this.chatUser) {this.$message({type: 'warning', message: "请选择聊天对象"})return;}if (!this.text) {this.$message({type: 'warning', message: "请输入内容"})} else {if (typeof (WebSocket) == "undefined") {console.log("您的浏览器不支持WebSocket");} else {console.log("您的浏览器支持WebSocket");// 组装待发送的消息 json// {"from": "zhang", "to": "admin", "text": "聊天文本"}let message = {from: this.user.username, to: this.chatUser, text: this.text}socket.send(JSON.stringify(message));  // 将组装好的json发送给服务端,由服务端进行转发this.messages.push({user: this.user.username, text: this.text})// 构建消息内容,本人消息this.createContent(null, this.user.username, this.text)this.text = '';}}},createContent(remoteUser, nowUser, text) {  // 这个方法是用来将 json的聊天消息数据转换成 html的。let html// 当前用户消息if (nowUser) { // nowUser 表示是否显示当前用户发送的聊天消息,绿色气泡html = "<div class=\"el-row\" style=\"padding: 5px 0\">\n" +"  <div class=\"el-col el-col-22\" style=\"text-align: right; padding-right: 10px\">\n" +"    <div class=\"tip left\">" + text + "</div>\n" +"  </div>\n" +"  <div class=\"el-col el-col-2\">\n" +"  <span class=\"el-avatar el-avatar--circle\" style=\"height: 40px; width: 40px; line-height: 40px;\">\n" +"    <img src=\"https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png\" style=\"object-fit: cover;\">\n" +"  </span>\n" +"  </div>\n" +"</div>";} else if (remoteUser) {   // remoteUser表示远程用户聊天消息,蓝色的气泡html = "<div class=\"el-row\" style=\"padding: 5px 0\">\n" +"  <div class=\"el-col el-col-2\" style=\"text-align: right\">\n" +"  <span class=\"el-avatar el-avatar--circle\" style=\"height: 40px; width: 40px; line-height: 40px;\">\n" +"    <img src=\"https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png\" style=\"object-fit: cover;\">\n" +"  </span>\n" +"  </div>\n" +"  <div class=\"el-col el-col-22\" style=\"text-align: left; padding-left: 10px\">\n" +"    <div class=\"tip right\">" + text + "</div>\n" +"  </div>\n" +"</div>";}console.log(html)this.content += html;},init() {this.user = sessionStorage.getItem("user") ? JSON.parse(sessionStorage.getItem("user")) : {}let username = this.user.username;let _this = this;if (typeof (WebSocket) == "undefined") {console.log("您的浏览器不支持WebSocket");} else {console.log("您的浏览器支持WebSocket");let socketUrl = "ws://localhost:9090/imserver/" + username;if (socket != null) {socket.close();socket = null;}// 开启一个websocket服务socket = new WebSocket(socketUrl);//打开事件socket.onopen = function () {console.log("websocket已打开");};//  浏览器端收消息,获得从服务端发送过来的文本消息socket.onmessage = function (msg) {console.log("收到数据====" + msg.data)let data = JSON.parse(msg.data)  // 对收到的json数据进行解析, 类似这样的: {"users": [{"username": "zhang"},{ "username": "admin"}]}if (data.users) {  // 获取在线人员信息_this.users = data.users.filter(user => user.username !== username)  // 获取当前连接的所有用户信息,并且排除自身,自己不会出现在自己的聊天列表里} else {// 如果服务器端发送过来的json数据 不包含 users 这个key,那么发送过来的就是聊天文本json数据//  // {"from": "zhang", "text": "hello"}if (data.from === _this.chatUser) {_this.messages.push(data)// 构建消息内容_this.createContent(data.from, null, data.text)}}};//关闭事件socket.onclose = function () {console.log("websocket已关闭");};//发生了错误事件socket.onerror = function () {console.log("websocket发生了错误");}}}}
}</script><style>
.tip {color: white;text-align: center;border-radius: 10px;font-family: sans-serif;padding: 10px;width:auto;display:inline-block !important;display:inline;
}.right {background-color: deepskyblue;
}
.left {background-color: forestgreen;
}
</style>

Springboot + WebSocket 实现在线聊天

一、后端

1.在Springboot项目的pom.xml中添加依赖

<!--websocket协议-->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
<!--hutool-->
<dependency><groupId>cn.hutool</groupId><artifactId>hutool-all</artifactId><version>5.4.3</version>
</dependency>

2.要想使用WebSocket配置config配置类

package com.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 {/*** 注入ServerEndpointExporter bean对象,他会自动注册使用@ServerEndpoint* @return*/@Beanpublic ServerEndpointExporter serverEndpointExporter(){return new ServerEndpointExporter();}
}

3.新建component问价夹,下方新建WebSocketServer核心代码

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-YwLc4Gkq-1675864418232)(C:\Users\86155\Desktop\websocket实现聊天室\image-20230208193030259.png)]

package com.websocket.component;import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;import javax.websocket.*;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;/*** @author websocket服务*/
@ServerEndpoint(value = "/imserver/{username}")
@Component
public class WebSocketServer {private static final Logger log = LoggerFactory.getLogger(WebSocketServer.class);/*** 记录当前在线连接数*/public static final Map<String, Session> sessionMap = new ConcurrentHashMap<>();/*** 连接建立成功调用的方法*/@OnOpenpublic void onOpen(Session session, @PathParam("username") String username) {sessionMap.put(username, session);log.info("有新用户加入,username={}, 当前在线人数为:{}", username, sessionMap.size());JSONObject result = new JSONObject();JSONArray array = new JSONArray();result.set("users", array);for (Object key : sessionMap.keySet()) {JSONObject jsonObject = new JSONObject();jsonObject.set("username", key);// {"username", "zhang", "username": "admin"}array.add(jsonObject);}
//        {"users": [{"username": "zhang"},{ "username": "admin"}]}sendAllMessage(JSONUtil.toJsonStr(result));  // 后台发送消息给所有的客户端}/*** 连接关闭调用的方法*/@OnClosepublic void onClose(Session session, @PathParam("username") String username) {sessionMap.remove(username);log.info("有一连接关闭,移除username={}的用户session, 当前在线人数为:{}", username, sessionMap.size());}/*** 收到客户端消息后调用的方法* 后台收到客户端发送过来的消息* onMessage 是一个消息的中转站* 接受 浏览器端 socket.send 发送过来的 json数据* @param message 客户端发送过来的消息*/@OnMessagepublic void onMessage(String message, Session session, @PathParam("username") String username) {log.info("服务端收到用户username={}的消息:{}", username, message);JSONObject obj = JSONUtil.parseObj(message);String toUsername = obj.getStr("to"); // to表示发送给哪个用户,比如 adminString text = obj.getStr("text"); // 发送的消息文本  hello// {"to": "admin", "text": "聊天文本"}Session toSession = sessionMap.get(toUsername); // 根据 to用户名来获取 session,再通过session发送消息文本if (toSession != null) {// 服务器端 再把消息组装一下,组装后的消息包含发送人和发送的文本内容// {"from": "zhang", "text": "hello"}JSONObject jsonObject = new JSONObject();jsonObject.set("from", username);  // from 是 zhangjsonObject.set("text", text);  // text 同上面的textthis.sendMessage(jsonObject.toString(), toSession);log.info("发送给用户username={},消息:{}", toUsername, jsonObject.toString());} else {log.info("发送失败,未找到用户username={}的session", toUsername);}}@OnErrorpublic void onError(Session session, Throwable error) {log.error("发生错误");error.printStackTrace();}/*** 服务端发送消息给客户端*/private void sendMessage(String message, Session toSession) {try {log.info("服务端给客户端[{}]发送消息{}", toSession.getId(), message);toSession.getBasicRemote().sendText(message);} catch (Exception e) {log.error("服务端发送消息给客户端失败", e);}}/*** 服务端发送消息给所有客户端*/private void sendAllMessage(String message) {try {for (Session session : sessionMap.values()) {log.info("服务端给客户端[{}]发送消息{}", session.getId(), message);session.getBasicRemote().sendText(message);}} catch (Exception e) {log.error("服务端发送消息给客户端失败", e);}}
}

4.如果有拦截就放开拦截

​ 我没有设置拦截,全部都是放开的


二、Websocket

1.Websocket 属性

属性 描述
Socket.readyState 只读属性 ready State 表示连接状态,可以是以下值:
0 - 表示连接尚未建立
1 - 表示连接已经建立,可以进行通信。
2 - 表示连接正在关闭
3 - 表示连接已经关闭或者连接不能打开
Socket.buffereAmount 只读属性 buffereAmount 已被 send()放入队列中等待传输,但是还没有发出的utf-8文本字节数

2.WebSocket 事件

事件 事件处理程序 描述
open Socket.onopen 连接建立时触发
message Socket.onmessage 客户端接受服务端数据时触发
error Socket.onerror 通信发生错误时触发
close Socket.onclose 连接关闭时触发

3.WebSocket 方法—一下是 WebSocket对象的相关方法,假定我们使用了以上代码创建Socket 对象

方法 描述
Socket.send() 使用连接发送数据
Socket.close() 关闭连接

三、前端

<template><div style="padding: 10px; margin-bottom: 50px"><el-row><el-col :span="4"><el-card style="width: 300px; height: 300px; color: #333"><div style="padding-bottom: 10px; border-bottom: 1px solid #ccc">在线用户<span style="font-size: 12px">(点击聊天气泡开始聊天)</span></div><div style="padding: 10px 0" v-for="user in users" :key="user.username"><span>{{ user.username }}</span><i class="el-icon-chat-dot-round" style="margin-left: 10px; font-size: 16px; cursor: pointer"@click="chatUser = user.username"></i><span style="font-size: 12px;color: limegreen; margin-left: 5px" v-if="user.username === chatUser">chatting...</span></div></el-card></el-col><el-col :span="20"><div style="width: 800px; margin: 0 auto; background-color: white;border-radius: 5px; box-shadow: 0 0 10px #ccc"><div style="text-align: center; line-height: 50px;">Web聊天室({{ chatUser }})</div><div style="height: 350px; overflow:auto; border-top: 1px solid #ccc" v-html="content"></div><div style="height: 200px"><textarea v-model="text" style="height: 160px; width: 100%; padding: 20px; border: none; border-top: 1px solid #ccc;border-bottom: 1px solid #ccc; outline: none"></textarea><div style="text-align: right; padding-right: 10px"><el-button type="primary" size="mini" @click="send">发送</el-button></div></div></div></el-col></el-row></div>
</template><script>import request from "@/utils/request";let socket;export default {name: "Im",data() {return {circleUrl: 'https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png',user: {},isCollapse: false,users: [],chatUser: '',text: "",messages: [],content: ''}},created() {this.init()},methods: {send() {if (!this.chatUser) {this.$message({type: 'warning', message: "请选择聊天对象"})return;}if (!this.text) {this.$message({type: 'warning', message: "请输入内容"})} else {if (typeof (WebSocket) == "undefined") {console.log("您的浏览器不支持WebSocket");} else {console.log("您的浏览器支持WebSocket");// 组装待发送的消息 json// {"from": "zhang", "to": "admin", "text": "聊天文本"}let message = {from: this.user.username, to: this.chatUser, text: this.text}socket.send(JSON.stringify(message));  // 将组装好的json发送给服务端,由服务端进行转发this.messages.push({user: this.user.username, text: this.text})// 构建消息内容,本人消息this.createContent(null, this.user.username, this.text)this.text = '';}}},createContent(remoteUser, nowUser, text) {  // 这个方法是用来将 json的聊天消息数据转换成 html的。let html// 当前用户消息if (nowUser) { // nowUser 表示是否显示当前用户发送的聊天消息,绿色气泡html = "<div class=\"el-row\" style=\"padding: 5px 0\">\n" +"  <div class=\"el-col el-col-22\" style=\"text-align: right; padding-right: 10px\">\n" +"    <div class=\"tip left\">" + text + "</div>\n" +"  </div>\n" +"  <div class=\"el-col el-col-2\">\n" +"  <span class=\"el-avatar el-avatar--circle\" style=\"height: 40px; width: 40px; line-height: 40px;\">\n" +"    <img src=\"https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png\" style=\"object-fit: cover;\">\n" +"  </span>\n" +"  </div>\n" +"</div>";} else if (remoteUser) {   // remoteUser表示远程用户聊天消息,蓝色的气泡html = "<div class=\"el-row\" style=\"padding: 5px 0\">\n" +"  <div class=\"el-col el-col-2\" style=\"text-align: right\">\n" +"  <span class=\"el-avatar el-avatar--circle\" style=\"height: 40px; width: 40px; line-height: 40px;\">\n" +"    <img src=\"https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png\" style=\"object-fit: cover;\">\n" +"  </span>\n" +"  </div>\n" +"  <div class=\"el-col el-col-22\" style=\"text-align: left; padding-left: 10px\">\n" +"    <div class=\"tip right\">" + text + "</div>\n" +"  </div>\n" +"</div>";}console.log(html)this.content += html;},init() {this.user = sessionStorage.getItem("user") ? JSON.parse(sessionStorage.getItem("user")) : {}let username = this.user.username;let _this = this;if (typeof (WebSocket) == "undefined") {console.log("您的浏览器不支持WebSocket");} else {console.log("您的浏览器支持WebSocket");let socketUrl = "ws://localhost:9090/imserver/" + username;if (socket != null) {socket.close();socket = null;}// 开启一个websocket服务socket = new WebSocket(socketUrl);//打开事件socket.onopen = function () {console.log("websocket已打开");};//  浏览器端收消息,获得从服务端发送过来的文本消息socket.onmessage = function (msg) {console.log("收到数据====" + msg.data)let data = JSON.parse(msg.data)  // 对收到的json数据进行解析, 类似这样的: {"users": [{"username": "zhang"},{ "username": "admin"}]}if (data.users) {  // 获取在线人员信息_this.users = data.users.filter(user => user.username !== username)  // 获取当前连接的所有用户信息,并且排除自身,自己不会出现在自己的聊天列表里} else {// 如果服务器端发送过来的json数据 不包含 users 这个key,那么发送过来的就是聊天文本json数据//  // {"from": "zhang", "text": "hello"}if (data.from === _this.chatUser) {_this.messages.push(data)// 构建消息内容_this.createContent(data.from, null, data.text)}}};//关闭事件socket.onclose = function () {console.log("websocket已关闭");};//发生了错误事件socket.onerror = function () {console.log("websocket发生了错误");}}}}
}</script><style>
.tip {color: white;text-align: center;border-radius: 10px;font-family: sans-serif;padding: 10px;width:auto;display:inline-block !important;display:inline;
}.right {background-color: deepskyblue;
}
.left {background-color: forestgreen;
}
</style>

Springboot + WebSocket 实现在线聊天相关推荐

  1. springboot+websocket构建在线聊天室(群聊+单聊)

    系列导读: 1.springboot+websocket构建在线聊天室(群聊+单聊) 2.Spring Boot WebSocket:单聊(实现思路) 3.Websocket Stomp+Rabbit ...

  2. springboot -- 整合websocket 实现在线聊天

    项目demo: 链接:https://pan.baidu.com/s/1xZtU-Rqc58m0-v397OW3hQ 提取码:01pt 复制这段内容后打开百度网盘手机App,操作更方便哦 websoc ...

  3. 【SpringBoot框架篇】18.使用Netty加websocket实现在线聊天功能

    文章目录 1.简介 2.最终功能实现的效果图 2.1.pc端 2.2.移动端 3.实战应用 3.1.引入依赖 3.2.配置文件 3.3.测试demo 3.3.1.消息内容实体类 3.3.2.处理请求的 ...

  4. SpringBoot与webSocket实现在线聊天室——实现私聊+群聊+聊天记录保存

    SpringBoot与webSocket实现在线聊天室--实现私聊+群聊+聊天记录保存 引用参考:原文章地址:https://blog.csdn.net/qq_41463655/article/det ...

  5. SpringBoot +WebSocket实现简单聊天室功能实例

    SpringBoot +WebSocket实现简单聊天室功能实例) 一.代码来源 二.依赖下载 三.数据库准备(sql) 数据库建表并插入sql 四.resources文件配置 application ...

  6. WebSocket实现在线聊天

    WebSocket实现在线聊天 前两天在公司接到一个需求,使用WebSocket实现微信扫码登陆,当时了解了一下WebSocket,都说WebSocket可以实现在线聊天,所以我自己也写了一个.(发个 ...

  7. Springboot+Vue实现在线聊天室项目-修改头像、添加好友接口的实现

    Springboot+Vue实现在线聊天室项目 该聊天室为大二上学期计算机网络大作业,并且是本人第一次使用vue实现前后端分离的项目,前端架构尚未熟悉可能会出现一些不妥之处,还请大佬们指出.(本文章写 ...

  8. SpringBoot 使用WebSocket打造在线聊天室(基于注解)

    点击上方"好好学java",选择"置顶公众号" 优秀学习资源.干货第一时间送达! 精彩内容 java实战练习项目教程 2018微服务资源springboot.s ...

  9. SpringBoot集成WebSocket实现在线聊天

    文章目录 前言 1.WebSocket引入 2.环境搭配 2.1.工程创建 2.2.依赖导入 2.3.配置类 3.具体实现 3.1.前置知识 3.2.数据封装 3.3.思路分析 3.4.服务构建 3. ...

最新文章

  1. Linux(CentOS)目录操作命令、文件操作命令、压缩解压缩命令
  2. AUC是什么?AUC的的意义是什么?AUC的判断分类器优劣标准是什么?AUC如何计算?
  3. 自习室网上预约系统设计_港澳居民“回乡证”出新规啦!新系统网上预约更方便!...
  4. 代码实例--请求的转发:RequestDispatcher对象处理请求的两个方法--forward和include
  5. UPS故障案例集(一)
  6. 条件 推导 迭代 并行
  7. 【Linux】一步一步学Linux——dig命令(160)
  8. 23种设计模式[5]:原型模式
  9. python数据处理随笔总结
  10. 最新全套Web前端视频教程
  11. 微信支付app支付怎么快速开通
  12. 一张图让你掌握测试人员能力模型及研发测试流程规范
  13. windbg加载符号
  14. 比较出名的几种美国主机
  15. iPad 变身做电脑显示器
  16. 【华人学者风采】黄维 西北工业大学
  17. JavaWeb教务管理系统(选课评教,框架SpringMvc+Hibernate)
  18. 使用 HSDB 查看Spring AOP产生的代理类
  19. 数字证书认证中心简介
  20. sql server 2008r2还原

热门文章

  1. 编写代码的软件用什么编写的_您到底是为谁编写代码?
  2. 用python根据当前星期,输出周一到周五的励志语句
  3. Python绘制世界疫情地图
  4. 简单模拟快递单号查询页面展示
  5. Job Statement
  6. 51单片机内存动态分配
  7. APM 新版电机电调校准
  8. 京东数科智能巡检机器人亮相中国数据中心设施论坛大会
  9. Spring Boot连接Oracle数据库驱动加载不上的问题(pom.xml引入ojdbc报错的问题)
  10. 如何将vectror<char>转换成string(C++)