专栏电商日志财经减肥爱情
投稿投诉
爱情常识
搭配分娩
减肥两性
孕期塑形
财经教案
论文美文
日志体育
养生学堂
电商科学
头戴业界
专栏星座
用品音乐

SpringBoot整合Socket实战案例,实现单点群发,

  作者:小目标青年
  来源:https:blog。csdn。netqq35387940本篇内容:
  后端前端简单HTML页面功能场景点:群发,所有人都能收到局部群发,部分人群都能收到单点推送,指定某个人的页面
  惯例,先看看本次实战示例项目结构:
  可以看到内容不多,也就是说,springboot整合socket,跟着我学,轻轻松松。
  不多说,开始:pom引入核心依赖dependenciesdependencygroupIdcom。alibabagroupIdfastjsonartifactIdversion1。2。75versiondependencydependencygroupIdcom。corundumstudio。socketiogroupIdnettysocketioartifactIdversion1。7。7versiondependencydependencygroupIdorg。springframework。bootgroupIdspringbootstarterwebartifactIddependencydependencygroupIdorg。springframework。bootgroupIdspringbootstartertestartifactIdscopetestscopedependencydependenciesyml加上配置项server:port:8089socketio:host:localhostport:8503maxFramePayloadLength:1048576maxHttpContentLength:1048576bossCount:1workCount:100allowCustomRequests:trueupgradeTimeout:10000pingTimeout:60000pingInterval:25000创建socket配置加载类MySocketConfig。javaimportcom。corundumstudio。socketio。SocketConfig;importcom。corundumstudio。socketio。SocketIOServer;importcom。corundumstudio。socketio。annotation。SpringAnnotationScanner;importorg。springframework。beans。factory。annotation。Value;importorg。springframework。context。annotation。Bean;importorg。springframework。context。annotation。Configuration;Author:JCcccDescription:Date:2022061321:50ConfigurationpublicclassMySocketConfig{Value({socketio。host})privateStringhost;Value({socketio。port})privateIntegerport;Value({socketio。bossCount})privateintbossCount;Value({socketio。workCount})privateintworkCount;Value({socketio。allowCustomRequests})privatebooleanallowCustomRequests;Value({socketio。upgradeTimeout})privateintupgradeTimeout;Value({socketio。pingTimeout})privateintpingTimeout;Value({socketio。pingInterval})privateintpingInterval;BeanpublicSocketIOServersocketIOServer(){SocketConfigsocketConfignewSocketConfig();socketConfig。setTcpNoDelay(true);socketConfig。setSoLinger(0);com。corundumstudio。socketio。Configurationconfignewcom。corundumstudio。socketio。Configuration();buildSocketConfig(socketConfig,config);returnnewSocketIOServer(config);}扫描nettysocketIo的注解(OnConnect、OnEvent等)BeanpublicSpringAnnotationScannerspringAnnotationScanner(){returnnewSpringAnnotationScanner(socketIOServer());}privatevoidbuildSocketConfig(SocketConfigsocketConfig,com。corundumstudio。socketio。Configurationconfig){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);}}创建消息实体MyMessage。javaAuthor:JCcccDate:202207239:05Description:publicclassMyMessage{privateStringtype;privateStringcontent;privateStringfrom;privateStringto;privateStringchannel;publicStringgetType(){returntype;}publicvoidsetType(Stringtype){this。typetype;}publicStringgetContent(){returncontent;}publicvoidsetContent(Stringcontent){this。contentcontent;}publicStringgetFrom(){returnfrom;}publicvoidsetFrom(Stringfrom){this。fromfrom;}publicStringgetTo(){returnto;}publicvoidsetTo(Stringto){this。toto;}publicStringgetChannel(){returnchannel;}publicvoidsetChannel(Stringchannel){this。channelchannel;}}
  代码简析:
  创建sockethandler负责记录客户端连接、下线
  MySocketHandler。javaimportcom。corundumstudio。socketio。SocketIOClient;importcom。corundumstudio。socketio。SocketIOServer;importcom。corundumstudio。socketio。annotation。OnConnect;importcom。corundumstudio。socketio。annotation。OnDisconnect;importcom。socket。mysocket。util。SocketUtil;importorg。springframework。beans。factory。annotation。Autowired;importjavax。annotation。PostConstruct;importjavax。annotation。PreDestroy;importorg。slf4j。Logger;importorg。slf4j。LoggerFactory;importorg。springframework。stereotype。Component;Author:JCcccDescription:Date:202262321:21ComponentpublicclassMySocketHandler{privatefinalLoggerlogLoggerFactory。getLogger(this。getClass());AutowiredprivateSocketIOServersocketIoServer;PostConstructprivatevoidstart(){try{socketIoServer。start();}catch(Exceptione){e。printStackTrace();}}PreDestroyprivatevoiddestroy(){try{socketIoServer。stop();}catch(Exceptione){e。printStackTrace();}}OnConnectpublicvoidconnect(SocketIOClientclient){StringuserFlagclient。getHandshakeData()。getSingleUrlParam(userFlag);SocketUtil。connectMap。put(userFlag,client);log。info(客户端userFlag:userFlag已连接);}OnDisconnectpublicvoidonDisconnect(SocketIOClientclient){StringuserFlagclient。getHandshakeData()。getSingleUrlParam(userFlag);log。info(客户端userFlag:userFlag断开连接);SocketUtil。connectMap。remove(userFlag,client);}}
  代码简析:
  封装的socket小函数
  SocketUtil。javaimportcom。alibaba。fastjson。JSON;importcom。alibaba。fastjson。JSONObject;importcom。corundumstudio。socketio。AckRequest;importcom。corundumstudio。socketio。SocketIOClient;importcom。corundumstudio。socketio。annotation。OnEvent;importorg。slf4j。Logger;importorg。slf4j。LoggerFactory;importorg。springframework。beans。factory。annotation。Autowired;importorg。springframework。stereotype。Component;importorg。springframework。util。StringUtils;importjava。util。Map;importjava。util。Objects;importjava。util。concurrent。ConcurrentHashMap;importjava。util。concurrent。ConcurrentMap;Author:JCcccDescription:Date:202262321:28ComponentpublicclassSocketUtil{privatefinalLoggerlogLoggerFactory。getLogger(this。getClass());暂且把用户客户端信息存在缓存publicstaticConcurrentMapString,SocketIOClientconnectMapnewConcurrentHashMap();OnEvent(valueCHANNELSYSTEM)publicvoidsystemDataListener(StringreceiveMsg){if(!StringUtils。hasLength(receiveMsg)){return;}JSONObjectmsgObject(JSONObject)JSON。parse(receiveMsg);StringuserFlagString。valueOf(msgObject。get(from));StringcontentString。valueOf(msgObject。get(content));log。info(收到用户:{}推送到系统频道的一条消息:{},userFlag,content);}publicvoidsendToAll(MapString,Objectmsg,StringsendChannel){if(connectMap。isEmpty()){return;}给在这个频道的每个客户端发消息for(Map。EntryString,SocketIOCliententry:connectMap。entrySet()){entry。getValue()。sendEvent(sendChannel,msg);}}publicvoidsendToOne(StringuserFlag,MapString,Objectmsg,StringsendChannel){拿出某个客户端信息SocketIOClientsocketClientgetSocketClient(userFlag);if(Objects。nonNull(socketClient)){单独给他发消息socketClient。sendEvent(sendChannel,msg);}}识别出客户端paramuserFlagreturnpublicSocketIOClientgetSocketClient(StringuserFlag){SocketIOClientclientnull;if(StringUtils。hasLength(userFlag)!connectMap。isEmpty()){for(Stringkey:connectMap。keySet()){if(userFlag。equals(key)){clientconnectMap。get(key);}}}returnclient;}}
  代码简析:
  写1个接口,模拟场景,前端页面调用后端接口,做消息推送
  TestController。javaimportcom。socket。mysocket。dto。MyMessage;importcom。socket。mysocket。util。SocketUtil;importorg。springframework。beans。factory。annotation。Autowired;importorg。springframework。web。bind。annotation。;importjava。util。HashMap;importjava。util。Map;Author:JCcccDescription:Date:2022061321:50RestControllerpublicclassTestController{publicfinalstaticStringSENDTYPEALLALL;publicfinalstaticStringSENDTYPEALONEALONE;AutowiredSocketUtilsocketUtil;PostMapping(testSendMsg)publicStringtestSendMsg(RequestBodyMyMessagemyMessage){MapString,ObjectmapnewHashMap();map。put(msg,myMessage。getContent());群发if(SENDTYPEALL。equals(myMessage。getType())){socketUtil。sendToAll(map,myMessage。getChannel());returnsuccess;}指定单人if(SENDTYPEALONE。equals(myMessage。getType())){socketUtil。sendToOne(myMessage。getTo(),map,myMessage。getChannel());returnsuccess;}returnfail;}}
  代码简析:
  好了,7步了。一切已经就绪了。前端简单页面
  接下来搞点前端HTML页面,玩一玩看看效果:
  第一个页面:
  TestClientStudentJC。html!DOCTYPEhtmlhtmlheadmetahttpequivContentTypecontenttexthtml;charsetutf8title我要连SOCKETtitlebasestylebody{padding:20px;}console{height:450px;overflow:auto;}。msgcolor{color:green;}styleheadbodylabal给系统推消息labalinputtypetextidcontentbuttonidbtnSendToSystemonclicksendSys();发送buttonbodyhtml
  代码简析:
  第二个页面,跟第一个基本一样,改一下用户唯一标识:
  TestClientStudentPU。html!DOCTYPEhtmlhtmlheadmetahttpequivContentTypecontenttexthtml;charsetutf8title我要连SOCKETtitlebasestylebody{padding:20px;}console{height:450px;overflow:auto;}。msgcolor{color:green;}styleheadbodylabal给系统推消息labalinputtypetextidcontentbuttonidbtnSendToSystemonclicksendSys();发送buttonbodyhtml
  OK,把项目跑起来,开始玩。
  直接访问客户端页面模拟学生JC连接socket:
  http:127。0。0。1:8089TestClientStudentJC。html
  可以看到服务端有监测到:
  这里监测的:
  先试试客户端给系统推消息先:
  可以看到服务端成功收到消息:
  这种方式,其实是因为服务监听了相关的频道:
  前端使用JS推到这个系统频道:
  ps:其实前端给服务端推消息,其实调用接口就可以。
  OK,进入核心应用场景1:群发,所有人都能收到
  系统给连上的客户端都推送消息
  {type:ALL,content:你们好,这是一条广播消息,全部人都能收到,channel:CHANNELSYSTEM}
  看看效果:
  然后是场景2,局部群发,部分人群都能收到
  其实也就是通过HTML客户端监听主题做区分就好:
  直接拉人口,升3:
  模拟2个学生,1个老师都连接上了socket
  当然,老师监听的是老师频道:
  然后我们模拟推送一下消息到指定的老师频道:
  {
  type:ALL,
  content:给老师们推一条消息!!!,
  channel:CHANNELTEACHER
  }
  最后一个场景,也就是单点推送,指定某个人收到
  模拟学生PU给学生JC推消息:
  可以看到在学生频道的JC正常收到了PU的消息:
  好了,该篇就到这吧。

