依照AJAX的长轮询(long-polling)格局实现简单的聊天室程序

按照AJAX的长轮询(long-polling)形式贯彻简单的聊天室程序

(转http://blog.csdn.net/neusoftware\_20063500/archive/2009/04/30/4140903.aspx)

 

那里只是做个测试,很粗略,没有办好线程同步的题材,只是为了长轮询。

原理:

可以看:http://yiminghe.javaeye.com/blog/294781

AJAX
的出现使得 JavaScript 可以调用 XMLHttpRequest 对象发出 HTTP
请求,JavaScript 响应处理函数遵照服务器重临的信息对 HTML
页面的来得举行更新。使用 AJAX 实现“服务器推”与观念的 AJAX
应用不同之处在于:

  1. 服务器端会阻塞请求直到有多少传递或逾期才回到。

  2. 客户端 JavaScript
    响应处理函数会在处理完服务器重回的新闻后,再一次发出请求,重新树立连接。

  3. 当客户端处理接收的多少、重新树立连接时,服务器端可能有新的多寡到达;这个音信会被服务器端保存直到客户端重新创立连接,客户端会五回把当下劳动器端所有的音讯取回。

图片 1

闲谈页面的代码:

view
plain
copy
to
clipboard
print?

  1. <%@ page language=”java” pageEncoding=”GBK”%>  
  2. <!DOCTYPE HTML PUBLIC “-//W3C//DTD HTML 4.01 Transitional//EN”>  
  3. <html>  
  4.     <head>  
  5.         <title>chat room</title>  
  6.         <meta http-equiv=”pragma” content=”no-cache”>  
  7.         <meta http-equiv=”cache-control” content=”no-cache”>  
  8.         <meta http-equiv=”expires” content=”0″>  
  9.         <meta http-equiv=”keywords” content=”keyword1,keyword2,keyword3″>  
  10.         <meta http-equiv=”description” content=”This is my page”>  
  11.         <mce:script type=”text/javascript” src=”ext-2.2/adapter/ext/ext-base.js” mce_src=”ext-2.2/adapter/ext/ext-base.js”></mce:script>  
  12.         <mce:script type=”text/javascript” src=”ext-2.2/ext-all.js” mce_src=”ext-2.2/ext-all.js”></mce:script>  
  13.         <mce:script type=”text/javascript”  
  14.             src=”ext-2.2/build/locale/ext-lang-zh_CN.js”></mce:script>  
  15.         <mce:script type=”text/javascript” src=”jslib/mm.js” mce_src=”jslib/mm.js”></mce:script>  
  16.     </head>  
  17.     <body>  
  18.         <div id=”main”></div><!– 显示聊天记录的区域 –>  
  19.         username:  
  20.         <input type=”text” name=”username” />  
  21.         <br>  
  22.         message:  
  23.         <input type=”text” id=”message”>  
  24.         <br>  
  25.         <input type=”button” value=”submit” onclick=”putMsg()”>  
  26.     </body>  
  27. </html>  

<%@ page language=”java” pageEncoding=”GBK”%> <!DOCTYPE HTML
PUBLIC “-//W3C//DTD HTML 4.01 Transitional//EN”> <html>
<head> <title>chat room</title> <meta
http-equiv=”pragma” content=”no-cache”> <meta
http-equiv=”cache-control” content=”no-cache”> <meta
http-equiv=”expires” content=”0″> <meta http-equiv=”keywords”
content=”keyword1,keyword2,keyword3″> <meta
http-equiv=”description” content=”This is my page”> <mce:script
type=”text/javascript” src=”ext-2.2/adapter/ext/ext-base.js”
mce_src=”ext-2.2/adapter/ext/ext-base.js”></mce:script>
<mce:script type=”text/javascript” src=”ext-2.2/ext-all.js”
mce_src=”ext-2.2/ext-all.js”></mce:script> <mce:script
type=”text/javascript”
src=”ext-2.2/build/locale/ext-lang-zh_CN.js”></mce:script>
<mce:script type=”text/javascript” src=”jslib/mm.js”
mce_src=”jslib/mm.js”></mce:script> </head> <body>
<div id=”main”></div><!– 展现聊天记录的区域 –>
username: <input type=”text” name=”username” /> <br>
message: <input type=”text” id=”message”> <br> <input
type=”button” value=”submit” onclick=”putMsg()”> </body>
</html>

概念mm.js,定义发送音信,定义接收信息的JS函数

view
plain
copy
to
clipboard
print?

  1. Ext.onReady(function () {  
  2.     getMsg();  
  3. });  
  4. function getMsg() {  
  5.     Ext.Ajax.request({url:”getMsg”, callback:function (options, success, response) {  
  6.         if (success) {  
  7.             Ext.DomHelper.append(Ext.get(“main”), response.responseText, true);  
  8.         }  
  9.         getMsg();  
  10.     }});  
  11. }  
  12. function putMsg() {  
  13.     Ext.Ajax.request({url:”putMsg”, params:{message:document.getElementById(“message”).value}});  
  14. }  
  15. /* 
  16. Ext.Updater.defaults.indicatorText='<div><img src=”icon/loading.gif” mce_src=”icon/loading.gif” width=”20″ height=”20″/>refresh…</div>’; 
  17.     var updater = Ext.get(‘main’).getUpdater(); 
  18.     updater.update({ 
  19.         url:”getMsg” 
  20.     }); 
  21. */  

Ext.onReady(function () { getMsg(); }); function getMsg() {
Ext.Ajax.request({url:”getMsg”, callback:function (options, success,
response) { if (success) { Ext.DomHelper.append(Ext.get(“main”),
response.responseText, true); } getMsg(); }}); } function putMsg() {
Ext.Ajax.request({url:”putMsg”,
params:{message:document.getElementById(“message”).value}}); } /*
Ext.Updater.defaults.indicatorText='<div><img
src=”icon/loading.gif” mce_src=”icon/loading.gif” width=”20″
height=”20″/>refresh…</div>’; var updater =
Ext.get(‘main’).getUpdater(); updater.update({ url:”getMsg” }); */

 下面是取得message的servlet

view
plain
copy
to
clipboard
print?

  1. package hyjc.listener;  
  2.   
  3. import java.io.IOException;  
  4. import java.io.PrintWriter;  
  5.   
  6. import javax.servlet.ServletException;  
  7. import javax.servlet.http.HttpServlet;  
  8. import javax.servlet.http.HttpServletRequest;  
  9. import javax.servlet.http.HttpServletResponse;  
  10.   
  11. public class GetMsg extends HttpServlet {  
  12.   
  13.     public void doGet(HttpServletRequest request, HttpServletResponse response)  
  14.             throws ServletException, IOException {  
  15.   
  16.         response.setContentType(“text/html”);  
  17.         PrintWriter out = response.getWriter();  
  18.         MessageList m = MessageList.getInstance();  
  19.         boolean end = false;  
  20.         while (!end) {  
  21.             System.out.println(“before get”);  
  22.             String msg = m.get();  
  23.             System.out.println(“after get ” + msg);  
  24.             out.write(msg + “<br>”);  
  25.             if (m.isEmpty()) {  
  26.                 end = true;  
  27.             }  
  28.         }  
  29.         out.close();  
  30.     }  
  31.   
  32.     public void doPost(HttpServletRequest request, HttpServletResponse response)  
  33.             throws ServletException, IOException {  
  34.         doGet(request, response);  
  35.     }  
  36.   
  37. }  

package hyjc.listener; import java.io.IOException; import
java.io.PrintWriter; import javax.servlet.ServletException; import
javax.servlet.http.HttpServlet; import
javax.servlet.http.HttpServletRequest; import
javax.servlet.http.HttpServletResponse; public class GetMsg extends
HttpServlet { public void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
response.setContentType(“text/html”); PrintWriter out =
response.getWriter(); MessageList m = MessageList.getInstance(); boolean
end = false; while (!end) { System.out.println(“before get”); String msg
= m.get(); System.out.println(“after get ” + msg); out.write(msg +
“<br>”); if (m.isEmpty()) { end = true; } } out.close(); } public
void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException { doGet(request, response); } }

