前言
什么是优雅停机?简单来说就是在对应用进程发送停止指令之后,能保证正在执行的业务操作不受影响。应用接收到停止指令之后的步骤应该是,停止接收访问请求,等待已经接收到的请求处理完成,并能成功返回,这时才真正停止应用。本文主要描述的是SpringBoot中优雅停机的几种方式。
方式一:使用Springboot配置
前提:Tomcat版本在9.0.33以上或SpingBoot版本在2.3以上
Graceful shutdown is supported with all four embedded web servers (Jetty, Reactor Netty, Tomcat, and Undertow) and with both reactive and Servlet-based web applications. It occurs as part of closing the application context and is performed in the earliest phase of stopping
SmartLifecycle
beans. This stop processing uses a timeout which provides a grace period during which existing requests will be allowed to complete but no new requests will be permitted. The exact way in which new requests are not permitted varies depending on the web server that is being used. Jetty, Reactor Netty, and Tomcat will stop accepting requests at the network layer. Undertow will accept requests but respond immediately with a service unavailable (503) response.
-
不同服务器有不同的行为:
-
Jetty, Reactor Netty, Tomcat:停止接收请求,客户端新请求超时
-
Undertow:接收请求但回复503
-
配置
- 开启优雅关闭:
- graceful:优雅停机
- immediate:立即停机
server:
shutdown: graceful
- 设置缓冲器(超时后无论线程任务是否执行完毕都会停机处理):
spring:
lifecycle:
timeout-per-shutdown-phase: 20s
使用
- 执行
kill -2 $PID
或kill -15 $PID
2021-06-29 19:39:51.724 INFO 29534 --- [extShutdownHook] o.s.b.w.e.tomcat.GracefulShutdown : Commencing graceful shutdown. Waiting for active requests to complete
2021-06-29 19:39:51.732 INFO 29534 --- [tomcat-shutdown] o.s.b.w.e.tomcat.GracefulShutdown : Graceful shutdown complete
PS:
- kill -2 相当于快捷键 Ctrl + C 会触发 Java的 ShutdownHook 事件处理
- kill -9,强制杀死进程,不会执行 ShutdownHook
方式二:调用actuator提供的接口
Spring Boot includes a number of additional features to help you monitor and manage your application when you push it to production. You can choose to manage and monitor your application by using HTTP endpoints or with JMX. Auditing, health, and metrics gathering can also be automatically applied to your application.
- 请求**/actuator/shutdown**执行优雅停机
引入maven依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
配置
management:
endpoint:
shutdown:
enabled: true
endpoints:
web:
exposure:
include: "shutdown"
-
management.endpoint.shutdown.enabled
:是否启动shutdown功能,默认false -
management.endpoints.web.exposure.include
:暴露actuator的shutdown端口- 可以把配置中的
shutdown
换成其他,比如*
(全部端点)、health
(健康检查)、info
(统计)等
- 可以把配置中的
使用
- 发起POST请求至
/actuator/shutdown
curl 'http://localhost:8080/actuator/shutdown' -i -X POST
回得到以下结果:
HTTP/1.1 200 OK
Content-Type: application/vnd.spring-boot.actuator.v3+json
Content-Length: 41
{
"message" : "Shutting down, bye..."
}
服务日志:
2021-06-29 19:39:51.724 INFO 29534 --- [extShutdownHook] o.s.b.w.e.tomcat.GracefulShutdown : Commencing graceful shutdown. Waiting for active requests to complete
2021-06-29 19:39:51.732 INFO 29534 --- [tomcat-shutdown] o.s.b.w.e.tomcat.GracefulShutdown : Graceful shutdown complete