getTraceAsString()
Aprenda o método getTraceAsString() do PHP: como ele retorna o rastreamento de pilha de uma exceção como string, como ler a saída e como registrá-la.
O que getTraceAsString() faz
getTraceAsString() é um método disponível em toda exceção PHP (qualquer classe que
implemente Throwable — Exception, Error e suas subclasses). Ele retorna o
rastreamento de pilha — a cadeia de chamadas de funções e métodos que estavam ativas no momento em que a
exceção foi lançada — formatado como uma única string legível por humanos.
O rastreamento de pilha responde à pergunta "como a execução chegou aqui?" Quando algo é lançado
profundamente no seu código, a mensagem sozinha (getMessage()) diz o que deu errado, mas
o rastreamento mostra o caminho exato de chamadas que levou até ele. Isso o torna a informação mais
útil ao depurar um erro que você não consegue reproduzir facilmente.
getTraceAsString() é a versão em string de getTrace(), que
retorna as mesmas informações como um array estruturado. Use getTrace() quando precisar inspecionar
frames individuais programaticamente; use getTraceAsString() quando quiser apenas algo para
registrar ou imprimir.
Sintaxe
public Throwable::getTraceAsString(): stringNão recebe argumentos e é final nas classes base Exception e Error, portanto
sempre retorna o formato de rastreamento padrão do PHP. Você o chama em um objeto de exceção capturado dentro de um
bloco catch:
<?php
try {
// Code that may throw an exception
} catch (Throwable $e) {
$trace = $e->getTraceAsString();
}Capturar Throwable (em vez de apenas Exception) significa que você também lida com objetos Error
como TypeError e DivisionByZeroError. Veja o capítulo Exception
para a hierarquia completa.
Um Exemplo Completo e Executável
Este script lança uma exceção dois níveis abaixo para que você possa ver como a string de rastreamento realmente fica:
<?php
function loadUser(int $id): array
{
throw new InvalidArgumentException("No user with id $id");
}
function handleRequest(): void
{
loadUser(42);
}
try {
handleRequest();
} catch (Throwable $e) {
echo $e->getTraceAsString();
}Saída:
#0 /app/index.php(10): loadUser(42)
#1 /app/index.php(14): handleRequest()
#2 {main}Lendo a Saída
Cada linha é um frame na pilha de chamadas, listado do mais interno para o mais externo:
#0,#1, … — o número do frame.#0é a chamada que estava em execução quando a exceção foi lançada; números maiores são os chamadores acima dela./app/index.php(10)— o arquivo e o número de linha do local da chamada.loadUser(42)— a função ou método que foi chamado, com seus argumentos. Argumentos de string longos são truncados (p. ex.'/etc/app/missin...') para manter o rastreamento legível.#2 {main}— o frame final especial que marca o script de nível superior (o escopo global).
O local do lançamento em si (o arquivo e linha exatos onde throw foi executado) não está nesta string —
ele está em getFile() e getLine().
Exemplos
Exemplo 1: Registrando o Rastreamento em um Arquivo
Em produção você raramente quer mostrar um rastreamento ao usuário — você o registra para análise posterior. Combine a mensagem, o arquivo e a linha com o rastreamento para um registro completo:
<?php
try {
// Code that may throw an exception
} catch (Throwable $e) {
$entry = sprintf(
"[%s] %s in %s:%d\n%s\n\n",
date('Y-m-d H:i:s'),
$e->getMessage(),
$e->getFile(),
$e->getLine(),
$e->getTraceAsString()
);
file_put_contents('/path/to/app.log', $entry, FILE_APPEND | LOCK_EX);
}LOCK_EX evita que duas requisições simultâneas intercalem suas entradas de log. Para
aplicações reais uma biblioteca de logging como Monolog é preferível, mas os dados subjacentes são a
mesma string que você obtém aqui.
Exemplo 2: Exibindo o Rastreamento no Navegador (Somente em Desenvolvimento)
Ao trabalhar localmente pode ser útil imprimir o rastreamento diretamente na página. Envolva-o em
<pre> para que as quebras de linha sejam preservadas, e escape-o para que o conteúdo do rastreamento não possa injetar HTML:
<?php
try {
// Code that may throw an exception
} catch (Throwable $e) {
echo '<pre>' . htmlspecialchars($e->getTraceAsString()) . '</pre>';
}Nunca exponha rastreamentos a usuários finais em produção — eles revelam caminhos de arquivo, estrutura do código e às vezes valores de argumentos que ajudam atacantes. Proteja isso com uma verificação de ambiente.
Exemplo 3: Preservando o Rastreamento em Re-lançamentos
Quando você captura uma exceção de baixo nível e lança uma mais significativa, passe a original como a exceção anterior para que seu rastreamento não seja perdido:
<?php
try {
// some database call that throws PDOException
} catch (PDOException $e) {
throw new RuntimeException('Could not load the report', 0, $e);
}A nova RuntimeException tem seu próprio rastreamento, enquanto
getPrevious() devolve a exceção original (e seu
getTraceAsString()). O manipulador padrão de exceções não capturadas do PHP imprime ambas, encadeadas.
Armadilhas Comuns
- O rastreamento descreve o ponto do lançamento, não o ponto de captura. Ele é fixado no momento em que a
exceção é construída, portanto chamar
getTraceAsString()mais tarde ainda mostra onde a exceção se originou, não onde você a tratou. - Argumentos podem ser truncados ou ocultados. Strings longas são encurtadas; com a
configuração INI
zend.exception_ignore_argsativada (padrão em muitas configurações de produção), os valores dos argumentos são omitidos inteiramente por segurança. - Retorna uma string, nunca
null. Mesmo para uma exceção lançada no nível superior você obtém pelo menos o frame#0 {main}.
Métodos Relacionados
getTrace()— os mesmos dados como um array estruturado.getMessage()— a mensagem de erro legível por humanos.getCode()— o código numérico da exceção.getPrevious()— a exceção anterior encadeada.set-exception-handler()— tratar exceções não capturadas globalmente.
Conclusão
getTraceAsString() transforma a pilha de chamadas de uma exceção em uma string compacta e registrável, tornando-a
uma das ferramentas mais valiosas para diagnosticar erros em PHP. Combine-a com getMessage(),
getFile() e getLine() para capturar um quadro completo de cada falha, registre-a em vez de
mostrá-la a usuários em produção, e preserve a cadeia com getPrevious() sempre que você
fizer um re-lançamento.