Estou pensando em criar uma ferramenta de depuração para meu aplicativo Java.
Gostaria de saber se é possível obter um rastreamento de pilha, assim como, Exception.printStackTrace()
mas sem realmente lançar uma exceção?
Meu objetivo é, em qualquer método, despejar uma pilha para ver quem é o responsável pela chamada do método.
public static void dumpStack() { new Exception("Stack trace").printStackTrace(); }
stderr
, o que parece ser a implicação da pergunta.Se você deseja rastrear apenas o encadeamento atual (em vez de todos os encadeamentos no sistema, como a sugestão de Ram), faça:
Thread.currentThread (). getStackTrace ()
Para encontrar o chamador, faça:
E chame esse método de dentro do método que precisa saber quem é o responsável pela chamada. No entanto, uma palavra de aviso: o índice do quadro de chamada na lista pode variar de acordo com a JVM! Tudo depende de quantas camadas de chamadas existem no getStackTrace antes de você atingir o ponto em que o rastreamento é gerado. Uma solução mais robusta seria obter o rastreamento e iterar sobre ele, procurando o quadro para getCallingMethodName e, em seguida, dê dois passos adiante para encontrar o verdadeiro chamador.
fonte
Você pode obter um rastreamento de pilha como este:
Se você deseja acessar o quadro, pode usar t.getStackTrace () para obter uma matriz de quadros de pilha.
Esteja ciente de que esse rastreamento de pilha (como qualquer outro) pode estar faltando alguns quadros se o compilador de hotspot estiver ocupado otimizando as coisas.
fonte
t.printStackTrace
port.printStackTrace(System.out)
.new Throwable().printStackTrace(System.out);
log.log(Level.SEVERE, "Failed to do something", new Throwable());
Observe que Thread.dumpStack () realmente lança uma exceção:
fonte
Você também pode enviar um sinal para a JVM para executar Thread.getAllStackTraces () em um processo Java em execução, enviando um sinal QUIT para o processo.
No Unix / Linux, use:
kill -QUIT process_id
, em que process_id é o número do processo do seu programa Java.No Windows, você pode pressionar Ctrl-Break no aplicativo, embora normalmente não veja isso a menos que esteja executando um processo de console.
O JDK6 introduziu outra opção, o comando jstack, que exibirá a pilha de qualquer processo JDK6 em execução no seu computador:
jstack [-l] <pid>
Essas opções são muito úteis para aplicativos em execução em um ambiente de produção e não podem ser modificados facilmente. Eles são especialmente úteis para diagnosticar conflitos de tempo de execução ou problemas de desempenho.
http://java.sun.com/developer/technicalArticles/Programming/Stacktrace/ http://java.sun.com/javase/6/docs/technotes/tools/share/jstack.html
fonte
Se você precisar capturar saída
fonte
O Java 9 introduziu o
StackWalker
classes e de suporte para caminhar pela pilha.Aqui estão alguns trechos do Javadoc:
fonte
HPROF Java Profiler
Você nem precisa fazer isso no código. Você pode anexar o Java HPROF ao seu processo e, a qualquer momento, pressionar Control- \ para gerar heap dump, threads em execução, etc. . . sem estragar seu código de aplicativo. Isso está um pouco desatualizado, o Java 6 vem com o jconsole da GUI, mas ainda acho o HPROF muito útil.
fonte
A resposta de Rob Di Marco é de longe a melhor se você estiver satisfeito com a saída
stderr
.Se você deseja capturar para a
String
, com novas linhas de acordo com um rastreamento normal, faça o seguinte:fonte