使用 Spring Boot 执行器安全地关闭休息服务器?

Posted

技术标签:

【中文标题】使用 Spring Boot 执行器安全地关闭休息服务器?【英文标题】:Using the Spring Boot actuator to shutdown a rest server safely? 【发布时间】:2018-01-23 19:36:58 【问题描述】:

这是How to shutdown a Spring Boot Application in a correct way? 的后续问题

假设我们的服务器当前连接了 3 个客户端,并且每个客户端都在运行一个长时间的作业。然后我们使用以下命令关闭服务器:

curl -X POST localhost:port/shutdown

这样做:

A) 让服务器在关闭之前完成 3 个客户端正在运行的作业?

B) 禁止发生任何其他连接,从而导致服务器最终关闭?

【问题讨论】:

【参考方案1】:

Spring Boot 关闭端点调用这个类:org.springframework.boot.actuate.endpoint.ShutdownEndpoint,它调用你的ApplicationContext 上的close()。这反过来...

破坏豆子 关闭豆厂 停止嵌入的 servlet 容器

如果您的 bean 已订购并仔细编写了关闭方法,那么这应该没问题。但如果没有,那么在关闭周期的某个时刻,“3 个客户端正在运行的作业”可能会被中断。此外,在您调用关机和关机周期开始之间的小时间窗口内,可能会建立新的连接。

Spring 提供应用程序事件和侦听器挂钩,允许您参与关闭周期。 ContextClosedEvent bean 被销毁、嵌入式容器关闭等之前发布,因此您可以使用它在默认行为启动之前实现自己的关闭行为。例如:

public class ShutdownListener implements ApplicationListener<ContextClosedEvent> 
    @Override
    public void onApplicationEvent(ContextClosedEvent event) 
        // 
    

你可以这样实现这个监听器

拒绝带有 HTTP 503 的连接请求(或者如果您不处理 HTTP 请求,则与此等效) 在继续关闭周期之前暂停以允许任何正在进行的作业完成

您注册此侦听器的方式与您在 Spring Boot 中注册任何 ApplicationListener 的方式相同,例如

SpringApplication app = new SpringApplication(MyApplication.class);
app.addListeners(new ShutdownListener());

【讨论】:

“毁豆”是什么意思? @JoseMartinez 这意味着关闭它们或丢弃它们。使用术语“销毁”是因为 Spring 允许您定义一个 destroy-method,它保证在应用程序上下文关闭时代表您调用它。 如何以编程方式拒绝所有连接?

以上是关于使用 Spring Boot 执行器安全地关闭休息服务器?的主要内容,如果未能解决你的问题,请参考以下文章

独立休息服务的Spring Boot安全性[重复]

带有spring-boot安全休息api的角度2

从 Shell 脚本优雅地关闭 Spring Boot 应用程序

Spring Boot 休息 API

在spring boot微服务中,休息调用的调度不工作。

使用 CAS 保护 Spring Boot Rest 服务