在服务器端为 servlet JSP MVC 网站运行定期任务

2022-09-02 11:52:15

我使用servlet和JSP开发了一个Web应用程序。我没有使用任何框架本身,而是使用我自己自制的MVC框架。我正在使用MySQL作为后端。

我想执行以下操作:

  1. 每小时从数据库中清理一些数据
  2. 每隔 15 分钟在 XML 文件中生成并存储有关数据的统计信息

问题是:目前我的所有代码都是由于从客户端收到的请求而运行的。

如何在服务器端运行定期任务?

我现在有一个解决方案是在控制器的 init 函数中创建一个线程。还有其他选择吗?


答案 1

您可以使用 ServletContextListener 在 webapp 的启动时执行一些初始化。运行定期任务的标准Java API方法是TimerTimerTask的组合。下面是一个启动示例:

public void contextInitialized(ServletContextEvent event) {
    Timer timer = new Timer(true);
    timer.scheduleAtFixedRate(new CleanDBTask(), 0, oneHourInMillis);
    timer.scheduleAtFixedRate(new StatisticsTask(), 0, oneQuartInMillis);
}

其中,这两个任务可能如下所示:

public class CleanDBTask extends TimerTask {
    public void run() {
        // Implement.
    }
}

但是,不建议在 Java EE 中使用。如果任务引发异常,则整个线程将被终止,您基本上需要重新启动整个服务器才能使其再次运行。对系统时钟的变化也很敏感。TimerTimerTimer

更新,更健壮的java.util.concurrent方式将是RespectedExecutorServiceRunnable的组合。下面是一个启动示例:

private ScheduledExecutorService scheduler;

public void contextInitialized(ServletContextEvent event) {
    scheduler = Executors.newSingleThreadScheduledExecutor();
    scheduler.scheduleAtFixedRate(new CleanDBTask(), 0, 1, TimeUnit.HOURS);
    scheduler.scheduleAtFixedRate(new StatisticsTask(), 0, 15, TimeUnit.MINUTES);
}

public void contextDestroyed(ServletContextEvent event) {
    scheduler.shutdownNow();
}

答案 2

您可以使用任何调度程序来安排您的过程,如石英,弹簧调度程序

http://static.springsource.org/spring/docs/2.5.x/reference/scheduling.html 在任何实现中都很好地支持了这些东西。


推荐