spring boot websocket

1.消息广播

/**
 * 广播模式
 */
@Configuration
@EnableWebSocketMessageBroker
public class WebSocketBroadcastConfig extends AbstractWebSocketMessageBrokerConfigurer {

    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/endpointWisely").withSockJS();
    }

    @Override
    public void configureMessageBroker(MessageBrokerRegistry registry) {
        registry.enableSimpleBroker("/topic");
    }
}
/**
 * 广播模式
 */
@Controller
public class WebSocketBroadcastController {

    @Autowired
    private SimpMessagingTemplate template;

    @MessageMapping("/welcome")//浏览器发送请求通过@messageMapping 映射/welcome 这个地址。
    //TODO 1.第一种方式通过注解SendTo发送消息
    //@SendTo("/topic/getResponse")//服务器端有消息时,会订阅@SendTo 中的路径的浏览器发送消息。
    public Response say(Message message) throws Exception {
        Thread.sleep(1000);
        Response response = new Response("Welcome, " + message.getName() + "!");
        //TODO 2.第二种方式通过SimpMessagingTemplate 发送
        template.convertAndSend("/topic/getResponse", response);
        return response;
    }
}
只要订阅/topic/getResponse的客户端都能收到消息
订阅消息:
function connect() {
    var socket = new SockJS('/endpointWisely'); //链接SockJS endpoint 名称为"/endpointWisely"
    stompClient = Stomp.over(socket);//使用stomp子协议的WebSocket 客户端
    stompClient.connect({}, function (frame) {//链接Web Socket的服务端。
        setConnected(true);
        console.log('Connected: ' + frame);
        stompClient.subscribe('/topic/getResponse', function (respnose) { //订阅/topic/getResponse 目标发送的消息。这个是在控制器的@SendTo中定义的。
            showResponse(JSON.parse(respnose.body).responseMessage);
        });
    });
}
发送消息:
//通过stompClient.send /welcome 目标 发送消息,这个是在控制器的@messageMapping 中定义的。
stompClient.send("/welcome", {}, JSON.stringify({'name': name}));

2.点对点模式

/**
 * 点对点模式
 */
@Configuration
@EnableWebSocketMessageBroker
public class WebSocketP2PConfig extends AbstractWebSocketMessageBrokerConfigurer {
    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/endpointChat").withSockJS();
    }

    @Override
    public void configureMessageBroker(MessageBrokerRegistry registry) {
        //点对点式增加消息代理
        registry.enableSimpleBroker("/user");
        //默认前缀就是/user
        registry.setUserDestinationPrefix("/user");
    }
}
/**
 * 点对点模式
 */
@Controller
public class WebSocketP2PController {

    @Autowired
    private SimpMessagingTemplate template;

    @MessageMapping("/chat")
    public void handlerChat(Message message) {
        template.convertAndSendToUser(message.getName(), "/queue/notifications"
                , "-sendTo:"
                        + message.getName());
    }
}
订阅消息:
var sock = new SockJS("/endpointChat");
var stomp = Stomp.over(sock);
stomp.connect({}, function(frame) {

    /**
 订阅了/user/queue/notifications 发送的消息,这里雨在控制器的 convertAndSendToUser 定义的地址保持一致,

     *  这里多用了一个/user,并且这个user 是必须的,使用user 才会发送消息到指定的用户。     *  */
    stomp.subscribe("/user/chat2/queue/notifications", handleNotification);
});

3.总结

广播模式和点对点模式实现是完全一样。如果有多个客户端订阅一个destination,那就是广播了,如果只有一个用户订阅了 destination,那就是点对点。
@Override
public void convertAndSendToUser(String user, String destination, Object payload, Map<String, Object> headers,
      MessagePostProcessor postProcessor) throws MessagingException {

   Assert.notNull(user, "User must not be null");
   user = StringUtils.replace(user, "/", "%2F");
   super.convertAndSend(this.destinationPrefix + user + destination, payload, headers, postProcessor);
}
默认前缀
private String destinationPrefix = "/user/";

最终还是调用convertAndSend方法。
@Override
public void convertAndSend(D destination, Object payload, Map<String, Object> headers,
      MessagePostProcessor postProcessor) throws MessagingException {

   Message<?> message = doConvert(payload, headers, postProcessor);
   send(destination, message);
}

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值