WebSocket

文章介绍了WebSocket作为HTML5的一种双工通信协议,以及如何在SpringBoot应用中配置WebSocket实现聊天室功能。包括WebSocket事件、方法,以及创建WebSocket工具类、事件监听类,配置WebSocketConfig,并展示了前端Vue.js的交互代码。
摘要由CSDN通过智能技术生成

WebSocket

WebSocket 事HTML5开始提供的一种在单个TCP连接上进行的双工通讯的协议,可以在html页面直接使用。

WebSocket使用客户端何服务器之间的数据交换变得更加简单,允许服务端主动向客户端推动数据。在WebSocketAPI中,浏览器和服务器只需完成一次握手,两者之间直接可以建立持久性的连接,并进行双向数据传输。

1,WebSocket 事件

以下是WebSocket对象的相关事件

事件事件处理程序描述
openSocket.onopen建立连接时触发
messageSocket.onmessage客户端接受服务器数据时触发
errorSocket.onerror通讯发生错误是触发
closeSocket.onclose连接关闭是触发

2,WebSocket方法

以下是WebSocket对象的相关方法

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

3,WebSocket聊天室

3.1,引入websocket依赖

    <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-websocket</artifactId>
            <exclusions>
                <exclusion>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-starter-web</artifactId>
                </exclusion>
            </exclusions>
        </dependency>

3.2,编写websocket工具类

package com.woniu.util;

import javax.websocket.RemoteEndpoint;
import javax.websocket.Session;
import java.io.IOException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

public class WebSocketUtil {

    
    //放所有参与聊天的用户标识
    public static final Map<String, Session> messageMap = new ConcurrentHashMap<>();

    /**
    *单个消息
    */
    public static void send(Session session,String message){
        if (session != null){
            final RemoteEndpoint.Basic basic = session.getBasicRemote();
            if (basic != null){
                try {
                    basic.sendText(message);
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }
    /**
    * 全体发消息
    */
    public static void sendAll(String message){
        messageMap.forEach((userName,session) -> send(session,message));
    }

}

3.3,编写websocket事件类

package com.woniu.webscoket;

import com.woniu.util.WebSocketUtil;
import org.springframework.stereotype.Component;
import org.springframework.web.bind.annotation.RestController;

import javax.websocket.*;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import java.io.IOException;

@RestController
@ServerEndpoint("/WebSocketHandler/{userName}")
public class WebSocketHandler {
    @OnOpen
    public void openSession(@PathParam("userName") String userName, Session session){
        String message = "欢迎:"+userName +"加入群聊";
        WebSocketUtil.messageMap.put(userName,session);
        //给所有人发消息
        WebSocketUtil.sendAll(message);

    }
    @OnMessage
    public void onMessage(@PathParam("userName") String userName, String message){
        message = userName +":" +message;
        WebSocketUtil.sendAll(message);
    }


    @OnClose
    public void onClose(@PathParam("userName") String userName,Session session){
        WebSocketUtil.messageMap.remove(userName);
        WebSocketUtil.sendAll("用户:"+userName+"离开聊天室");

        try {
            session.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

3.4,编写WebSocketConfig 配置类, 并在启动类上加上 @EnableWebSocket 注解

@Configuration
public class WebSocketConfig {

    @Bean
    public ServerEndpointExporter serverEndpointExporter(){

        return new ServerEndpointExporter();
    }
}

3.5,如果是springsecurity框架需要给websocket配免拦截

    //忽略websocket拦截
    @Override
    public void configure(WebSecurity webSecurity) {
        webSecurity.ignoring().antMatchers(
                "/WebSocketHandler/**"
        );
    }

3.6,报错解决

​ 类似:ailed to register @ServerEndpoint class,在test类加上

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)

3.7,前端代码

<template>
  <div>

    <el-row >
      <el-col :span="6" :offset="3"> <p style="font-">1号聊天室</p></el-col>
    </el-row>
    <el-row>
      <el-col :span="12" :offset="1"> <textarea id="textarea" disabled="disabled" cols="50" rows="10"></textarea></el-col>
    </el-row>
    <el-row>
          <el-col :span="24">
            <span>  用户名:</span>
            <span>  <el-input type="text" v-model="userName"/></span>
            <span>  <el-button type="primary" @click="join">加入聊天室</el-button></span>
        </el-col>
    </el-row>

    <el-row>
      <el-col :span="4" :offset="1"> <el-input type="text" v-model="message"/> </el-col>
      <el-col :span="4" >
          <el-button type="success" @click="send">发送</el-button>
        </el-col>
    </el-row>

  
  </div>
</template>

<script>

export default {
  data(){
    return{
      url:'ws://192.168.2.70:8083/WebSocketHandler/',
      ws:'',
      userName:'',
      message:''
    }  
  
  },
  methods:{
    join(){
      if(this.userName == ""){
          alert("请输入您的大名!")
      }
      this.ws = new WebSocket(this.url + this.userName);

      this.ws.onopen = function(){
        console.log("连接成功!")
      }
      
      this.ws.onmessage = function(result){
    
        var textarea = document.getElementById("textarea");
        textarea.append(result.data+'\n');
        textarea.scrollTop = textarea.scrollHeight;
      }

      this.ws.onclose = function(){
        var textarea = document.getElementById("textarea");
        textarea.append('用户:'+this.userName+'离开聊天室 \n');  
        console.log("")
      }

    },
    send(){
      if(this.ws != null){
          this.ws.send(this.message);
          this.message = "";
      }
    }
  }
}
</script>

<style scoped>
p{
 font-size: 20px;
 color: red;
}
.el-row{
  margin:10px 5px;
}
span{
  float: left;
}
</style>

3.8,效果图

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值