Estou tentando garantir que meu aplicativo Java tome medidas razoáveis para ser robusto, e parte disso envolve o desligamento normal. Estou lendo sobre ganchos de desligamento e na verdade não entendo como utilizá-los na prática.
Existe um exemplo prático por aí?
Digamos que eu tenha um aplicativo realmente simples como este abaixo, que grave números em um arquivo, 10 em uma linha, em lotes de 100, e quero garantir que um determinado lote termine se o programa for interrompido. Entendo como registrar um gancho de desligamento, mas não faço ideia de como integrá-lo ao meu aplicativo. Alguma sugestão?
package com.example.test.concurrency;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.PrintWriter;
public class GracefulShutdownTest1 {
final private int N;
final private File f;
public GracefulShutdownTest1(File f, int N) { this.f=f; this.N = N; }
public void run()
{
PrintWriter pw = null;
try {
FileOutputStream fos = new FileOutputStream(this.f);
pw = new PrintWriter(fos);
for (int i = 0; i < N; ++i)
writeBatch(pw, i);
}
catch (FileNotFoundException e) {
e.printStackTrace();
}
finally
{
pw.close();
}
}
private void writeBatch(PrintWriter pw, int i) {
for (int j = 0; j < 100; ++j)
{
int k = i*100+j;
pw.write(Integer.toString(k));
if ((j+1)%10 == 0)
pw.write('\n');
else
pw.write(' ');
}
}
static public void main(String[] args)
{
if (args.length < 2)
{
System.out.println("args = [file] [N] "
+"where file = output filename, N=batch count");
}
else
{
new GracefulShutdownTest1(
new File(args[0]),
Integer.parseInt(args[1])
).run();
}
}
}
java
shutdown-hook
Jason S
fonte
fonte
Respostas:
Você pode fazer o seguinte:
.interrupt
os threads de trabalho, se aguardarem dados em alguma chamada de bloqueio)writeBatch
a conclusão dos threads de trabalho (executando no seu caso) chamando oThread.join()
método nos threads de trabalho.Algum código incompleto:
static volatile boolean keepRunning = true;
Em run () você muda para
Em main () você adiciona:
É mais ou menos assim que eu faço um gracioso "rejeitar todos os clientes ao pressionar Control-C" no terminal.
Dos documentos :
Ou seja, um gancho de encerramento mantém a JVM em execução até que o gancho seja finalizado (retornado do método run ()) .
fonte
mainThread
é um encadeamento daemon, entãojoin
garantimos que aguardamos o término antes de deixar a JVM encerrar.Ganchos de desligamento são threads não iniciados registrados com Runtime.addShutdownHook (). A JVM não oferece nenhuma garantia na ordem em que os ganchos de desligamento são iniciados.Para obter mais informações, consulte http://techno-terminal.blogspot.in/2015/08 /shutdown-hooks.html
fonte