关闭挂钩在 Eclipse 中不起作用

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/12836551/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-19 19:10:28  来源:igfitidea点击:

Shutdown hook doesn't work in Eclipse

javaeclipseshutdown-hook

提问by urir

I have added a shutdown hookvia:

我通过以下方式添加了关闭挂钩

Runtime.getRuntime().addShutdownHook(myShutdownHook);

It works fine normally, but not when I click the red stop button in Eclipse. Is there a way to make the shutdown hook be called in Eclipse?

它正常工作,但当我单击 Eclipse 中的红色停止按钮时就不行了。有没有办法在 Eclipse 中调用关闭钩子?

采纳答案by Zoltán

The red stop button forcibly kills the application, i.e. not gracefully, so the JVM doesn't know that the application is exiting, therefore the shutdown hooks are not invoked.

红色停止按钮强行杀死应用程序,即不优雅,因此JVM 不知道应用程序正在退出,因此不会调用关闭挂钩。

Unfortunately, there is no way (in Windows, at least) to provide a mechanism that ensures that the hook is always invoked. It's just something that may be invoked, but there is no guarantee.

不幸的是,没有办法(至少在 Windows 中)提供一种机制来确保始终调用钩子。这只是可以调用的东西,但不能保证。

回答by Marek Jagielski

I made a hack by replacing JavaProcess with decorated one:

我通过用装饰的 JavaProcess 替换 JavaProcess 进行了黑客攻击:

    IProcess p = launch.getProcesses()[0];
    launch.addProcess(new JavaProcessDecorator(p));
    launch.removeProcess(p);

And decorator is overriding terminate function.

而装饰器正在覆盖终止功能。

public class JavaProcessDecorator implements IProcess {

private IProcess p;

public JavaProcessDecorator(IProcess p) {
    this.p = p;
}

private boolean sigkill = false;

@SuppressWarnings("rawtypes")
@Override public Object        getAdapter(Class arg)                { return p.getAdapter(arg); }
...
@Override public ILaunch       getLaunch()                          { return p.getLaunch(); }
@Override public IStreamsProxy getStreamsProxy()                    { return p.getStreamsProxy(); }
@Override public void          setAttribute(String s1, String s2)   {        p.setAttribute(s1, s2); }
@Override public void          terminate() throws DebugException    {
    if(!sigkill) {
        try {
            IDebugIService cs = DirmiServer.INSTANCE.getRemote("main", IDebugIService.class);
            if(cs != null) cs.modelEvent(new TerminateRequest());
        } catch (RemoteException e) { }
        this.sigkill = true;
    } else p.terminate();
}}

At first click on red button, I send a message to application asking for gently termination. If it is not working, second click on red button will kill it.

首先点击红色按钮,我向应用程序发送一条消息,要求温和终止。如果它不起作用,第二次点击红色按钮将杀死它。

回答by Christoph142

I know I'm a bit late to the party, but I found this thread seeking for help and so will probably others.

我知道我参加聚会有点晚了,但我发现这个帖子正在寻求帮助,其他人也可能会寻求帮助。

We had the same issue and solved it with an Eclipse plugin(on Linux) which provides additional stop buttons now. I hope this serves all of you as well as it did help us :)

我们遇到了同样的问题,并使用Eclipse 插件(在 Linux 上)解决了它,该插件现在提供了额外的停止按钮。我希望这对你们所有人都有帮助,因为它确实帮助了我们:)

回答by Mubashar

Red stop button just terminates the application and according to eclipse devs they can't do anything about it see this issuein eclipse bug tracker.

红色停止按钮只是终止应用程序,根据 eclipse 开发人员的说法,他们无法做任何事情,在 eclipse 错误跟踪器中看到这个问题

回答by user2088211

@Pacerier - From the Javadoc: In rare circumstances the virtual machine may abort, that is, stop running without shutting down cleanly. This occurs when the virtual machine is terminated externally, for example with the SIGKILL signal on Unix or the TerminateProcess call on Microsoft Windows. The virtual machine may also abort if a native method goes awry by, for example, corrupting internal data structures or attempting to access nonexistent memory. If the virtual machine aborts then no guarantee can be made about whether or not any shutdown hooks will be run.

@Pacerier - 来自 Javadoc:在极少数情况下,虚拟机可能会中止,即在没有彻底关闭的情况下停止运行。当虚拟机在外部终止时会发生这种情况,例如在 Unix 上使用 SIGKILL 信号或在 Microsoft Windows 上使用 TerminateProcess 调用。如果本地方法出错,例如破坏内部数据结构或尝试访问不存在的内存,虚拟机也可能中止。如果虚拟机中止,则无法保证是否会运行任何关闭挂钩。

回答by SaurabhJinturkar

If you just want to test if the hook is working or not, throw new RuntimeException()from the trigger point. This should call the shutdown hook even from Eclipse.

如果您只想测试挂钩是否正常工作,请throw new RuntimeException()从触发点开始。这应该甚至从 Eclipse 调用关闭钩子。