使用RunTime.getRunTime().addShutdownHook优雅关闭线程池

Posted will的猜想

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用RunTime.getRunTime().addShutdownHook优雅关闭线程池相关的知识,希望对你有一定的参考价值。

有时候我们用到的程序不一定总是在JVM里面驻守,可能调用完就不用了,释放资源.

RunTime.getRunTime().addShutdownHook的作用就是在JVM销毁前执行的一个线程.当然这个线程依然要自己写.

利用这个性质,如果我们之前定义了一系列的线程池供程序本身使用,那么就可以在这个最后执行的线程中把这些线程池优雅的关闭掉.

比如我们定义了一个线程池

private ExecutorService streamThreadPool = Executors.newFixedThreadPool(streamNum);

然后我们需要对它进行优雅关闭

Runtime.getRuntime().addShutdownHook(new Thread() 
   public void run() 
      shutdownGracefully();
   
);
public void shutdownGracefully() 
   shutdownThreadPool(streamThreadPool, "main-pool");


/**
 * 优雅关闭线程池
 * @param threadPool
 * @param alias
 */
private void shutdownThreadPool(ExecutorService threadPool, String alias) 
   log.info("Start to shutdown the thead pool: ", alias);

   threadPool.shutdown(); // 使新任务无法提交.
   try 
      // 等待未完成任务结束
      if (!threadPool.awaitTermination(60, TimeUnit.SECONDS)) 
         threadPool.shutdownNow(); // 取消当前执行的任务
         log.warn("Interrupt the worker, which may cause some task inconsistent. Please check the biz logs.");

         // 等待任务取消的响应
         if (!threadPool.awaitTermination(60, TimeUnit.SECONDS))
            log.error("Thread pool can't be shutdown even with interrupting worker threads, which may cause some task inconsistent. Please check the biz logs.");
      
    catch (InterruptedException ie) 
      // 重新取消当前线程进行中断
      threadPool.shutdownNow();
      log.error("The current server thread is interrupted when it is trying to stop the worker threads. This may leave an inconcistent state. Please check the biz logs.");

      // 保留中断状态
      Thread.currentThread().interrupt();
   

   log.info("Finally shutdown the thead pool: ", alias);

这样我们就可以在JVM销毁前无论有没有执行的线程都会进行中断,然后关闭线程池.

以上是关于使用RunTime.getRunTime().addShutdownHook优雅关闭线程池的主要内容,如果未能解决你的问题,请参考以下文章

如何与 Runtime.getRuntime().exec(command) 程序进行交互?

如何使用 Android 代码更改分辨率(大小)和密度,Runtime.getRuntime().exec(...) 不起作用

使用RunTime.getRunTime().addShutdownHook优雅关闭线程池

使用RunTime.getRunTime().addShutdownHook优雅关闭线程池

使用Runtime.getRuntime().exec()在java中调用python脚本

无法从 Java 进程(Runtime.getRuntime().exec() 或 ProcessBuilder)读取 InputStream