这是一个用自己实现的HTTP长连接做的聊天室.
HTTP长连接。在index.html,发起一个异步请求。在请求的Servlet里,把当前sessionId和线程加入到映射列表中,然后把当前线程wait()。在其他人登陆或者发消息的时候,让映射里的所有线程notify(),notify()之后会返回一些数据到页面,页面接收处理之后,再次发起一个新的请求。
1.Constants.java,存储会话,消息,会话线程映射集合.
package com.rx.chart.common;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* 公共属性
*
* @author Renxin
*
*/
public class Constants {
/**
* Session集合
*/
public static List<String> users = new ArrayList<String>();
/**
* 消息集合
*/
public static List<String> messages = new ArrayList<String>();
/**
* 会话线程映射
* Key:SessionId
* Value:Thread
*/
public static Map<String, Thread> sessionThreadMapping = new HashMap<String, Thread>();
}
2.SessionListener.java,监听Session的创建和销毁,维护会话列表.
package com.rx.chart.listener;
import static com.rx.chart.common.Constants.users;
import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;
import com.rx.chart.util.Util;
/**
* Session监听器
*
* @author Renxin
*
*/
public class SessionListener implements HttpSessionListener {
public void sessionCreated(HttpSessionEvent httpsessionevent) {
// 加入到Session集合
users.add(httpsessionevent.getSession().getId());
// 唤醒全部更新列表
Util.wakeUpAllThread();
}
public void sessionDestroyed(HttpSessionEvent httpsessionevent) {
// 从Session集合移除
users.remove(httpsessionevent.getSession().getId());
// 唤醒全部更新列表
Util.wakeUpAllThread();
}
}
3.Initialization.java,获取用户列表和消息列表
package com.rx.chart.servlet;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import com.rx.chart.util.Util;
/**
* 初始化
*
* @author Renxin
*
*/
public class Initialization extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// 返回消息
Util.out(response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
4.RefreshUserList.java,长连接刷新信息.
package com.rx.chart.servlet;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import com.rx.chart.common.Constants;
import com.rx.chart.util.Util;
/**
* 刷新
*
* @author Renxin
*
*/
public class RefreshUserList extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
HttpSession session = request.getSession();
// 加入映射
Constants.sessionThreadMapping.put(session.getId(), Thread
.currentThread());
// 当前线程等待
try {
synchronized (Thread.currentThread()) {
Thread.currentThread().wait();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
// 返回消息
Util.out(response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
5.SendMessage,发送消息.
package com.rx.chart.servlet;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import com.rx.chart.common.Constants;
import com.rx.chart.util.Util;
/**
* 发送消息
*
* @author Renxin
*
*/
public class SendMessage extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
HttpSession session = request.getSession();
String message = request.getParameter("message");
message = session.getId() + ":" + message;
Constants.messages.add(message);
// 唤醒全部更新列表
Util.wakeUpAllThread();
// 返回消息
Util.out(response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
6.Util,工具类.
package com.rx.chart.util;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletResponse;
import com.rx.chart.common.Constants;
import flexjson.JSONSerializer;
/**
* 工具类
*
* @author Renxin
*
*/
public class Util {
/**
* 唤醒全部
*/
public static void wakeUpAllThread() {
Iterator<Map.Entry<String, Thread>> iterator = Constants.sessionThreadMapping
.entrySet().iterator();
while (iterator.hasNext()) {
Map.Entry<String, Thread> entry = iterator.next();
Thread thread = entry.getValue();
synchronized (thread) {
thread.notify();
}
}
}
/**
* 唤醒指定
*
* @param sessionId
*/
public static void wakeUpAllThread(String sessionId) {
Iterator<Map.Entry<String, Thread>> iterator = Constants.sessionThreadMapping
.entrySet().iterator();
while (iterator.hasNext()) {
Map.Entry<String, Thread> entry = iterator.next();
if (sessionId.equals(entry.getKey())) {
Thread thread = entry.getValue();
synchronized (thread) {
thread.notify();
}
}
}
}
/**
* 输出用户列表
*
* @param response
* @throws IOException
*/
public static void out(HttpServletResponse response) throws IOException {
Map<String, List<String>> map = new HashMap<String, List<String>>();
map.put("users", Constants.users);
map.put("messages", Constants.messages);
response.setContentType("text/html");
PrintWriter out = response.getWriter();
out.print(new JSONSerializer().serialize(map));
out.flush();
out.close();
}
}
7.页面
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme() + "://"
+ request.getServerName() + ":" + request.getServerPort()
+ path + "/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<base href="<%=basePath%>">
<title>首页</title>
<script type="text/javascript" src="js/jquery-1.7.1.min.js">
</script>
</head>
<body>
<div>
<div>
<h2>
用户列表
</h2>
</div>
<div id="userList"></div>
</div>
<div>
<div>
<h2>
消息列表
</h2>
</div>
<div id="messageList"></div>
</div>
<div>
<input type="text" id="message" />
<input type="button" value="发送" onclick="subMsg();" />
</div>
</body>
</html>
<script type="text/javascript">
//处理内容
function handlerContent(content) {
eval('var c=' + content);
if (c.users) {
var html;
html = '<ul>';
for ( var u in c.users) {
html += '<li>';
html += c.users[u];
html += '</li>';
}
html += '</ul>';
$('#userList').html(html);
}
if (c.messages) {
var html;
html = '<ul>';
for ( var m in c.messages) {
html += '<li>';
html += c.messages[m];
html += '</li>';
}
html += '</ul>';
$('#messageList').html(html);
}
}
//发消息
function subMsg() {
$.post('SendMessage', {
'message' : $('#message').val()
}, function(content) {
handlerContent(content);
});
$('#message').val('');
}
//初始化
function init() {
$.post('Initialization', function(content) {
handlerContent(content);
refreshUserList();
});
}
//刷新列表
function refreshUserList() {
$.post('RefreshUserList', function(content) {
handlerContent(content);
refreshUserList();
});
}
window.onload = init();
</script>
分享到:
相关推荐
基于长连接的简易聊天室jQuery+.net 2.0 Comet Comet练手,尚有不少bug,还未实现维护用户列表功能 是长连接的不是轮询方式 升级版本 http://download.csdn.net/source/2216847
Netty中实现多客户端连接与通信-以实现聊天室群聊功能为例示例代码
利用长连接技术实现聊天室例子.
基于TCP/IP协议的网络聊天室的设计与实现毕业论文 本文主要介绍了基于TCP/IP协议的网络聊天室的设计与实现,讨论了聊天室系统的架构、功能和实现细节。聊天室系统采用C/S模式,基于TCP/IP协议,使用MFC技术实现。...
linux系统下实现聊天室 (1)在Linux系统下,使用TCP协议套接字编程; (2)服务器应具有处理多个客户端连接能力(设定最大连接数,如5个); (3)具有群发和私聊的能力; (4)过程描述
Java聊天室系统主要用于实现在线聊天,基本功能包括:服务端和客户端。本系统结构如下: (1)服务端: 1、能够开启和关闭服务器 2、等待着客户端从特殊端口发送的请求 3、监听的端口并不是固定的,服务端的端口...
【设计要求】用java实现基于C/S模式的聊天室程序。聊天室分为服务器端 和客户端两部分,服务器端程序主要负责侦听客户端发来的消息,客户端需要登 陆到服务器端才可以实现正常的聊天功能。 服务器端主要功能如下:在...
主要功能: (1)私聊 (2)群聊 实现方法:(具体参考代码) (1)服务端:起初使用多进程和管道,但没有实现;后来我就使用了多线程。 客户端:使用多进程,采用I/O分割模型。
基于WinSock的局域网聊天室设计与实现 WinSock是Windows下的Socket规范,已经成为兼容当前流行操作系统的一种通用的网络编程接口。WinSock是一个基于Socket模型的API,由Application、API和SPI组成。其中Winsock ...
利用长连接技术实现聊天室例子, 重新上传例子
Java聊天室系统主要用于实现在线聊天,基本功能包括:服务端和客户端。本系统结构如下: (1)服务端: 1、能够开启和关闭服务器 2、等待着客户端从特殊端口发送的请求 3、监听的端口并不是固定的,服务端的...
Java聊天室系统主要用于实现在线聊天,基本功能包括:服务端和客户端。本系统结构如下: (1)服务端: 1、能够开启和关闭服务器 2、等待着客户端从特殊端口发送的请求 3、监听的端口并不是固定的,服务端的端口...
本程序用winsocket 实现了一个基于c/s 架构的简单的聊天室程序。 采用面向连结的socket api, 信息发送、接收为阻塞同步方式。为实现多用户聊天,采用了服务器端分发线程处理,主线程阻塞接受客户端socket, 每接收...
系统具有目前聊天室的基本功能:包括支持多种头像,字色,语气选择,支持emote,支持私聊,支持在线聊友查找,支持分屏显示,支持用户定制自己的私人头像,支持脏话过滤,支持嘉宾聊天。屏蔽掉自己讨厌的人物,可以给...
本项目基于Spring平台,整合websocket协议,实现一个简易web聊天室的功能。主要特性如下: 1.包含聊天室登录、退出的功能。登录时,浏览器自动向服务器发起websocket连接,退出时自动切断。 2.登录后,用户可查看到...
使用WebSocket+SpringBoot搭建简易的多人聊天室 由浅入深,配合博客入门教程文章食用,风味独特。 使用WebSocket+SpringBoot搭建简易的多人聊天室 由浅入深,配合博客入门教程文章食用,风味独特。 使用WebSocket+...
java多线程实现TCP连接UDP聊天的聊天程序
asp 语言制作聊天室 与数据库进行连接 能实现公聊 选择不同的聊天室
Java聊天室的设计与实现socket 设计软件源码+WORD毕业论文文档 Java聊天室系统主要用于实现在线聊天,基本功能包括:服务端和客户端。本系统结构如下: (1)服务端: 1、能够开启和关闭服务器 2、等待着客户端从...