• 用Soket.io 实现给指定的人推送消息


    使用vue+springboot

    1.引入jar包

            <!--socket-io-->
            <dependency>
                <groupId>com.corundumstudio.socketio</groupId>
                <artifactId>netty-socketio</artifactId>
                <version>1.7.7</version>
            </dependency>
    

     2.配置类

    import com.corundumstudio.socketio.SocketConfig;
    import com.corundumstudio.socketio.SocketIOServer;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    
    /**
     * @author linzf
     * @since 2019-06-13
     * 类描述:socketIo的配置类
     */
    @Configuration
    public class SocketIoConfig {
    
        @Value("${socketio.host}")
        private String host;
    
        @Value("${socketio.port}")
        private Integer port;
    
        @Value("${socketio.bossCount}")
        private int bossCount;
    
        @Value("${socketio.workCount}")
        private int workCount;
    
        @Value("${socketio.allowCustomRequests}")
        private boolean allowCustomRequests;
    
        @Value("${socketio.upgradeTimeout}")
        private int upgradeTimeout;
    
        @Value("${socketio.pingTimeout}")
        private int pingTimeout;
    
        @Value("${socketio.pingInterval}")
        private int pingInterval;
    
        /**
         * 以下配置在上面的application.yml中已经注明
         * @return 实例化socketIo的服务对象
         */
        @Bean
        public SocketIOServer socketIOServer() {
            SocketConfig socketConfig = new SocketConfig();
            socketConfig.setTcpNoDelay(true);
            socketConfig.setSoLinger(0);
            com.corundumstudio.socketio.Configuration config = new com.corundumstudio.socketio.Configuration();
            config.setSocketConfig(socketConfig);
            config.setHostname(host);
            config.setPort(port);
            config.setBossThreads(bossCount);
            config.setWorkerThreads(workCount);
            config.setAllowCustomRequests(allowCustomRequests);
            config.setUpgradeTimeout(upgradeTimeout);
            config.setPingTimeout(pingTimeout);
            config.setPingInterval(pingInterval);
            return new SocketIOServer(config);
        }
    }
    

      3.接口类

    public interface SocketIoService {
    
        /**
         * 推送的事件
         */
        String PUSH_EVENT = "push_event";
    
        /**
         * 启动服务
         *
         * @throws Exception
         */
        void start() throws Exception;
    
        /**
         * 停止服务
         */
        void stop();
    
        /**
         * 推送信息
         *
         * @param pushMessage
         */
        void pushMessageToUser(PushMessage pushMessage);
    
    }
    

      4.接口实现类

    import com.corundumstudio.socketio.SocketIOClient;
    import com.corundumstudio.socketio.SocketIOServer;
    import com.qd.ks.config.PushMessage;
    import com.qd.ks.config.SocketIoService;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Service;
    
    import javax.annotation.PostConstruct;
    import javax.annotation.PreDestroy;
    import java.util.List;
    import java.util.Map;
    import java.util.concurrent.ConcurrentHashMap;
    
    /**
     * @author linzf
     * @since 2019-06-13
     * 类描述:socket的实现类
     */
    @Service(value = "socketIOService")
    public class SocketIoServiceImpl implements SocketIoService {
    
        /**
         * 用来存已连接的客户端
         */
        private static Map<String, SocketIOClient> clientMap = new ConcurrentHashMap<>();
    
        /**
         * socketIo的对象
         */
        @Autowired
        private SocketIOServer socketIOServer;
    
        /**
         * 功能描述:当前的service被初始化的时候执行以下的方法
         * @throws Exception
         */
        @PostConstruct
        private void autoStartUp() throws Exception {
            start();
        }
    
        /**
         * 功能描述:当我们的系统停止的时候关闭我们的socketIo
         * @throws Exception
         */
        @PreDestroy
        private void autoStop() throws Exception {
            stop();
        }
    
        @Override
        public void start() throws Exception {
            // 监听客户端连接
            socketIOServer.addConnectListener(client -> {
                /**
                 * 此处实现我们的socket的连接的用户的逻辑,此处我前端传的是loginUser这个参数,大家可以根据自己的情况来定义入参
                 */
                String loginUser = getParamsByClient(client).get("loginUserId").get(0);
                clientMap.put(loginUser, client);
            });
    
            // 监听客户端断开连接
            socketIOServer.addDisconnectListener(client -> {
                String loginUser = getParamsByClient(client).get("loginUserId").get(0);
                if (loginUser != null && !"".equals(loginUser)) {
                    clientMap.remove(loginUser);
                    client.disconnect();
                }
            });
    
            // 处理自定义的事件,与连接监听类似
            socketIOServer.addEventListener(PUSH_EVENT, PushMessage.class, (client, data, ackSender) -> {
                // TODO do something
            });
            socketIOServer.start();
    
        }
    
        @Override
        public void stop() {
            if (socketIOServer != null) {
                socketIOServer.stop();
                socketIOServer = null;
            }
        }
    
        /**
         * 功能描述:发送消息到前端
         * @param pushMessage 发送消息的实体
         */
        @Override
        public void pushMessageToUser(PushMessage pushMessage) {
            String loginUser=String.valueOf(pushMessage.getLoginUserId());
            if(clientMap.get(loginUser)!=null){
                clientMap.get(loginUser).sendEvent(PUSH_EVENT, pushMessage);
            }
    
        }
    
        /**
         * 此方法为获取client连接中的参数,可根据需求更改
         *
         * @param client
         * @return
         */
        private Map<String, List<String>> getParamsByClient(SocketIOClient client) {
            // 从请求的连接中拿出参数
            Map<String, List<String>> params = client.getHandshakeData().getUrlParams();
            return params;
        }
    }
    

      5.消息推送实体

    import lombok.Data;
    
    import java.util.Map;
    
    /**
     * @author linzf
     * @since 2019-06-13
     * 类描述:socket消息发送实体类
     */
    @Data
    public class PushMessage {
    
        /**
         * 当前登陆的用户
         */
        private Long loginUserId;
    
        /**
         * 推送的标题
         */
        private String title;
    
        /**
         * 推送的内容
         */
        private Map<String, Object> content;
    
        /**
         * 空的构造函数
         */
        public PushMessage() {
            super();
        }
    
        /**
         * 构造函数
         * @param loginUserId
         * @param title
         * @param content
         */
        public PushMessage(Long loginUserId,String title, Map<String, Object> content) {
            this.loginUserId = loginUserId;
            this.title = title;
            this.content = content;
        }
    }
    

      6.接受前端发送的请求

    import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
    import com.config.PushMessage;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.*;
    import java.util.HashMap;
    import java.util.List;
    import java.util.Map;
    
    @RestController
    @RequestMapping("interfaces/socket")
    public class SocketController {
    
        @Autowired
        private SocketIoService socketIoService;
        @PostMapping("send")
        public ResultJson sendMsg(@RequestParam("content") String content, @RequestParam("cardno")String cardno, @RequestParam("examId")String examId){
           socketIoService.pushMessageToUser(new PushMessage(Long.valueOf(cardno),"",content));//推送给指定的人 cardno,content消息
      
        return ResultJson.ok();
    } }

      

     

     7.vue中的实现

    安装socket.io-client
    

      

    8.

    import SocketIO from "socket.io-client"
    

    9.

      mounted() {
        let opts = {
          query: 'loginUserId='+this.userId
        }
        let socket = SocketIO.connect('http://192.168.0.111:9099', opts)
        socket.on('connect', function () {
          console.log('连接成功')
        })
        let reconnet = content=>{
        }
        socket.on('push_event', function (data) {
        //接收服务端传输的消息,然后调用reconnet方法进行数据展示 if(data.content!==""){ reconnet(data.content) } }) socket.on('disconnect', function () { console.log('已经下线') }) },
  • 相关阅读:
    gulp管理静态资源缓存
    你懂AI吗(1)
    Vue.js之render函数基础
    笑看女程序员征婚SQL,半夜巡逻民警突然对我大喊int类型占几个字节
    高吞吐量的分布式发布订阅消息系统Kafka之Producer源码分析
    Java并没有衰落.大家对它的认识才刚刚开始 Java8全新出发
    那些面试官必问的JAVA多线程和并发面试题及回答
    在阿里一位新员工是怎么一步步培养起来的
    Lambda表达式用法大比较: Scala和Java 8
    国内外程序员编程网站、博客,对学编程的你提供一点小小的帮助
  • 原文地址:https://www.cnblogs.com/liuna369-4369/p/14765389.html
Copyright © 2020-2023  润新知