上边是加上音讯的servlet

view
plain
copy
to
clipboard
print?

  1. package hyjc.listener;  
  2.   
  3. import java.io.IOException;  
  4. import java.io.PrintWriter;  
  5.   
  6. import javax.servlet.ServletException;  
  7. import javax.servlet.http.HttpServlet;  
  8. import javax.servlet.http.HttpServletRequest;  
  9. import javax.servlet.http.HttpServletResponse;  
  10.   
  11. public class PutMsg extends HttpServlet {  
  12.   
  13.     public void doGet(HttpServletRequest request, HttpServletResponse response)  
  14.             throws ServletException, IOException {  
  15.   
  16.         response.setContentType(“text/html”);  
  17.         System.out.println(“put message”);  
  18.         PrintWriter out = response.getWriter();  
  19.         out.flush();  
  20.         String msg = request.getParameter(“message”);  
  21.         if (null != msg) {  
  22.             MessageList.getInstance().add(msg);  
  23.         } else {  
  24.             System.out.println(“添加消息:” + msg + “成果”);  
  25.         }  
  26.         out.close();  
  27.     }  
  28.   
  29.     public void doPost(HttpServletRequest request, HttpServletResponse response)  
  30.             throws ServletException, IOException {  
  31.         doGet(request, response);  
  32.     }  
  33.   
  34. }  

