websocket整理

作者: 瑜骐 | 来源:发表于2018-09-30 18:28 被阅读28次

简介

websocket简介

HTML5 WebSocket设计出来的目的就是取代轮询和长连接,使客户端浏览器具备像C/S框架下桌面系统的即时通讯能力,实现了浏览器和服务器全双工通信,建立在TCP之上,虽然WebSocket和HTTP一样通过TCP来传输数据,但WebSocket可以主动的向对方发送或接收数据,就像Socket一样;并且WebSocket需要类似TCP的客户端和服务端通过握手连接,连接成功后才能互相通信。双向通信、事件驱动、异步、使用ws或wss协议的客户端能够真正实现意义上的推送功能。

stomp简介

STOMP is the Simple (or Streaming) Text Orientated Messaging Protocol.STOMP provides an interoperable wire format so that STOMP clients can communicate with any STOMP message broker to provide easy and widespread messaging interoperability among many languages, platforms and brokers.

整体流程

客户端和mq对应的交互流程

客户端浏览器对应的每一个tab页面链接对应的服务端endPoint,其内部的处理过程,实际上是经过socket http TCP握手建立链接,然后使用协议websocket 和stomp进行通信。

整体交互流程

主要源码如下:
WebSocketConfig.java源码

import org.springframework.context.annotation.Configuration;
import org.springframework.messaging.simp.config.MessageBrokerRegistry;
import org.springframework.web.socket.config.annotation.AbstractWebSocketMessageBrokerConfigurer;
import org.springframework.web.socket.config.annotation.EnableWebSocketMessageBroker;
import org.springframework.web.socket.config.annotation.StompEndpointRegistry;

@Configuration
@EnableWebSocketMessageBroker
public class WebSocketConfig extends AbstractWebSocketMessageBrokerConfigurer {

    @Override
    public void configureMessageBroker(MessageBrokerRegistry config) {
        config
            .setApplicationDestinationPrefixes("/app") // 客户端请求的路径中要包括app
            .enableStompBrokerRelay("/topic") // 转换对应的路径前缀
            .setRelayHost("localhost")
            .setRelayPort(61613)  // 这个转发默认端口
            .setClientLogin("guest")
            .setClientPasscode("guest");
    }

    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/websocket-app").withSockJS(); // 定义站点
    }

}

MessagingController.java 如下:

import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.messaging.handler.annotation.SendTo;
import org.springframework.stereotype.Controller;

@Controller
public class MessagingController {

    @MessageMapping("/message")  // 客户端请求完整路径是/app/message
    @SendTo("/topic/mural") // 转发的前缀包括topic,mural为路由规则
    public String send(String message) throws Exception {
        return message;
    }

}

WebSocketController.js 如下:

class WebSocketController {
    
    constructor() {
        this._onConnected = this._onConnected.bind(this);
    }
    
    _onConnected(frame) {
        this.setConnected(true);
        console.log('Connected: ' + frame);
        this.stompClient.subscribe('/topic/mural', this.showMessage); // 订阅转发
    }
    
    setConnected(connected) {
        document.getElementById('connect').disabled = connected;
        document.getElementById('disconnect').disabled = !connected;
        document.getElementById('mural').style.visibility = connected ? 'visible' : 'hidden';
        document.getElementById('response').innerHTML = '';     
    }
    
    connect() {
        var socket = new SockJS('/websocket-app'); // 连接站点
        this.stompClient = Stomp.over(socket);  
        this.stompClient.connect({}, this._onConnected);
    }

    disconnect() {
        if(this.stompClient != null) {
            this.stompClient.disconnect();
        }
        this.setConnected(false);
        console.log("Disconnected");
    }
    
    sendMessage() {
        var message = document.getElementById('text').value;
        this.stompClient.send("/app/message", {}, message); // 请求路径为app/message 
    }
    
    showMessage(message) {
        var response = document.getElementById('response');
        var p = document.createElement('p');
        p.style.wordWrap = 'break-word';
        p.appendChild(document.createTextNode(message.body));
        response.appendChild(p);
    }

}
var webSocket = new WebSocketController();

index.html 如下:

<html>
    <head>
        <title>Spring WebSocket Messaging</title>
        <script src="/webjars/sockjs-client/sockjs.min.js"></script>
        <script src="/webjars/stomp-websocket/stomp.min.js"></script>
        <script src="/WebSocketController.js"></script>
    </head>
    <body onload="webSocket.disconnect()">
        <div>
            <div>
                <button id="connect" onclick="webSocket.connect();">Connect</button>
                <button id="disconnect" disabled="disabled" onclick="webSocket.disconnect();">
                    Disconnect
                </button>
            </div>
            <br />
            <div id="mural">
                <input type="text" id="text" placeholder="Write a message..."/>
                <button id="sendMessage" onclick="webSocket.sendMessage();">Send</button>
                <p id="response"></p>
            </div>
        </div> 
    </body>
</html>

springboot websocket rabbitmq源码

参见:http://djeison.me/2017/11/04/spring-websocket-rabbitmq/

运行截图显示

注意点

第一步要在rabbitmq 上运行 rabbitmq_stomp,对应的命令如下:

>rabbitmq-plugins enable rabbitmq_stomp

rabbitmq web管理后台对应的截图

rabbitmq connection 截图
rabbitmq channel 截图
rabbitmq exchange截图
rabbitmq queue截图
rabbitmq 路由key mural

参考

  1. Spring WebSocket on RabbitM
  2. Stomp

相关文章

  • Websocket相关知识整理

    Websocket 协议格式说明 最近整理项目中关于websocket中的部分,由于之前代码中websocket的...

  • websocket整理

    简介 websocket简介 HTML5 WebSocket设计出来的目的就是取代轮询和长连接,使客户端浏览器具备...

  • 整理 Netty WebSocket

    文前说明作为码农中的一员,需要不断的学习,我工作之余将一些分析总结和学习笔记写成博客与大家一起交流,也希望采用这种...

  • 井通Websocket命令总结

    下面websocket命令是经过整理的,测试通过的,大家可以打开websocket测试工具试试。 0、Websoc...

  • socket与WebSocket协议

    本文整理了对Socket与WebSocket协议的理解,基于WebSocket聊天室的实现及实现原理,Worker...

  • 【网络协议笔记】第五层:应用层(Application)HTTP

    这一篇整理了WebSocket、FTP、RESTful、SMTP、IMAP、POP等协议。 1.ARP/RARP/...

  • websocket+netty概念整理

  • websocket和轮询的整理

    1.WebSocket的应用场景和特点: 1. 应用场景: WebSocket是一种在单个TCP连接上进行全双工通...

  • WebSocket

    WebSocket Introduction WebSocket general:阮一峰的WebSocket 教程...

  • 2020-04-03

    ## webSocket初探 ## 目录 - 为什么WebSocket - 什么是WebSocket - WebS...

网友评论

    本文标题:websocket整理

    本文链接:https://www.haomeiwen.com/subject/eazioftx.html