HTTP長串連實現“伺服器推”的技術快速入門及示範樣本

來源:互聯網
上載者:User

在我的印象裡HTTP是一種“無狀態的協議”,也就是不知道以前請求的曆史,無法保留上一次請求的結果。
Cookie的誕生,彌補了這個不足,瀏覽器可以通過本地持久化請求資料來記錄上次請求的環境。但這個沒有根本上改變HTTP請求本身的這種“用戶端請求伺服器端相應”模式——用戶端是主動的,而伺服器是被動的。
最近聽說有“HTTP長串連”,去探索了一把,果然很有意思,能夠實現“伺服器推”的這種概念,也就是伺服器是主動發送請求,用戶端是被動接受請求。
關於“伺服器推”及“HTTP長串連”的概念網上很多,給一個比較系統的介紹文章:
http://www.ibm.com/developerworks/cn/web/wa-lo-comet/

HTTP長串連這種把資料從伺服器主動“推”到用戶端的技術,能帶來的好處不言而喻。它可以把最新的統計資料輸出到用戶端,也可以實現即時通訊。

下面是JSP實現的一個“監控伺服器時間”程式的程式碼範例(片段)
1、web.xml

<servlet><servlet-name>ServerTimeMonitorServlet</servlet-name><servlet-class>com.ebiz.test.ServerTimeMonitorServlet</servlet-class><init-param><param-name>interval</param-name><param-value>1</param-value></init-param></servlet><servlet-mapping><servlet-name>ServerTimeMonitorServlet</servlet-name><url-pattern>/ServerTimeMonitor</url-pattern></servlet-mapping>

2、servlet:ServerTimeMonitorServlet.java

package com.ebiz.test;import java.io.IOException;import java.text.SimpleDateFormat;import java.util.Date;import javax.servlet.ServletConfig;import javax.servlet.ServletException;import javax.servlet.http.HttpServlet;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;public class ServerTimeMonitorServlet extends HttpServlet {private static final long serialVersionUID = -3981794330055840248L;private String interval = "1";public void init(ServletConfig config) throws ServletException {this.interval = config.getInitParameter("interval");super.init();}public void destroy() {this.interval = null;super.destroy();}protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException,java.io.IOException {for (int i = 0; i < 100; i++) {try {Thread.sleep(1000 * Integer.valueOf(interval));} catch (NumberFormatException e) {e.printStackTrace();} catch (InterruptedException e) {e.printStackTrace();}SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss E");String date_str = df.format(new Date());writerResponse(response, date_str, "showServerTime");// msg是test.jsp中的那個js方法的名稱}return;}protected void writerResponse(HttpServletResponse response, String body, String client_method) throws IOException {StringBuffer sb = new StringBuffer();sb.append("<script type=\"text/javascript\">//<![CDATA[\n");sb.append("parent.").append(client_method).append("(\"").append(body).append("\");\n");sb.append("//]]></script>");System.out.println(sb.toString());response.setContentType("text/html;charset=GBK");response.addHeader("Pragma", "no-cache");response.setHeader("Cache-Control", "no-cache,no-store,must-revalidate");response.setHeader("Cache-Control", "pre-check=0,post-check=0");response.setDateHeader("Expires", 0);response.getWriter().write(sb.toString());response.flushBuffer();}public String getInterval() {return interval;}public void setInterval(String interval) {this.interval = interval;}}

3、jsp:server-time-monitor.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" %><%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %><c:set var="ctx" value="${pageContext.request['contextPath']}" /><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8" /><title>HTTP 長串連測試 —— 監控伺服器時間 </title></head><body><div id="monitor-window">伺服器現在是:<span id="time"></span></div><form id="a-form" action="${ctx}/ServerTimeMonitor" method="post" target="handleFrame"><input type="submit" name="submit" id="submit" value=" 擷取並監控伺服器時間 " /></form><iframe name="handleFrame" id="handleFrame" style="display:none"></iframe><!-- <script type="text/javascript" src="http://code.jquery.com/jquery-1.10.2.min.js"></script> --><script type="text/javascript" src="jquery-1.10.2.min.js"></script><script type="text/javascript">//<![CDATA[function showServerTime(msg) {$("#time").html(msg);}//]]></script></body></html>

執行過程

仔細看JSP這段HTML代碼,很有意思。

1、form通過POST請求把返回的Script代碼輸出到iframe中(form的target="handleFrame")。這段返回的Script代碼在伺服器的控制台輸出如下:

<script type="text/javascript">//<![CDATA[parent.showServerTime("2013-08-17 12:08:14 星期六");//]]></script>

2、iframe完成載入上面這段代碼後解析並執行,這段代碼的作用是調用父頁面的“showServerTime”方法,把訊息傳入。

3、父頁面showServerTime函數負責處理接收到的訊息。

4、Servlet負責定時執行和輸出,源源不斷向用戶端發送內容。

原來,這個隱藏的iframe起到了一個“紐帶”的作用。

示範結果

測試結果

在Chrome中標題前面有一個正在載入的表徵圖,感覺上頁面一直在載入,IE9中沒有這個現象,其他瀏覽器沒有測試。

(完)

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.