最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

SpringBoot如何添加WebSocket的方法示例

 更新時間:2020年10月30日 09:42:53   作者:T_Antry  
這篇文章主要介紹了SpringBoot如何添加WebSocket的方法示例,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧

一、WebSocket介紹

網站上的即時通訊是很常見的,比如網頁的QQ,聊天系統(tǒng)等。按照以往的技術能力通常是采用輪詢、Comet技術解決。
HTTP協議是非持久化的,單向的網絡協議,在建立連接后只允許瀏覽器向服務器發(fā)出請求后,服務器才能返回相應的數據。當需要即時通訊時,通過輪詢在特定的時間間隔(如1秒),由瀏覽器向服務器發(fā)送Request請求,然后將最新的數據返回給瀏覽器。這樣的方法最明顯的缺點就是需要不斷的發(fā)送請求,而且通常HTTP request的Header是非常長的,為了傳輸一個很小的數據 需要付出巨大的代價,是很不合算的,占用了很多的寬帶。
缺點:會導致過多不必要的請求,浪費流量和服務器資源,每一次請求、應答,都浪費了一定流量在相同的頭部信息上
然而WebSocket的出現可以彌補這一缺點。在WebSocket中,只需要服務器和瀏覽器通過HTTP協議進行一個握手的動作,然后單獨建立一條TCP的通信通道進行數據的傳送。

二、WebSocket運行機制

WebSocket 是 HTML5 一種新的協議,也是一個典型的應用層協議。它實現了瀏覽器與服務器全雙工通信,能更好的節(jié)省服務器資源和帶寬并達到實時通訊,它建立在 TCP 之上,同 HTTP 一樣通過 TCP 來傳輸數據,但是它和 HTTP 最大不同是:

WebSocket 是一種雙向通信協議,在建立連接后,WebSocket 服務器和 Browser/Client Agent 都能主動的向對方發(fā)送或接收數據,就像 Socket 一樣;

WebSocket 需要類似 TCP 的客戶端和服務器端通過握手連接,連接成功后才能相互通信。
非 WebSocket 模式傳統(tǒng) HTTP 客戶端與服務器的交互如下圖所示:


使用 WebSocket 模式客戶端與服務器的交互如下圖:

在這里插入圖片描述

三、WebSocket實現

這里通過一個簡單的聊天例程,實現spring boot +websocket代碼的演示。
引入maven

<!-- websocket -->
    <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-websocket</artifactId>
      <version>2.3.4.RELEASE</version>
    </dependency>

配置類WebConfig

package org.antry.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.socket.server.standard.ServerEndpointExporter;

/**
 * @ClassName WebSocketConfig
 * @Description TODO
 * @Autor TT
 * @Date 2020/10/9 23:00
 * @Version 1.0
 */
@Configuration
public class WebSocketConfig {

  @Bean
  public ServerEndpointExporter serverEndpointExporter() {
    return new ServerEndpointExporter();
  }

}

WebSocket類
在這個類里,有一個集合,用來存放所有連接。
當有新的連接進來時,在onOpen()方法中,我們每個連接都會存下對應id作為標識。假設這個id已經存過,則會關閉此連接,防止同一個id多處登錄。
連接斷開時,在onClose()方法中,將此連接移出集合。
當有新的消息發(fā)送過來時,會去遍歷連接,找到對應接收人id的連接,然后把消息推送給接收人。

package org.antry.websocket;
import org.springframework.stereotype.Component;
import javax.websocket.OnClose;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import java.io.IOException;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.atomic.AtomicInteger;
/**
 * @ClassName MyWebsocket
 * @Description TODO
 * @Autor TT
 * @Date 2020/10/10 11:02
 * @Version 1.0
 */
@ServerEndpoint(value = "/websocket/{user}")
@Component
public class MyWebsocket {
  // 通過類似GET請求方式傳遞參數的方法(服務端采用第二種方法"WebSocketHandler"實現)
//  websocket = new WebSocket("ws://127.0.0.1:18080/testWebsocket?id=23&name=Lebron");
  /**
   * 在線人數
   */
  public static AtomicInteger onlineNumber = new AtomicInteger(0);

  /**
   * 所有的對象,每次連接建立,都會將我們自己定義的MyWebsocket存放到List中,
   */
  public static List<MyWebsocket> webSockets = new CopyOnWriteArrayList<MyWebsocket>();

  /**
   * 會話,與某個客戶端的連接會話,需要通過它來給客戶端發(fā)送數據
   */
  private Session session;

