Dropwizard关闭钩子

7
问题在于,我通过ctrl + c停止了Dropwizard应用程序,并在主类中插入了一个Shutdown Hook,在关闭之前执行一些操作。但是现在应用程序的ServerConnector在我想做的事情之前被关闭了。
我有一个轮询服务(轮询我的资源之一),我需要告诉他们,应用程序即将关闭以防止一些问题。我需要在资源关闭前至少15秒钟的时间。
有什么解决这个问题的方法吗?
2个回答

9

您可以使用生命周期钩子来管理某些资源。

public class ManagedObject implements Managed {

    private final Object obj;

    public ManagedObject(Object obj) {
        this.obj = obj;
    }

    @Override
    public void start() throws Exception {
        // Do something to start the object
    }

    @Override
    public void stop() throws Exception {
        // Do something to stop the object
    }
}

接下来在环境上进行注册

ManagedObject myManagedObject = new ManagedObject(obj);
environment.lifecycle().manage(myManagedObject);

6

添加一个Dropwizard任务,该任务将更改静态字段的状态(或您想要传递数据的任何其他方式),您的轮询资源将使用该状态进行响应。

public class ShutdownTask extends Task {
    private int timeoutSeconds;

    public ShutdownTask (int timeoutSeconds) {
        super("shutdown");
        this.timeoutSeconds = timeoutSeconds;
    }

      @Override
    public void execute(ImmutableMultimap<String, String> parameters, PrintWriter output) throws Exception {
        // you probably can take the timeout parameter from the request via 'parameters' instead of the constructor.
        PollingResource.shuttingDownIn = timeoutSeconds;
    }
}


environment.admin().addTask(new ShutdownTask(15));

然后编写一个bash脚本,该脚本将curl到任务。
curl -X POST http://dw.example.com:8081/tasks/shutdown

还有:

  • 尽管人们不太喜欢 System.exit(0),但是你可以在执行方法中添加以下内容:

Thread.sleep(timeoutSeconds * 1000); System.exit(0)

  • 或者在 Bash 脚本中等待并杀死 Dropwizard 应用程序。

kill -SIGINT <pid>


是的,这不是我现在的做法,但服务器管理员或Linux服务停止命令仍将以“旧方式”停止应用程序。服务资源将立即关闭,我目前不知道如何解决它。 - heaphach
是的,触发任务的想法是将服务器置于“关闭”状态,以便资源仍然可用。然后,在服务器处于此状态时等待n秒钟,然后停止服务。 - Natan
但是如果你使用ctrl+c,资源仍然会被释放,而我想要避免这种情况 :-) - heaphach
2
如果应用程序不是以这种方式停止,会发生什么?那么我就有一个大问题,这就是为什么我需要另一种方式的原因 :-) - heaphach
1
托管对象并没有帮助我,或者说我使用方法不正确。问题仍然存在,即使我使用了托管对象,应用程序连接器仍然不允许新的连接。似乎应用程序连接器首先停止工作。 - heaphach
显示剩余3条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接