2012-08-25 22 views
6

¿Hay alguna manera posible de agregar swing a un gancho de apagado (es decir, mostrar una ventana emergente cuando se apaga la máquina virtual)?¿Cómo uso el columpio en un gancho de cierre?

Me doy cuenta de que si trato de crear un nuevo JFrame, me dará un error, ya que intenta registrar un gancho de apagado, que falla ya que el VM ya se está cerrando. Me pregunto si hay, de hecho, cualquier forma de evitar esto

+3

Yo diría que no, e incluso si coud, te recomiendo que no te – MadProgrammer

+0

@MadProgrammer He mirado alrededor, y no pude encontrar nada, pero estaba pensando que debería ser posible ya que muchas aplicaciones le proporciono una ventana emergente, no solo al cerrarla, sino como si apagara la computadora (que a su vez apaga la máquina virtual de Java) –

+0

Hace poco, un programa arrojó una excepción porque un desarrollador estaba accediendo a un Componente de oscilación dentro de un enlace cerrado (bajo Java 7, creo). Diría que podría tener un problema al tratar de seguir este concepto. Parte del problema es no saber en qué estado se encuentra realmente la JVM, o el orden en que se llaman los ganchos de cierre – MadProgrammer

Respuesta

13

Realmente no deberías estar haciendo esto.De the Runtime.addShutdownHook specification:

La máquina virtual Java apaga en respuesta a dos tipos de eventos:

  • El programa sale Normalmente, cuando las últimas salidas de rosca no daemon o cuando el exit (equivalente, System.exit) se invoca el método, o
  • La máquina virtual es terminada en respuesta a una interrupción del usuario, como escribir ^C, o un evento en todo el sistema, como el cierre de sesión del usuario o el cierre del sistema.

...

ganchos de apagado se ejecutan en un momento delicado en el ciclo de vida de una máquina virtual y, por tanto, deben codificarse defensiva. En particular, deben escribirse para que sean seguros para subprocesos y para evitar interbloqueos en la medida de lo posible. Tampoco deben confiar ciegamente en los servicios que pueden haber registrado sus propios ganchos de cierre y, por lo tanto, pueden estar ellos mismos en el proceso de cierre. Los intentos de utilizar otros servicios basados ​​en subprocesos, como el subproceso de despacho de eventos AWT, por ejemplo, pueden provocar interbloqueos.

Los ganchos de cierre también deben terminar su trabajo rápidamente. Cuando un programa invoca exit, la expectativa es que la máquina virtual se apague y salga de inmediato. Cuando la máquina virtual finaliza debido al cierre de sesión del usuario o al cierre del sistema, el sistema operativo subyacente solo puede permitir una cantidad fija de tiempo para cerrar y salir. Por lo tanto, no es aconsejable intentar ninguna interacción del usuario o realizar un cálculo de larga duración en un enlace de cierre.

...

En raras ocasiones la máquina virtual puede abortar , es decir, dejar de correr sin necesidad de apagar limpiamente. Esto ocurre cuando la máquina virtual finaliza externamente, por ejemplo con la señal SIGKILL en Unix o la llamada TerminateProcess en Microsoft Windows. La máquina virtual también puede abortar si un método nativo falla al, por ejemplo, corromper las estructuras internas de datos o intentar acceder a una memoria inexistente. Si la máquina virtual aborta, no se puede garantizar si se ejecutarán o no los ganchos de cierre.

advertencias específicas aquí que sugieren no hacen esto:

  1. "ganchos de apagado del PC también deben terminar su trabajo rápidamente."

    Basándose en nada que pudiera tomar un tiempo para hacer su trabajo, o bloquear indefinidamente en la facilidad de entrada como JOptionPane diálogos, es no lo que debe hacer en su gancho de cierre.

  2. "intentos de utilizar otros servicios basados ​​en la rosca como el AWT hilo evento de expedición, por ejemplo, puede conducir a puntos muertos"

    oscilación se ejecuta en la parte superior de AWT, cuyo subyacente evento de despacho el hilo también puede estar en proceso de cierre.Tratar de usar Swing o AWT mientras se apaga puede conducir no solo a bloqueos muertos sino que también puede no funcionar en absoluto, de todos modos.

  3. "Si la máquina virtual aborta entonces no se puede garantizar por si o no los ganchos de cierre se llevará a cabo"

    No hay garantías de que su usuario podría incluso, posiblemente, transmitir su mensaje, ya que los ganchos de cierre solo están garantizados para ejecutarse cuando sale normalmente o finaliza - no cuando se detiene o cancela.

+0

+1 nice some más información para el OP –

+1

+1 mucha información agradable y me encantó el resumen – MadProgrammer

+0

Esto es lo que había entendido antes, esperaba que hubiera una manera, pero supongo que no –

2
  1. Swing GUI que se debe hacer en Event Dispatch Thread, entonces

  2. Simple way, pero la acción del usuario final requerido (cerca JDialog)

+0

Me temo que no veo qué relevancia tiene tu respuesta para la pregunta original. –

+0

@DuncanJones Él lo está respondiendo. Su respuesta es sobre shutdown hook + enlaces a una posible solución ... –

+0

@mKorbel No veo cómo funcionaría la primera opción; No estoy llamando al cierre, está sucediendo como una ocurrencia aleatoria, solo quiero manejarlo con una ventana emergente. Para el segundo, veo cierto potencial en eso, sin embargo, ¿Runtime # exec funcionará cuando la JVM/computadora se cierre? –

2

Si lo hay, no le ayudará.

Los ganchos de cierre se invocan de forma asíncrona como parte del cierre de la JVM, por lo que un cuadro de diálogo "confirmar" no confirmará nada ya que no puede detener o revertir el proceso de apagado. Esperar a que un usuario tome una decisión no es el tipo de acción para la que está destinado un cierre. Un gancho de cierre en un programa interactivo no tiene sentido. El caso de uso real para los ganchos de cierre es:

para liberar recursos y otra limpieza cuando la JVM shutsdown

También es importante tener en cuenta el gancho de cierre suele siempre ser ejecutado, para más información, véase mi respuesta aquí: How to shutdown java application correctly from C# one

+0

A pesar de que se maneja de forma asíncrona, el hilo aún no es daemon y, por lo tanto, aún podría funcionar ... no es que debas __ever__ hacerlo. – oldrinb

+0

@veer cierto, pero supongo que el mayor problema al que se enfrentará el OP es que no todas las terminaciones de una aplicación invocarán al gancho de cierre –

-1

No estoy seguro de su pregunta, pero creo que es imposible ejecutar o mostrar una ventana emergente cuando JVM se está cerrando. Es como tratar de correr mientras te preparas para dormir? Solo adivinando. :)

4

Se supone que los ganchos de cierre se ejecutan lo más rápido posible. Eso no incluye esperar a que un usuario confirme un diálogo. En cualquier caso, no tiene garantía de que el hilo del evento Swing aún se esté ejecutando.

No puede hacer esto.

+0

+1 nice "no tienes garantía de que el hilo del evento Swing aún se esté ejecutando" –

Cuestiones relacionadas