如何优雅地保证程序不退出?

mac2025-02-08  18

首先提两个问题:

springboot应用程序只在main方法中调用SpringApplication.run(xx),程序就运行起来了,他为什么能保持住不退出?quartz程序为什么能一直运行不退出?

我们为了让程序保持不退出,一般使用Thread.sleep方法,或者使用一个while无限循环,但是总感觉不太优雅。参考springboot和tomcat的源码写了一个小工具,可以优雅地实现程序保持住不退出。

package top.jfunc.common.thread; import java.util.concurrent.TimeUnit; /** * 使程序不退出,保证至少一个前台进程 * @see https://dubbo.apache.org/zh-cn/blog/spring-boot-dubbo-start-stop-analysis.html * @author xiongshiyan at 2019/10/16 , contact me with email yanshixiong@126.com or phone 15208384257 */ public class HoldProcessor { private volatile boolean stopAwait = false; /** * Thread that currently is inside our await() method. */ private volatile Thread awaitThread = null; /** * 开始等待 */ public void startAwait(){ Thread awaitThread = new Thread(this::await,"hold-process-thread"); awaitThread.setContextClassLoader(getClass().getClassLoader()); //这一步很关键,保证至少一个前台进程 awaitThread.setDaemon(false); awaitThread.start(); } /** * 停止等待,退出程序,一般放在shutdown hook中执行 * @see Runtime#addShutdownHook(Thread) */ public void stopAwait() { //此变量 stopAwait=true; Thread t = awaitThread; if (null != t) { t.interrupt(); try { t.join(1000); } catch (InterruptedException e) { // Ignored } } } private void await(){ try { awaitThread = Thread.currentThread(); while(!stopAwait) { try { TimeUnit.SECONDS.sleep(10); } catch( InterruptedException ex ) { // continue and check the flag } } } finally { awaitThread = null; } } }

示例使用方法:

System.out.println("程序开始"); HoldProcessor holdProcessor = new HoldProcessor(); System.out.println("开始等待"); holdProcessor.startAwait(); System.out.println("添加shutdown hook"); Runtime.getRuntime().addShutdownHook(new Thread(()->{ System.out.println("收到kill 信号,停止程序"); holdProcessor.stopAwait(); }));

参考:https://dubbo.apache.org/zh-cn/blog/spring-boot-dubbo-start-stop-analysis.html

最新回复(0)