package hyjc.listener; import java.io.IOException; import
java.io.PrintWriter; import javax.servlet.ServletException; import
javax.servlet.http.HttpServlet; import
javax.servlet.http.HttpServletRequest; import
javax.servlet.http.HttpServletResponse; public class PutMsg extends
HttpServlet { public void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
response.setContentType(“text/html”); System.out.println(“put message”);
PrintWriter out = response.getWriter(); out.flush(); String msg =
request.getParameter(“message”); if (null != msg) {
MessageList.getInstance().add(msg); } else {
System.out.println(“添加音讯:” + msg + “成果”); } out.close(); } public
void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException { doGet(request, response); } }

上边是存放信息的音讯队列,内部用阻塞队列使用

view
plain
copy
to
clipboard
print?

  1. package hyjc.listener;  
  2.   
  3. import java.util.Iterator;  
  4. import java.util.concurrent.LinkedBlockingQueue;  
  5.   
  6. public class MessageList {  
  7.   
  8.     private static MessageList list = null;  
  9.   
  10.     private static Object key = new Object();  
  11.   
  12.     private MessageList() {  
  13.         this.add(“hello”);  
  14.         this.add(“world”);  
  15.     }  
  16.   
  17.     public static MessageList getInstance() {  
  18.         synchronized (key) {  
  19.             if (list == null) {  
  20.                 list = new MessageList();  
  21.             }  
  22.             return list;  
  23.         }  
  24.     }  
  25.   
  26.     private LinkedBlockingQueue<String> queue = new LinkedBlockingQueue<String>();  
  27.   
  28.     public boolean isEmpty() {  
  29.         return queue.isEmpty();  
  30.     }  
  31.   
  32.     public int size() {  
  33.         return queue.size();  
  34.     }  
  35.   
  36.     public String get() {  
  37.         try {  
  38.             return queue.take();  
  39.         } catch (InterruptedException e) {  
  40.             e.printStackTrace();  
  41.             return null;  
  42.         }  
  43.     }  
  44.   
  45.     public void clear() {  
  46.         queue.clear();  
  47.     }  
  48.   
  49.     public void add(String msg) {  
  50.         try {  
  51.             queue.put(msg);  
  52.         } catch (InterruptedException e) {  
  53.             e.printStackTrace();  
  54.         }  
  55.     }  
  56.   
  57.     public Iterator<String> iterator() {  
  58.         return queue.iterator();  
  59.     }  
  60. }  

package hyjc.listener; import java.util.Iterator; import
java.util.concurrent.LinkedBlockingQueue; public class MessageList {
private static MessageList list = null; private static Object key = new
Object(); private MessageList() { this.add(“hello”); this.add(“world”);
} public static MessageList getInstance() { synchronized (key) { if
(list == null) { list = new MessageList(); } return list; } } private
LinkedBlockingQueue<String> queue = new
LinkedBlockingQueue<String>(); public boolean isEmpty() { return
queue.isEmpty(); } public int size() { return queue.size(); } public
String get() { try { return queue.take(); } catch (InterruptedException
e) { e.printStackTrace(); return null; } } public void clear() {
queue.clear(); } public void add(String msg) { try { queue.put(msg); }
catch (InterruptedException e) { e.printStackTrace(); } } public
Iterator<String> iterator() { return queue.iterator(); } }

下边是出现说法效果,输入message,点击submit,就会添加到MessageList中,然后会在GetMsg中继续执行,实现长连接

图片 2

 

任何有关著作

http://yiminghe.javaeye.com/blog/284953

http://yiminghe.javaeye.com/blog/294781 

http://yiminghe.javaeye.com/blog/300050 

 

相关文章