在线观看不卡亚洲电影_亚洲妓女99综合网_91青青青亚洲娱乐在线观看_日韩无码高清综合久久

鍍金池/ 問(wèn)答/Java  HTML/ springboot websocket convertAndSendToUse

springboot websocket convertAndSendToUser這個(gè)方法中的user到底是從哪里來(lái)的?

我找了一天,回家才能上的google,找到了一個(gè)差不多的答案,但是我覺(jué)得也沒(méi)能說(shuō)明白,這個(gè)user到底是怎么來(lái)的,
我英文不好,用的翻譯軟件,可能這是導(dǎo)致我看不明白的原因

https://stackoverflow.com/que...

所以希望能有人給解答一下

convertAndSendToUser(username, destination, message)API。
它接受一個(gè)字符串用戶名,這意味著如果我們以某種方式為每個(gè)連接設(shè)置唯一的用戶名,我們應(yīng)該能夠發(fā)送消息給訂閱主題的特定用戶。

不明白的是,這個(gè)用戶名是從哪里來(lái)的?

該用戶名是java.security.Principal類的實(shí)例。但是這個(gè)Principal對(duì)象是如何獲取的,是如何存入spring的,我如何根據(jù)這個(gè)用戶進(jìn)行一些業(yè)務(wù)判斷,來(lái)決定是否發(fā)送消息,如果當(dāng)前用戶是A則給B發(fā)送消息,這樣的需求如何實(shí)現(xiàn)?

回答
編輯回答
奧特蛋

第一步,寫一個(gè)類實(shí)現(xiàn)Principal
例如:

public class WebsocketUserVO implements Principal {
    private  String id;
    public WebsocketUserVO(String id) {
        this.id = id;
    }

    @Override
    public String getName() {
        return id;
    }
}

第二步,在創(chuàng)建連接的時(shí)候,設(shè)置用戶

public class WebsocketUserInterceptor extends ChannelInterceptorAdapter {

    @Autowired
    private WebSocketServ webSocketServ;

    @Autowired
    private SimpUserRegistry userRegistry;

    @SuppressWarnings("rawtypes")
    @Override
    public Message<?> preSend(Message<?> message, MessageChannel channel) {
        StompHeaderAccessor accessor = MessageHeaderAccessor.getAccessor(message, StompHeaderAccessor.class);
        if (StompCommand.CONNECT.equals(accessor.getCommand())) {
            System.out.println("連接success");
            Object raw = message.getHeaders().get(SimpMessageHeaderAccessor.NATIVE_HEADERS);
            if (raw instanceof Map) {
                Object name = ((Map) raw).get("name");
                if (name instanceof LinkedList) {
                    String id = ((LinkedList) name).get(0).toString();
                    //設(shè)置當(dāng)前訪問(wèn)器的認(rèn)證用戶
                    accessor.setUser(new WebsocketUserVO(id));
                    webSocketServ.pushOnlineUser(id);
                }
            }
        } else if (StompCommand.DISCONNECT.equals(accessor.getCommand())) {
            //點(diǎn)擊斷開連接,這里會(huì)執(zhí)行兩次,第二次執(zhí)行的時(shí)候,message.getHeaders.size()=5,第一次是6。直接關(guān)閉瀏覽器,只會(huì)執(zhí)行一次,size是5。
            System.out.println("斷開連接");
            WebsocketUserVO vo = (WebsocketUserVO) message.getHeaders().get(SimpMessageHeaderAccessor.USER_HEADER);

            //  如果同時(shí)發(fā)生兩個(gè)連接,只有都斷開才能叫做不在線
            if (message.getHeaders().size() == 5&&StringUtils.isBlank(userRegistry.getUser(vo.getName()))) {
                webSocketServ.removeOnlineUser(vo.getName());
            }
        }
        return message;
    }

}

第三步,發(fā)送消息

   messagingTemplate.convertAndSendToUser(userId,url, MVCUtil.success(object));
   這里的userId,就是WebsocketUserVO里面getName返回的值

2018年9月5日 18:47