关于server push,the google way
前一篇webmine 的 blah中提到 ajax + server push 的想法。实做之中突然发现,貌似这个耳熟能详的东西,反而有点不好弄。
大量的server push,都是 cgi/php/perl 等的例子,采用标准的“页面下不完”方式来实现(即,Content-type: multipart/x-mixed-replace),根据我若干年前做的实验,一方面,这对 IE 是不 work 的(不支持这个 content-type ),另一方面,据说页面没下完,浏览器对 javascript 根本不处理(听说过没试过)。而我试图通过 ajax 来调用 server push 的企图,显然在这种状况下,有遭遇撞墙的危险。
这个 serverpush 也不是什么新东西,为啥没人留下有价值的方案呢?灵机一动,想起了 gmail 中嵌入的 gtalk 早就听说它是 serverpush 的了,先学习一下再说。
和哥们约好了在 gmail 上做试验,同时打开 firebug 监控网络通讯。我发现:总是有一个链接持续较长时间,但,时间稍长它就会断开(大约35秒),然后再开一个新连接,继续保持。而这35秒的过程中,一旦有任何新消息,该连接就立即断开,然后冒出一个新的连接继续保持连接状态。这个连接,大概就是 google 方式的 serverpush 连接了。
我姑且将这种方式称作 serverpush 的 google way 。可以认为这是“切成小块的 serverpush 连接”。每一个连接是被保持的 serverpush 连接。整个连接是由很多个“收到消息”或“连接超时”的隔断串起来的很多个连接。
对照一下前面提到的状况,分析一下这样做的好处。
1,连接超时的超时断开机制,保持了 http 本身的瞬时特性,是不是有的浏览器或防火墙会自动判断连接时长,然后自动断开连接呢?我没办法验证,但这个怀疑是值得注意的。
2,连接保持中,一有消息,就立即断开。相比“页面下不完”的方式,这保证了收到的消息,在第一时间能够得处理。而,这样的方式中,一个连接对应一条消息,相比 append 或 replace 的方式,也比较容易处理。
我知道你心中的疑惑——既然它也是每隔一会儿就重新连接的方式,那么,它是不是 client pull 而不是 server push 呢?
我们熟知的 client pull 方式中,每次的连接都是不被保持的,两次连接之间的时间间隔也是确定的。如果每次重新连接之间的时间间隔是 10 秒,那么,在这 10 秒之间发生的新数据,客户端是没办法“立即”获得通知的。你也许会说,10秒的时间间隔也不长,但对于象“对方正在敲击键盘”这样的东西,这个延迟恐怕就使得这样的信息失去了价值。
从资源消耗的角度来说,断开重连的方式当然是比长连接的开销要大一些,毕竟有重建连接的开销。但从实现层面来讲,这样的连接更类似于标准的 http (兼容性更好),而且具有 server push 的所有特性,也是不错的选择,不是么?
先说这么多,下次说说它在 erlang 中的实现。


Comments
长连接中的js输出是可以立即执行的,ie,ff各个版本都没问题。
各门户以前的web聊天室都用这个方式。
哦。看到了这篇看来是我搞错了。
btw,你提到的 client flash + server socket server 的方式,貌似也很不错的样子。 flash 谁都有,又能和 javascript 有效的交互,有时间了也要试试。
这都能搜出来?!
就是BOSH了
jabber的协议来的
你所谓的google way其实也是长连接。根据http 1.1的要求,如果两个请求接连发生,浏览器要重用前一个请求的tcp连接。
@zsuxqm,
http 在 v1.1 定义了 keep alive 的 chunk header 语义可以达到相同的效果。但,与此处讨论的 google way 并不相同。
两者的区别在于:chunk header 由 http 规范来保证,在一个长连接中实现服务端的消息接收。而 google way 则对协议的版本没有要求,它由客户端的 ajax 代码实现,由“接收循环”脚本,以每次接收到数据之后再发起一个新连接的方式来实现服务端的消息接收。
如果以 firebug 的 network 视图来观察 gmail 之中的 gtalk 通讯。你会发现,随着时间的推移 google way 方式会有多个相对较短(比一般的请求长,但不会超过某个值)的通讯柱状图。而 chunk header 方式则应该只会有一个很长(但永不结束)的通讯柱状图。
[...] 关于 mochiweb 和 comet ,也是本站一直以来的关注重点,除了“放狗”和“wikipedia”之外,也可以比较便利的参考本站的[这篇]以及[这篇]。 [...]
文中分析的google方式有点像分布式系统中“更新传播”的混合方式:基于租用的更新传播。也就是说它即是 client pull 又是 server push
http://cryolite.javaeye.com/blog/281324
Write a Comment