Java程序优雅关机

优先使用 kill -15 pid, 实在退出不了再用kill -9 pid

kill pid 等同于 kill -15 pid

kill命令可以发送信号给进程,15和9都是信号的编号。15代表SIGTERM,表示正常停止进程,进程可以在退出前完成一些收尾工作; 9代表SIGKILL,表示强制停止进程。

kill -l可以列出所有信号。

pkill可以根据关键字给进程发送信号,例如: pkill -15 -f test-2.0.0.0.jar

在Java代码中,可以通过Runtime.getRuntime().addShutdownHook()添加进程停止时的钩子来实现优雅关机。在这个hook中我们可以完成释放资源、保存程序运行时的状态等操作。

spingboot项目优雅关机示例如下:

ConfigurableApplicationContext ctx = SpringApplication.run(Application.class, args);
Runtime.getRuntime().addShutdownHook(new Thread(ctx::close, "shutdownHook"));

addShutdownHook方法的参数是Thread,我们可以指定进程收到停止信号后所要做的事情(Runnable接口的实现类的匿名对象)。在进程收到SIGTERM即15这个信号时,这个线程就会运行。

ApplicationContext.close()方法中会调用所有DisposableBean的destroy方法,一般通过实现DisposableBean来完成资源释放等操作,例如:

@Component
public class ThreadManager implements DisposableBean {
	@Override
	public void destroy() throws Exception {
		// TODO
	}
}

有一点要注意,进程在收到SIGTERM这个信号后,其他用户线程都停止了,只有addShutdownHook指定的线程在工作。所以你的收尾工作只能在hook线程中执行。一个错误示例如下:


volatile boolean run = true;

public void run() {
	// 业务线程运行这段代码
	while (this.run) {
		// 1.do something
	}
	// 2.释放资源
}

// shutdownHook中调用这个方法
public void stop() {
	this.run = false;
}

上面2处的代码不会执行,因为在收到SIGTERM信号后业务线程停止了,只有hook线程在运行,应该改成这样:


volatile boolean run = true;

public void run() {
	// 业务线程运行这段代码
	while (this.run) {
		// 1.do something
	}
}

// shutdownHook中调用这个方法
public void stop() {
	// 2.释放资源
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值