开局1胜3负!上赛季东部第一的迈阿密热火到底怎么了?因为不是湖人篮网76人这样的网红球队,迈阿密热火在常规赛阶段受到的关注要小得多。所以上赛季他们53胜29负也没有被认为是冠军热门,季后赛一路杀进东决也惊到了不少人。所以新赛季,当他ETC在短期内不太可能升至23。10美元以上尽管查尔斯霍斯金森(CharlesHoskinson)对代币的Twitter帐户暂停发脾气,但仍增加了6。71。有争议的CardanoADA创始人在推特上发布了他对暂停的观察。他认72,梅西2球2助踢疯了!7场6球4助,连超C罗,贝利登顶双第一本轮欧冠比赛中大巴黎对阵海法马卡比的比赛也几乎是一场没有悬念的比赛。梅西在比赛第19分钟,就在禁区内冷静地完成了一记抽射打入了比赛的第一球。本场比赛也朝着惨案的方向发展开来了。随后名单公示!苏州拟表扬这些外企苏州是经济大市工业大市开放大市开放程度高开放成效好一直是苏州的鲜明特征近日苏州市人民政府办公室发布公告拟对在2021年度为我市经济发展作出积极贡献的部分外商及港澳台商投资企业予以通中甲积分榜!南通支云10绝杀险胜,四川九牛5球横扫北体大2022赛季中国足球甲级联赛,北京时间10月26日下午,有3场比赛精彩角逐。南通支云绝杀石家庄功夫,排名回归榜首,距离冲超成功更进一步。此外,苏州东吴战胜淄博蹴鞠,四川九牛5球横扫国乒适应场地训练!邱贻可帮孙颖莎捡球,樊振东首日轮空无需登场2022年新乡WTT世界杯决赛将在10月27日拉开大幕,在首个比赛日中,樊振东因为首轮轮空,将无需登场,国乒其余3男5女都将出战。今天上午,全体参赛的国乒队员来到比赛场地进行适应场京东11。11让低价更实在买手机使用消费券可打9折目前,内需依然是拉动我国经济增长的主要动力,消费是第一驱动力。今年上半年,从国家到地方密集出台政策举措激活消费市场,发放消费券成为重要方式之一。据数据统计,全国累计发放消费券超过百论厚道还得是问界M5,满眼的铝合金,续航1100km,25。98万起随着科技的发展,手机已经从最开始简单的通讯工具,变成了一个可以用来听音乐打游戏看电影收付款的智能终端。如今这样一幕在汽车行业中再次上演,在新能源浪潮的席卷下,传统的燃油车正慢慢退出28岁的你在干什么?知乎读到了清华树洞的故事或者平凡才是生活最真实的样子吧。每个人都以自己的方式在平凡日子里生活打拼。彷徨与无措,还是一点一点地成长起来了。虽然人生万象,各有悲欢。但好多人的实际行动告诉我们,美好生活固然没有俄开发基于石墨烯和玻璃的复合材料科技日报莫斯科10月25日电(记者董映璧)俄罗斯科研人员研发出借助激光生产出基于石墨烯和玻璃的导电且稳定的复合材料。这项技术的优点是成本低,石墨烯结构成为玻璃的一部分,而不仅仅是涂碧叶已泛黄秋风无情地摇着树秆,摇落碧叶已泛黄的脸。秋风飞扬轻轻地扫着,飘落凋零一地的残叶。岁月无痕掠过心上,是谁在时光里悲催落泪。摇落深知宋玉悲,风流儒雅亦吾师,怅望千秋一洒泪,萧条异代不同
为什么感觉越穷的家庭越不重视教育?1不是不重视,是没钱供孩子上学。2教育最后拼的是金钱是父母的格局。3教育很重要,谁都知道,但高等教育是需要钱的,越向上学,钱需要的越多。4初中三年拼中考,一半的学生上不了高中,拼的想不通,任天堂掌机贵在哪?有那钱买台手机不香吗?题主的问题描述这么说,说明你并没有理解游戏的本质,老山内说过一句话,游戏的本质就是好玩,好玩这个属性和画面和游戏是否大型真的没有什么直接关联,任天堂的掌机能独树一帜,肯定有它的特点拿到教师资格证,距离教师的编制还有多遥远?准确地说,拿到教师资格证,就相当于高三学生拿到了准考证,有了参加考编的资格。有的高三学生经过三天考试,一下子考上自己满意的学校。而有的学生却一而再,再而三地与自己想考的学校失之交臂科学家怎么知道光线是从多少光年外的星体上发出的?科学家怎么知道光线是从多少光年外的星体上发出的?看了网上一些帖子和评论,有这种想法的网友很多,他们根本不相信那些遥远的星光来自几十几百甚至几十亿上百亿光年以外,认为科学家们也是随意如何规划从西安去甘南九寨沟十天游的线路?我刚回来,我们走的路线是西安陇南九寨沟川主寺唐克朗木寺扎尕那夏河兰州西安。一路走来风景很美,不足之处就是应该直接从夏河到天水,再到西安,不用去兰州,因为兰州真的没啥好玩的,而且外地为什么飞船去到火星这么远的距离我们人类还能遥控它?是什么原理?如果说这个和小朋友玩的遥控玩具汽车一样也不要奇怪,对于美国推进实验室的勇气号和机遇号火星探测器来说无线电是对其进行遥控的主要方式。看看我们购买的民用无人机产品,其设置中也包含自动返为什么科学家费曼会说,世界上没有人真的懂得量子力学?因为我们至今都只能描述其现象,而无法了解其机制。连事物的成因都不明白,能说懂吗?而量子就是这么一群,我们还无法确定具体成因的事物,这就是费曼的原意。首先,没人懂量子。虽然1900年考电工证难度大吗?低压的有前途,还是高压的有前途?从事电力工作的小鲁班这几天正好在培训电工证,我来说说我的看法考电工难度大不大要从报考条件及考试内容两个方面来看。一电工证报考条件及资料要求。根据前几天的电工考试培训,培训的老师讲了怎样改掉小孩写作业慢的问题?孩子写作业慢可能有几方面原因1磨蹭孩子本身想去干别的,自己不愿意写作业,但是无奈家长催着写作业,万般无奈之下挪到书桌前,实际上还是身到心不到。这样的状态写作业效率很低,一般都是东摸联想激起的民愤,究竟是因为什么?联想为什么激起民愤?我想这不是偶然的,是多方面的甚至是深层次的原因引起的民愤,并不是某些简单的问题。笔者根据网上网民有根有据的爆料,个人认为,主要在于这两个方面引起民众的共愤。第一如何平衡美术教学中偏操作弱文化修养的问题?如何平衡美术教学中偏操作弱文化修养的问题?这个问题对我来讲,是个门外汉。我只能画一些简单的简笔画。偶尔,教孩子画简笔画蜡笔画,我也是依葫芦画瓢。以我的认知学美术的人,一定是爱好,并
友情链接:快好找快生活快百科快传网中准网文好找聚热点快软网