应用服务器的可扩展性
当我们从应用服务器角度来审视开放连接的问题时,我们发现了这个问题的多面性。我们都知道,现在的应用服务器可以高效率的处理大量的连接,但是在现有Servlet模式下,每一个连接需要执行一个线程。如果这些连接由于偶发性的服务器发起更新而变为长期存活的话,服务器的可扩展性势必受到线程池耗尽的严重威胁。
虽然在servlet模型中关于异步通信的标准正在JSR315中被实现,但业界一直在通过完全不同的非标准化方法来解决这个问题。标准机制的缺失让人非常失望,因为任何可升级扩展的推送机制将需要与底层的服务器机制来紧密结合,需要实行专门的部署。好消息是,在开源应用服务器上已经出现许多不同的解决方案。
Tomcat 6通过一个附加的Servlet接口—org.apache.catalina.CometProcessor,提供了异步请求处理(ARP)功能
CometProcessor可以在当数据在连接上可读的时候,让Servlet接收事件,而不会通过阻塞读来消耗一个线程。与不同的service()方法相比,基于事件的机制让开发者可以很好的对异步I/O处理进行控制。Tomcat 6还提供了一个CometFilter接口,当comet事件被处理的时候,才激活被调用的过滤器链。
Glassfish V2/Grizzly通过类
com.sun.enterprise.web.connector.grizzly.comet.CometEngine来提供ARP功能。应用程序可以通过一个CometHandler来注册接受事件,而且和Tomcat 6一样,当数据可用的时候处理读事件,反之则执行阻塞读操作。
Jetty 6则在现有servlet API中提供了支持ARP的扩展机制。它的org.mortbay.util.ajax.Continuation类提供了suspend/resume方法,来挂起请求操作,并在以后让其在另一个不同的线程上异步恢复。当在servlet的Service()成员内调用suspend()时,将产生一个异常,并被Jetty服务器所捕获,然后用于确认这个请求是否被恢复。恢复这个请求需要重新调用service()方法,然后它可以进行写响应。延长机制的一个复杂之处是,service()方法必须被明确执行来支持触发延伸。更好的做法是可以应用过滤机制的标准servlet,不过,过滤器同样也必须处理触发延伸的问题。
ICEfaces异步HTTP服务器AHS算不上是一个应用服务器,但是它可以与任何应用服务器一起为ICEfaces应用提供ARP支持。和上面所提到机制不同之处是,没有与AHS相关的编程API,它的功能是专门针对ICEfaces的。需要对AHS进行配置来处理异步通讯通道,使用一个边界线程池来对进行中的请求匹配更新。它可以被部署在群环境中,包含一个servlet模式,可以被用来在portal环境下处理AJAX推送。
开发模式
在简单理解了推送机制和它相应的复杂性之后,很多开发者选择了对开发真正的推送风格应用敬而远之。现在将我们的目光转向那些可以帮助我们实现推送式应用程序开发的开源AJAX技术。
Dojo/Cometd/Bayeux提供了一个以客户端为中心的编程模式和一个通用的可扩展到服务器的发布/订阅机制。我们可以为专门的消息类定义一个专门的通道,这些通道的客户端可存在于浏览器或服务器中。使用JavaScript应用逻辑来处理从服务器推送的消息,以及相应的更新用户界面。从服务器角度来看,需要定义一个推送通道,然后服务器端应用逻辑通过该通道来发布事件。Cometd是一个非常灵活的机制,可同时支持在服务器端的Java和Python实现。Cometd已经被集成到Tomcat 6、Grizzly和Jetty 6中。通过使用一个支持在窗口之间进行大数据传输的共享cookie机制,浏览器连接共享成为可能。从本质上来说,Cometd方式带来了一个松散耦合的分布式系统,因此应用开发者需要解决一些相应的复杂问题,例如安全性和可维护性。
DWR/Reverse AJAX则在远程过程调用RPC基础上提供了一个以客户为中心的编程模式。简单来说,DWR通过JavaScript实现了从客户端调用服务器端的Java对象,而Reverse AJAX则是从服务器端的Java对象来调用JavaScript对象。对于一次推送交互,要求执行一个JavaScript来处理特定更新,服务器端的Java逻辑必须合理的调用这个JavaScript。DWR servlet则通过HTTP连接来处理RPC呼叫集合,但是连接共享问题在JavaScript执行中没有得到解决。DWR现已集成到Jetty 6中。
ICEfaces/AJAX推送在JSF基础上提供了一个以服务器为中心的编程模式。ICEfaces对JSF进行了扩展之后,可以支持一个透明AJAX桥,它可以在JSF生命周期的基础上实现更多针对浏览器的修改。一个简单的扩展API允许应用程序逻辑在一些异步事件基础上请求一个页面刷新,浏览器客户端的逻辑组合可以同时接收相同的更新。另外,它还提供了一个RenderHub功能来处理底层异步展现机制的同步和性能优化。ICEfaces可以被配置成从Tomcat 6、Grizzly和Jetty中使用ARP机制,当然还有ICEfaces AHS。ICEfaces桥通过一个共享cookie机制来支持连接共享,当在servlet模式下配置AHS后,可以支持portal环境中的AJAX推送。
结束语
在本篇文章中,我们把Web 2.0看作一个自然的即时社会化网络平台,而且也了解了使用轻量级Web技术来实现它所要求的推送功能的复杂性。尽管多数现有AJAX技术无法解决这一问题,不过一些开源技术已经出现,来帮助我们实现这个必需的功能。因此,有了这些开源技术,我们今天就能实现真正的Web 2.0。另外,随着标准化的进一步落实,下一代浏览器实现也将最终降低实现这一功能的复杂性。如果推送式的Web应用和Web 2.0已进入你的视线,那么投入到其中看看它能实现的强大应用吧。不过,需要提醒大家的是,你应该细心的检查你现有的最佳开发模式和部署条件,进而设计一个方式,可以让你将精力集中在应用程序开发上,而不是底层的推送功能开发上。
|