2012-01-09 34 views
3

更具体地说,我有一个多线程命令行Java应用程序,它运行并收集数据,直到用户终止它为止。什么是终止永久运行的命令行Java应用程序的干净/推荐的方式?

用户终止它的一个显而易见的方法是推送Control-C,但是接下来我需要在VM中安装关闭钩子并处理所有线程。

是否有更好的/更适合的方式让用户通知应用程序该关机了?

例如,是否有一种方法来捕获一些其他组合键并在我的应用程序中设置布尔标志?

作为进一步的澄清,我寻求功能上类似于在信号处理C.

+0

,我不知道这是否是正确与否:扩展Thread的'的run(){ while(!isInterrupted()){/ *在这里运行你的java代码* /}}}'然后,为扩展的Thread类调用interrupt()。 – 2012-01-09 07:17:43

+0

你不能依靠关机挂钩。看看Java监控和管理 – 2012-01-09 07:44:38

+0

@merlin:再次梅林,根据你想要的优雅的问题(清理资源并说再见,然后出来)。如果你想检测异常终止,你需要处理外部JVM边界即在操作系统级别。检测您的进程是否在Perl脚本内启动java进程,但让脚本使用waitpid系统调用等待JVM。 – 2012-01-09 09:53:58

回答

2

一种方法可以创建一个新的线程将“听”到标准输入的东西。根据您决定的任何关键模式,该线程可以在主应用程序中设置标志。

+0

我也想过这个,但是有一个线程只是听标准的,也感觉很恶心。有谁知道更好的方法来做到这一点? – merlin2011 2012-01-09 07:02:47

+0

不相信线程。如果OS默默地杀死正在监听的线程,该怎么办? – 2012-01-09 07:37:08

+0

@SureshSankar为什么OS要杀死线程? – Manish 2012-01-09 07:54:00

1

是否有更好/更合适的方式让用户通知 应用程序是否应该关闭了?

最好的办法是使用Java Monitoring and Management

看这个post例如。

最好不要依靠在Java关机hook.Shutdown钩工程KILL -15KILL并没有为KILL -9硬杀伤

0

工作,这是不是Java的具体解决方案,但(ATLEAST上Linux)时,操作系统会将SIGTERM发送到所有进程(在宽限期后由SIGKILL执行)。您的应用程序应该为此安装一个处理程序,然后正常关闭。一旦你这样做了,当你关闭虚拟机时它会自动照顾自己。

+0

Java可以捕获SIGTERM吗? – merlin2011 2012-01-09 07:28:09

+0

我从来没有用Java编码过,所以我不知道。但是,如果这是在UNIX上,这似乎是正确的做法。 – 2012-01-09 07:33:35

+0

@ merlin2011 - 根据anubhava的回答,是的。 – 2012-01-09 09:14:27

1

考虑使用关闭钩子是这样的:

Runtime.getRuntime().addShutdownHook(shutdownHook); 

有自己的代码在运行时的JVM在下列条件1终止:

  1. 程序正常退出时,如最后一个非守护进程线程退出或Runtime.exit()方法被调用时。
  2. 虚拟机响应用户中断(例如键入CTRL-C)或系统范围事件(例如用户注销或系统关闭)而终止(例如,JVM接收其中一个中断信号SIGHUP( Unix Only),SIGINT或SIGTERM)。

你可以参考:http://www.ibm.com/developerworks/ibm/library/i-signalhandling/了解更多详情(免责声明:很老本文适用于JDK 1.3.1)

+0

其他线程何时针对关闭挂接的运行时间运行?也就是说,关机挂钩或虚拟机是否等待活动线程完成? – merlin2011 2012-01-09 07:47:04

+0

如果非守护线程正在运行,那么JVM会在退出之前等待该线程完成。 – anubhava 2012-01-09 08:27:22