在GWT启动时启动后台线程

时间:2009-02-11 21:24:37

标签: java multithreading gwt

我有一个GWT应用程序,显示由JFreeChart呈现的一些图表。每隔几分钟,页面刷新一次,这会导致应用程序生成新图表。 (换句话说,整个图表生成过程由客户端请求引导。)问题是多个客户端命中同一个服务器会导致生成图表的多个请求,但由于所有用户的图表相同,真的没有理由这样做。我想在后台线程中预渲染图表,这将在应用程序启动时启动,然后根据请求将已呈现的图表提供给客户端。

我没有在GWT中看到任何“认可”的方式来在服务器启动时执行您自己的代码。我能想到的唯一方法是创建一个由应用程序容器在启动时加载的servlet,然后在init()方法中启动图表生成线程。

有更优选的方法吗?

注意:假设这是真的,“不”是一个完全可以接受的答案。

4 个答案:

答案 0 :(得分:6)

回答你的问题:不.GWT是一种前端技术,穿过这条线路的唯一GWT就是RPC机制。您可以执行的唯一“GWT”类型方法是在用户第一次请求时检查图表文件是否存在,如果不这样做则生成图表文件。这意味着使用文件系统来检查它是否已经创建。

更好的方法是按照你的说法去做,例如:配置你的web项目,以便在启动时启动课程。您可以在web.xml中执行此操作,如下所述:

http://wiki.metawerx.net/wiki/Web.xml.LoadOnStartup

以下是Stripes如何做到这一点的例子:

<servlet>
        <servlet-name>StripesDispatcher</servlet-name>
        <servlet-class>net.sourceforge.stripes.controller.DispatcherServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>StripesDispatcher</servlet-name>
        <url-pattern>*.action</url-pattern>
    </servlet-mapping>

答案 1 :(得分:3)

我不同意你应该把代码放在servlet初始化中来创建这些线程。当Web应用程序停止时,您将无法控制何时销毁这些线程。此外,当您再次启动Web应用程序时,它是否会再次创建这些线程?

更好的方法是使用名为contextInitialized的J2EE ServletContextListener事件创建线程,使用contextDestroyed事件来销毁线程。这也允许您控制线程销毁并等待线程中的代码在销毁之前完成执行。

看起来这解释了它是如何工作的: http://www.java-tips.org/java-ee-tips/java-servlet/how-to-work-with-servletcontextlistener.html

答案 2 :(得分:2)

首先,我不赞同之前的海报,即GWT只是一种前端技术,因为该框架包含了异步构建和调用服务的所有内容。例如,请参阅RemoteServiceServlet和用法。 GWT提供客户端和服务器端组件。

话虽如此,GWT似乎没有专门的启动类型servlet。但是,由于后端是基于servlet的,为了保持一致性,我倾向于使用启动servlet(在google中搜索Loading Servlets on Startup),并让它在启动时生成图表,然后定期生成需要的。

另一种方法是让一个cron作业定期重新构建图表,直接或通过调用私有服务。

无论哪种方式,客户端请求只会检索预先生成的图表。生成新图表时,只需将其替换为旧图表,以便用户没有明显的延迟。

答案 3 :(得分:0)

GWT是一个前端框架。我确实有一些特定的服务器组件,但这些组件仅用于序列化/反序列化客户端的请求。请记住,前端是JavaScript,后端是java。因此,服务器组件将JavaScript对象转换为它的java表示。如果查看代码,您会发现GWT RemoteServiceServlet只是继承了标准“javax.servlet.http.HttpServlet”,就像任何servlet一样。它只是实现了自己的doPost和doGet方法来进行序列化。

话虽如此,您的问题可能适用于众多其他框架。它不依赖于GWT。您只需要配置servlet容器以在启动时启动GWT RemoteServiceServlet。 servlet可以具有所有客户端使用的静态缓存并提供相同的图表。然后,您可以在启动时启动第二个线程,定期更新线程。