HTML5 WebSocket+Tomcat8实现真●Web版即时聊天室(单人+多人)
2015-10-13 13:42
686 查看
之前做了一篇tomcat7的websocket聊天室,这是基于tomcat7和jdk1.7下的,有的项目是在tomcat8下的,这个时候就会有问题,因为8下面不支持那种写法,它是以注解的方式来实现websocket,参照HTML5 WebSocket+Tomcat实现Web版即时聊天室 ,下面就介绍一下如何在8下面实现聊天室,多人加单人!
最重要的是获取每个用户登录的session,这里的session是HttpSession,websocket自带了session,但在实际项目中我们可能只用到第一种,如何在8下面获取呢?
这里要写个类,来继承ServerEndpointConfig.Configurator:
再在websocket服务里添加这个配置,就像这样
我将两个HttpSession放在一个map里,由用户进入,就put进去,如下
代码为
前台的页面没有改变,经测试,可行!!!
代码我已经上传到网上,源码下载
最重要的是获取每个用户登录的session,这里的session是HttpSession,websocket自带了session,但在实际项目中我们可能只用到第一种,如何在8下面获取呢?
这里要写个类,来继承ServerEndpointConfig.Configurator:
package com.socket; import javax.websocket.HandshakeResponse; import javax.websocket.server.HandshakeRequest; import javax.websocket.server.ServerEndpointConfig; import javax.servlet.http.HttpSession; public class GetHttpSessionConfigurator extends ServerEndpointConfig.Configurator { @Override public void modifyHandshake(ServerEndpointConfig config,HandshakeRequest request, HandshakeResponse response) { HttpSession httpSession = (HttpSession) request.getHttpSession(); config.getUserProperties().put(HttpSession.class.getName(), httpSession); } }
再在websocket服务里添加这个配置,就像这样
@ServerEndpoint(value = "/websocket",configurator=GetHttpSessionConfigurator.class)
我将两个HttpSession放在一个map里,由用户进入,就put进去,如下
private static final Map<HttpSession,ChatServlet> onlineUsers = new HashMap<HttpSession, ChatServlet>();
代码为
package com.socket; import java.io.IOException; import java.util.HashMap; import java.util.Map; import javax.servlet.http.HttpSession; import javax.websocket.EndpointConfig; import javax.websocket.OnClose; import javax.websocket.OnError; import javax.websocket.OnMessage; import javax.websocket.OnOpen; import javax.websocket.Session; import javax.websocket.server.ServerEndpoint; import utils.MessageUtil; @ServerEndpoint(value = "/websocket",configurator=GetHttpSessionConfigurator.class) public class ChatServlet { private static final Map<HttpSession,ChatServlet> onlineUsers = new HashMap<HttpSession, ChatServlet>(); private static int onlineCount = 0; private HttpSession httpSession; private Session session; @OnOpen public void onOpen(Session session,EndpointConfig config){ this.session = session; this.httpSession = (HttpSession) config.getUserProperties().get(HttpSession.class.getName()); if(httpSession.getAttribute("user") != null){ onlineUsers.put(httpSession, this); } String names = getNames(); String content = MessageUtil.sendContent(MessageUtil.USER,names); broadcastAll(content); addOnlineCount(); //在线数加1 System.out.println("有新连接加入!当前在线人数为" + onlineUsers.size()); } @OnClose public void onClose(){ onlineUsers.remove(this); //从set中删除 subOnlineCount(); //在线数减1 System.out.println("有一连接关闭!当前在线人数为" + getOnlineCount()); } @OnMessage public void onMessage(String message, Session session) throws IOException { HashMap<String,String> messageMap = MessageUtil.getMessage(message); //处理消息类 String fromName = messageMap.get("fromName"); //消息来自人 的userId String toName = messageMap.get("toName"); //消息发往人的 userId String mapContent = messageMap.get("content"); if(toName.isEmpty()){ sendOffLine(fromName,toName); return; } if("all".equals(toName)){ String msgContentString = fromName + "对所有人说: " + mapContent; //构造发送的消息 String content = MessageUtil.sendContent(MessageUtil.MESSAGE,msgContentString); broadcastAll(content); }else{ try { String content = MessageUtil.sendContent(MessageUtil.MESSAGE,mapContent); singleChat(fromName,toName,content); } catch (IOException e) { e.printStackTrace(); } } System.out.println("来自客户端的消息:" + message); broadcastAll(message); } private void singleChat(String fromName, String toName, String mapContent) throws IOException { String msgContentString = fromName + "对" + toName + "说: " + mapContent; String contentTemp = MessageUtil.sendContent(MessageUtil.MESSAGE,msgContentString); boolean isExit = false; for (HttpSession key : onlineUsers.keySet()) { if(key.getAttribute("user").equals(toName)){ isExit = true; } } if(isExit){ for (HttpSession key : onlineUsers.keySet()) { if(key.getAttribute("user").equals(fromName) || key.getAttribute("user").equals(toName)){ onlineUsers.get(key).session.getBasicRemote().sendText(contentTemp); } } }else{ String content = MessageUtil.sendContent(MessageUtil.MESSAGE,"客服不在线请留言..."); broadcastAll(content); } } private void sendOffLine(String fromName, String toName) throws IOException { String msgContentString = toName + "不在线"; String content = MessageUtil.sendContent(MessageUtil.MESSAGE,msgContentString); for (HttpSession key : onlineUsers.keySet()) { if(key.getAttribute("user").equals(fromName) || key.getAttribute("user").equals(toName)){ onlineUsers.get(key).session.getBasicRemote().sendText(content); } } } private static void broadcastAll(String msg) { for (HttpSession key : onlineUsers.keySet()) { try { onlineUsers.get(key).session.getBasicRemote().sendText(msg); } catch (IOException e) { e.printStackTrace(); } } } @OnError public void onError(Session session, Throwable error){ System.out.println("发生错误"); error.printStackTrace(); } private String getNames() { String names = ""; for (HttpSession key : onlineUsers.keySet()) { String name = (String) key.getAttribute("user"); names += name + ","; } String namesTemp = names.substring(0,names.length()-1); return namesTemp; } public static synchronized int getOnlineCount() { return onlineCount; } public static synchronized void addOnlineCount() { ChatServlet.onlineCount++; } public static synchronized void subOnlineCount() { ChatServlet.onlineCount--; } }
前台的页面没有改变,经测试,可行!!!
代码我已经上传到网上,源码下载
相关文章推荐
- 解决Tomcat服务器访问链接数过大的问题
- tomcat结合nginx使用小结
- Linux配置java环境安装jdk1.6和tomcat6.0
- 如何启动免安装版Tomcat并将Tomcat添加到服务中
- Myeclipse+Tomcat安装与配置
- Tomcat源码分析——启动与停止服务
- <学习笔记>Could not load the Tomcat server configuration
- Tomcat 系统架构与设计模式,第 2 部分: 设计模式分析
- Tomcat 系统架构与设计模式,第 1 部分: 工作原理
- Java中tomcat memecached session 共享同步问题的解决办法
- Tomcat简易安装指南
- 同时打开两个Tomcat
- Tomcat 启动时 There is no Action mapped for namespace [/] and action name [] associated with context pa
- Tomcat 启动时 There is no Action mapped for namespace [/] and action name [] associated with context pa
- Tomcat 启动时 There is no Action mapped for namespace [/] and action name [] associated with context pa
- eclipse+tomcat项目部署
- Java程序读取tomcat下的properties配置文件
- Linux下Tomcat版本升级方案
- tomcat工作原理
- tomcat和weblogic设置编码方式