  /**
   * 每個會話的用戶
   */
  private String user;
  /**
   * 建立連接
   *
   * @param session
   */
  @OnOpen
  public void onOpen(Session session, @PathParam("user") String user) {
    System.err.println(user);
    if (user == null || "".equals(user)) {
      try {
        session.close();
      } catch (IOException e) {
        e.printStackTrace();
      }
      return;
    }
    onlineNumber.incrementAndGet();
    for (MyWebsocket MyWebsocket : webSockets) {
      if (user.equals(MyWebsocket.user)) {
        try {
          session.close();
        } catch (IOException e) {
          e.printStackTrace();
        }

        return;
      }
    }
    this.session = session;
    this.user = user;
    webSockets.add(this);
  }
  /**
   * 連接關閉
   */
  @OnClose
  public void onClose() {
    onlineNumber.decrementAndGet();
    webSockets.remove(this);
  }
  /**
   * 收到客戶端的消息
   *
   * @param message 消息
   * @param session 會話
   */
  @OnMessage
  public void onMessage(String message, Session session, @PathParam("user") String user) {
    System.err.println(message);
    String[] strArr = message.split("~");
    pushMessage(user,strArr[0],strArr[1]);
  }
  /**
   * 發(fā)送消息
   *
   * @param message 消息
   */
  public void sendMessage(String message) {
    try {
      session.getBasicRemote().sendText(message);
    } catch (IOException e) {
      e.printStackTrace();
    }
  }

  /**
   * 消息推送
   *
   * @param message
   * @param uuid  uuid為空則推送全部人員
   */
  public static void pushMessage(String user, String message, String uuid) {

    if (uuid == null || "".equals(uuid)) {
      for (MyWebsocket MyWebsocket : webSockets) {
        MyWebsocket.sendMessage(user + ":" + message);
      }
    } else {
      for (MyWebsocket MyWebsocket : webSockets) {
        if (uuid.equals(MyWebsocket.user)) {
          MyWebsocket.sendMessage(message);
        }
      }
    }
  }
}

兩個簡單的前端頁面,他們的不同是,接收id和發(fā)送id不同。
testOne.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>聊天窗口1</title>

  <meta name="viewport" content="width=device-width, initial-scale=1">
  <link href="public/dist/lib/uploader/zui.uploader.min.css" rel="external nofollow" rel="external nofollow" rel="stylesheet">

</head>
<body>
  <div>
    <div class="input-group">
      <input type="text" class="form-control" id="msg">
      <span class="input-group-btn">
    <button class="btn btn-default" type="button" onclick="send()">發(fā)送</button>
 </span>
    </div>
  </div>

<script src="public/dist/lib/jquery/jquery.js"></script>
<script src="public/dist/js/zui.min.js"></script>
<script src="public/layer/layer.js"></script>
<script src="public/js/function.js"></script>
<script src="public/js/testOne.js"></script>
</body>
</html>

testOne.js

var websocket = null;
var sendId = 0;
var receiveId = 1;
//---------------------------
/**
 * 初始化websocket
 * @param id
 */
doInit(sendId)
function doInit(sendId){
  if ('WebSocket' in window) {
    websocket = new WebSocket("ws:localhost:10086/websocket/" + sendId);
  } else {
    alert("瀏覽器不支持");
  }
  websocket.onopen = function () {
    addMessage("webscoket已經連接成功");
  };
  websocket.onclose = function () {
    addMessage("webscoket連接失敗");
  };
  websocket.onmessage = function (event) {
    alert("收到消息:"+event.data);
  };
  websocket.onerror = function () {
    addMessage("webscoket連接失敗");
  };
}
/**
 * 發(fā)送一條消息
 */
function send(){
  websocket.send(value('msg')+"~"+receiveId);
}
/**
 * 測試打印調試信息用
 * @param msg
 */
function addMessage(msg) {
  console.log(msg)
}

testTwo.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>聊天窗口2</title>
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <link href="public/dist/lib/uploader/zui.uploader.min.css" rel="external nofollow" rel="external nofollow" rel="stylesheet">
</head>
<body>
<div>
  <div class="input-group">
    <input type="text" class="form-control" id="msg">
    <span class="input-group-btn">
    <button class="btn btn-default" type="button" onclick="send()">發(fā)送</button>
 </span>
  </div>
</div>

<script src="public/dist/lib/jquery/jquery.js"></script>
<script src="public/dist/js/zui.min.js"></script>
<script src="public/layer/layer.js"></script>
<script src="public/js/function.js"></script>
<script src="public/js/testTwo.js"></script>
</body>
</html>

testTwo.js

var websocket = null;
var sendId = 1;
var receiveId = 0;
//---------------------------
/**
 * 初始化websocket
 * @param id
 */
doInit(sendId)
function doInit(receiveId){
  if ('WebSocket' in window) {
    websocket = new WebSocket("ws:localhost:10086/websocket/" + sendId);
  } else {
    alert("瀏覽器不支持");
  }
  websocket.onopen = function () {
    addMessage("webscoket已經連接成功");
  };
  websocket.onclose = function () {
    addMessage("webscoket連接失敗");
  };
  websocket.onmessage = function (event) {
    alert("收到消息:"+event.data);
  };
  websocket.onerror = function () {
    addMessage("webscoket連接失敗");
  };
}
/**
 * 發(fā)送一條消息
 */
function send(){
  websocket.send(value('msg')+"~"+receiveId);
}
/**
 * 測試打印調試信息用
 * @param msg
 */
function addMessage(msg) {
  console.log(msg)
}

分別用兩個瀏覽器,打開這兩個頁面進行訪問。結果如下

在這里插入圖片描述

在這里插入圖片描述

到此這篇關于SpringBoot如何添加WebSocket的方法示例的文章就介紹到這了,更多相關SpringBoot添加WebSocket內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • Java實現導出pdf格式文件的示例代碼

    Java實現導出pdf格式文件的示例代碼

    這篇文章主要為大家詳細介紹了Java實現導出pdf格式文件的相關知識,文中的示例代碼講解詳細,感興趣的小伙伴可以跟隨小編一起學習一下
    2024-02-02
  • Java for循環(huán)幾種寫法整理

    Java for循環(huán)幾種寫法整理

    這篇文章主要介紹了Java for循環(huán)幾種寫法整理的相關資料,需要的朋友可以參考下
    2017-02-02
  • Spring Security+JWT實現認證與授權的實現

    Spring Security+JWT實現認證與授權的實現

    本文主要介紹了Spring Security+JWT實現認證與授權的實現,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2022-04-04
  • jpa 使用@Column來定義字段類型

    jpa 使用@Column來定義字段類型

    這篇文章主要介紹了jpa使用@Column來定義字段類型,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-11-11
  • SpringBoot中的bean管理示例詳解

    SpringBoot中的bean管理示例詳解

    這篇文章主要介紹了SpringBoot中的bean管理,本文結合示例代碼給大家講解的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2023-06-06
  • Java常量池知識點總結

    Java常量池知識點總結

    本篇文章給大家通過理論原理等方便徹底分析了Java常量池的相關知識,有興趣的朋友閱讀學習下吧。
    2017-12-12
  • postman?如何實現傳遞?ArrayList?給后臺

    postman?如何實現傳遞?ArrayList?給后臺

    這篇文章主要介紹了postman?如何實現傳遞?ArrayList給后臺,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-12-12
  • JavaFx實現拼圖游戲

    JavaFx實現拼圖游戲

    這篇文章主要為大家詳細介紹了JavaFx實現拼圖游戲,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-09-09
  • IntelliJ IDEA中properties文件顯示亂碼問題的解決辦法

    IntelliJ IDEA中properties文件顯示亂碼問題的解決辦法

    今天小編就為大家分享一篇關于IntelliJ IDEA中properties文件顯示亂碼問題的解決辦法,小編覺得內容挺不錯的,現在分享給大家,具有很好的參考價值,需要的朋友一起跟隨小編來看看吧
    2018-10-10
  • Springboot如何使用logback實現多環(huán)境配置?

    Springboot如何使用logback實現多環(huán)境配置?

    上一篇文章中老顧介紹了logback基本配置,了解了日志配置的基本方式.我們平時在系統(tǒng)開發(fā)時,開發(fā)環(huán)境與生產環(huán)境的日志配置會不一樣;那今天老顧就跟大家介紹一下如何實現多環(huán)境配置,需要的朋友可以參考下
    2021-06-06

最新評論

昌邑市| 汕头市| 淮南市| 遂宁市| 武城县| 孝义市| 云霄县| 曲松县| 邵阳县| 辽宁省| 儋州市| 禹州市| 绵竹市| 辽阳市| 景德镇市| 望江县| 通河县| 宝丰县| 封丘县| 涿州市| 永昌县| 万宁市| 财经| 普宁市| 高青县| 花莲市| 交口县| 安阳县| 渭源县| 洛浦县| 石狮市| 盐边县| 周宁县| 合江县| 观塘区| 同心县| 伊川县| 绥棱县| 全椒县| 长汀县| 兖州市|