Como posso obter um rastreamento de pilha JavaScript quando ligo uma exceção?

519

Se eu mesmo lançar uma exceção JavaScript (por exemplo, throw "AArrggg"), como posso obter o rastreamento de pilha (no Firebug ou não)? Agora eu só entendi a mensagem.

edit : Como muitas pessoas abaixo postaram, é possível obter um rastreamento de pilha para uma exceção JavaScript, mas eu quero obter um rastreamento de pilha para minhas exceções. Por exemplo:

function foo() {
    bar(2);
}
function bar(n) {
    if (n < 2)
        throw "Oh no! 'n' is too small!"
    bar(n-1);
}

Quando fooé chamado, eu quero obter um rastreamento de pilha que inclui as chamadas para foo, bar, bar.

David Wolever
fonte
1
possível duplicata de Javascript rastreamento da pilha excepção
ripper234
O bug ainda está aberto no rastreador de erros do Firebug desde 2008: code.google.com/p/fbug/issues/detail?id=1260 - comece já!
Miller Medeiros
13
A resposta deve ser "lançar novo erro ('arrrgh');" veja esta página muito bem escrita: devthought.com/2011/12/22/a-string-is-not-an-error
elegant dice
1
(2013) Agora você pode obter rastreamentos de pilha no Firebug no Firefox, mesmo que seja simples throw 'arrrgh';, e eles parecem iguais throw new Error('arrrgh');. throw new Error('arrrgh');No entanto, o depurador do Chrome ainda precisa conforme indicado (mas o Chrome parece fornecer rastreamentos muito mais detalhados).
usar o seguinte comando
26
@ChetanSastry Eu pesquisei para 'rastreamento de pilha javascript' e este foi o primeiro resultado
David Sykes

Respostas:

756

Edição 2 (2017):

Em todos os navegadores modernos, você pode simplesmente ligar para: console.trace(); (Referência MDN)

Edição 1 (2013):

Uma solução melhor (e mais simples), como apontado nos comentários sobre a pergunta original, é usar a stackpropriedade de um Errorobjeto da seguinte maneira:

function stackTrace() {
    var err = new Error();
    return err.stack;
}

Isso irá gerar uma saída como esta:

DBX.Utils.stackTrace@http://localhost:49573/assets/js/scripts.js:44
DBX.Console.Debug@http://localhost:49573/assets/js/scripts.js:9
.success@http://localhost:49573/:462
x.Callbacks/c@http://localhost:49573/assets/js/jquery-1.10.2.min.js:4
x.Callbacks/p.fireWith@http://localhost:49573/assets/js/jquery-1.10.2.min.js:4
k@http://localhost:49573/assets/js/jquery-1.10.2.min.js:6
.send/r@http://localhost:49573/assets/js/jquery-1.10.2.min.js:6

Fornecendo o nome da função de chamada junto com o URL, sua função de chamada e assim por diante.

Original (2009):

Uma versão modificada deste snippet pode ajudar um pouco:

function stacktrace() { 
  function st2(f) {
    return !f ? [] : 
        st2(f.caller).concat([f.toString().split('(')[0].substring(9) + '(' + f.arguments.join(',') + ')']);
  }
  return st2(arguments.callee.caller);
}
Eugene Morozov
fonte
11
Não sei por que isso não foi votado mais - as outras respostas não funcionaram tão bem para mim. BTW, certifique-se de não argumentos tratar como um array (atualizado snippet aqui: gist.github.com/965603 )
ripper234
1
não está funcionando no chrome, tacktrace (): [Exceção: TypeError: Object # <Object> não tem método
hetaoblog
3
ver comentário na pergunta original: você não precisa de código personalizado, basta usar "throw new Error ( 'arrrgh')"
Joshua Richardson
16
Error.stack é indefinido no IE, só funciona no Chrome e Mozilla Firefox
Philipp Munin
4
Observe que calleragora está obsoleto e calleefoi removido do modo estrito do ES5. Aqui está o porquê stackoverflow.com/questions/103598/…
PhilT
187

Observe que o chromium / chrome (outros navegadores que usam a V8) e o Firefox possuem uma interface conveniente para obter um rastreamento de pilha através de uma propriedade de pilha nos objetos Erro .

try {
   // Code throwing an exception
} catch(e) {
  console.log(e.stack);
}

Aplica-se às exceções de base e às que você mesmo lança. (Considere que você usa a classe Error, que é uma boa prática).

Veja detalhes na documentação da V8

Jocelyn delalande
fonte
12
O Firefox também suporta a .stackpropriedade.
Kennytm 03/04
2
Eu gostaria de poder votar 100 vezes! Obrigado Jocelyn. Ele realmente ajudou muito
safrazik
1
você também pode usar console.error(e.stack);para que ele se parece com uma mensagem de exceção padrão
Bruno Peres
80

No Firefox, parece que você não precisa lançar a exceção. É o suficiente para fazer

e = new Error();
console.log(e.stack);
Justin L.
fonte
Funciona também em aplicativos móveis (criados usando JQM).
Samik R
Também funciona no Chromium (versão 43 de qualquer maneira).
Andy Beverley
No Firefox 59, isso não funciona quando chamado via window.onerror, mostra uma pilha quase vazia com apenas a onerrorfunção.
precisa saber é o seguinte
Ainda melhor, você poderia fazer: console.log(new Error().stack)> : (> :(> :(
Andrew
25

Se você possui o firebug, há uma opção de interrupção em todos os erros na guia script. Depois que o script atingir seu ponto de interrupção, você poderá olhar a janela da pilha do firebug:

captura de tela

Helephant
fonte
5
Hm, isso não parece funcionar. Ele me interrompe em um depurador devido a erros gerados pelo Javascript (por exemplo, erros variáveis ​​indefinidos), mas quando ligo minhas próprias exceções, ainda não recebo nada além da mensagem "Exceção não capturada".
23430 David Wolever
11

Uma boa (e simples) solução, conforme apontado nos comentários da pergunta original, é usar a stackpropriedade de um Errorobjeto da seguinte maneira:

function stackTrace() {
    var err = new Error();
    return err.stack;
}

Isso irá gerar uma saída como esta:

DBX.Utils.stackTrace@http://localhost:49573/assets/js/scripts.js:44
DBX.Console.Debug@http://localhost:49573/assets/js/scripts.js:9
.success@http://localhost:49573/:462
x.Callbacks/c@http://localhost:49573/assets/js/jquery-1.10.2.min.js:4
x.Callbacks/p.fireWith@http://localhost:49573/assets/js/jquery-1.10.2.min.js:4
k@http://localhost:49573/assets/js/jquery-1.10.2.min.js:6
.send/r@http://localhost:49573/assets/js/jquery-1.10.2.min.js:6

Fornecendo o nome da função de chamada junto com o URL e o número da linha, sua função de chamada e assim por diante.

Eu tenho uma solução realmente elaborada e bonita que eu criei para um projeto no qual estou trabalhando atualmente e extraí e refiz um pouco para generalizar. Aqui está:

(function(context){
    // Only global namespace.
    var Console = {
        //Settings
        settings: {
            debug: {
                alwaysShowURL: false,
                enabled: true,
                showInfo: true
            },
            stackTrace: {
                enabled: true,
                collapsed: true,
                ignoreDebugFuncs: true,
                spacing: false
            }
        }
    };

    // String formatting prototype function.
    if (!String.prototype.format) {
        String.prototype.format = function () {
            var s = this.toString(),
                args = typeof arguments[0],
                args = (("string" == args || "number" == args) ? arguments : arguments[0]);
            if (!arguments.length)
                return s;
            for (arg in args)
                s = s.replace(RegExp("\\{" + arg + "\\}", "gi"), args[arg]);
            return s;
        }
    }

    // String repeating prototype function.
    if (!String.prototype.times) {
        String.prototype.times = function () {
            var s = this.toString(),
                tempStr = "",
                times = arguments[0];
            if (!arguments.length)
                return s;
            for (var i = 0; i < times; i++)
                tempStr += s;
            return tempStr;
        }
    }

    // Commonly used functions
    Console.debug = function () {
        if (Console.settings.debug.enabled) {
            var args = ((typeof arguments !== 'undefined') ? Array.prototype.slice.call(arguments, 0) : []),
                sUA = navigator.userAgent,
                currentBrowser = {
                    firefox: /firefox/gi.test(sUA),
                    webkit: /webkit/gi.test(sUA),
                },
                aLines = Console.stackTrace().split("\n"),
                aCurrentLine,
                iCurrIndex = ((currentBrowser.webkit) ? 3 : 2),
                sCssBlack = "color:black;",
                sCssFormat = "color:{0}; font-weight:bold;",
                sLines = "";

            if (currentBrowser.firefox)
                aCurrentLine = aLines[iCurrIndex].replace(/(.*):/, "$1@").split("@");
            else if (currentBrowser.webkit)
                aCurrentLine = aLines[iCurrIndex].replace("at ", "").replace(")", "").replace(/( \()/gi, "@").replace(/(.*):(\d*):(\d*)/, "$1@$2@$3").split("@");

            // Show info if the setting is true and there's no extra trace (would be kind of pointless).
            if (Console.settings.debug.showInfo && !Console.settings.stackTrace.enabled) {
                var sFunc = aCurrentLine[0].trim(),
                    sURL = aCurrentLine[1].trim(),
                    sURL = ((!Console.settings.debug.alwaysShowURL && context.location.href == sURL) ? "this page" : sURL),
                    sLine = aCurrentLine[2].trim(),
                    sCol;

                if (currentBrowser.webkit)
                    sCol = aCurrentLine[3].trim();

                console.info("%cOn line %c{0}%c{1}%c{2}%c of %c{3}%c inside the %c{4}%c function:".format(sLine, ((currentBrowser.webkit) ? ", column " : ""), ((currentBrowser.webkit) ? sCol : ""), sURL, sFunc),
                             sCssBlack, sCssFormat.format("red"),
                             sCssBlack, sCssFormat.format("purple"),
                             sCssBlack, sCssFormat.format("green"),
                             sCssBlack, sCssFormat.format("blue"),
                             sCssBlack);
            }

            // If the setting permits, get rid of the two obvious debug functions (Console.debug and Console.stackTrace).
            if (Console.settings.stackTrace.ignoreDebugFuncs) {
                // In WebKit (Chrome at least), there's an extra line at the top that says "Error" so adjust for this.
                if (currentBrowser.webkit)
                    aLines.shift();
                aLines.shift();
                aLines.shift();
            }

            sLines = aLines.join(((Console.settings.stackTrace.spacing) ? "\n\n" : "\n")).trim();

            trace = typeof trace !== 'undefined' ? trace : true;
            if (typeof console !== "undefined") {
                for (var arg in args)
                    console.debug(args[arg]);

                if (Console.settings.stackTrace.enabled) {
                    var sCss = "color:red; font-weight: bold;",
                        sTitle = "%c Stack Trace" + " ".times(70);

                    if (Console.settings.stackTrace.collapsed)
                        console.groupCollapsed(sTitle, sCss);
                    else
                        console.group(sTitle, sCss);

                    console.debug("%c" + sLines, "color: #666666; font-style: italic;");

                    console.groupEnd();
                }
            }
        }
    }
    Console.stackTrace = function () {
        var err = new Error();
        return err.stack;
    }

    context.Console = Console;
})(window);

Confira no GitHub (atualmente v1.2)! Você pode usá-lo como ele Console.debug("Whatever");e, dependendo das configurações Console, imprimirá a saída e um rastreamento de pilha (ou apenas informações simples / nada extra). Aqui está um exemplo:

Console.js

Certifique-se de brincar com as configurações do Consoleobjeto! Você pode adicionar espaçamento entre as linhas do rastreamento e desativá-lo totalmente. Aqui está com Console.traceset para false:

Sem pistas

Você pode até desativar o primeiro bit de informação mostrado (definido Console.settings.debug.showInfocomo false) ou desativar a depuração totalmente (definido Console.settings.debug.enabledcomo false) para nunca mais precisar comentar uma instrução de depuração! Apenas deixe-os entrar e isso não fará nada.

Gabriel Nahmias
fonte
10

Eu não acho que exista algo embutido que você possa usar, no entanto, encontrei muitos exemplos de pessoas criando suas próprias.

Mark Biek
fonte
Ah, obrigado - o primeiro link que parece existir (embora a falta de suporte à recursão possa torná-lo impraticável).
267 David Wolever
Sim, não vi nenhuma recursão compatível à primeira vista. Ficarei curioso para ver se há uma boa solução para isso.
22630 Mark Biek
1
Eu acho que o segundo link deve suportar recursão para Firefox e Opera porque ele usa o rastreamento de pilha de erros em vez de criar manualmente um usando a variável argumentos. Gostaria de saber se você encontra uma solução entre navegadores para o problema de recursão (o primeiro artigo é meu). :)
Helephant
Helephant: O segundo não funcionará aqui porque, quando eu pego a exceção, é uma "string" (ou seja, não "e.stack"): foo = function () {throw "Arg"; } tente {foo (); } catch (e) {/ * typeof e == "string" * /} Talvez eu esteja jogando errado? (início do discurso obrigatória sobre o quão estúpido tutoriais JavaScript são ...)
David Wolever
Tente jogar um objeto: throw { name: 'NameOfException', message: 'He's dead, Jim' }.
Aaron Digulla 25/03
7

Você pode acessar as propriedades stack( stacktraceno Opera) de uma Errorinstância, mesmo que você a tenha lançado. O problema é que você precisa se certificar de que usa throw new Error(string)(não esqueça o novo em vez de throw string.

Exemplo:

try {
    0++;
} catch (e) {
    var myStackTrace = e.stack || e.stacktrace || "";
}
Eli Gray
fonte
O stacktrace não funciona no Opera. Eu nem consigo encontrar algo sobre isso.
NVI
@NV: Parece que o stacktrace não está nos erros criados pelo usuário; portanto, você deve fazer isso: tente {0 ++} catch (e) {myStackTrace = e.stack || e.stacktrace}
Eli Gray
7

Isso fornecerá um rastreamento de pilha (como matriz de cadeias) para os modernos Chrome, Opera, Firefox e IE10 +

function getStackTrace () {

  var stack;

  try {
    throw new Error('');
  }
  catch (error) {
    stack = error.stack || '';
  }

  stack = stack.split('\n').map(function (line) { return line.trim(); });
  return stack.splice(stack[0] == 'Error' ? 2 : 1);
}

Uso:

console.log(getStackTrace().join('\n'));

Exclui da pilha sua própria chamada e o título "Erro" usado pelo Chrome e Firefox (mas não pelo IE).

Não deve travar em navegadores mais antigos, mas apenas retornar a matriz vazia. Se você precisar de uma solução mais universal, consulte stacktrace.js . Sua lista de navegadores suportados é realmente impressionante, mas, na minha opinião, é muito grande para a pequena tarefa a que se destina: 37 KB de texto minificado, incluindo todas as dependências.

Konstantin Smolyanin
fonte
7

Uma atualização para a resposta de Eugene: O objeto de erro deve ser lançado para que o IE (versões específicas?) Preencha a stackpropriedade. O seguinte deve funcionar melhor que o exemplo atual e evitar retornar undefinedquando estiver no IE.

function stackTrace() {
  try {
    var err = new Error();
    throw err;
  } catch (err) {
    return err.stack;
  }
}

Nota 1: Esse tipo de coisa deve ser feito apenas durante a depuração e desativado quando ativo, especialmente se chamado com freqüência. Nota 2: Isso pode não funcionar em todos os navegadores, mas parece funcionar no FF e no IE 11, o que atende perfeitamente às minhas necessidades.

Patrick Seymour
fonte
6

Uma maneira de obter um rastreamento real da pilha no Firebug é criar um erro real, como chamar uma função indefinida:

function foo(b){
  if (typeof b !== 'string'){
    // undefined Error type to get the call stack
    throw new ChuckNorrisError("Chuck Norris catches you.");
  }
}

function bar(a){
  foo(a);
}

foo(123);

Ou use console.error()seguido de uma throwinstrução, pois console.error()mostra o rastreamento da pilha.

Miller Medeiros
fonte
4

Este código de polyfill funciona em navegadores modernos (2017) (IE11, Opera, Chrome, FireFox, Yandex):

printStackTrace: function () {
    var err = new Error();
    var stack = err.stack || /*old opera*/ err.stacktrace || ( /*IE11*/ console.trace ? console.trace() : "no stack info");
    return stack;
}

Outras respostas:

function stackTrace() {
  var err = new Error();
  return err.stack;
}

não está funcionando no IE 11!

Usando argument.callee.caller - não funciona no modo estrito em nenhum navegador!

Petr Varyagin
fonte
3

No Google Chrome (versão 19.0 e posterior), simplesmente lançar uma exceção funciona perfeitamente. Por exemplo:

/* file: code.js, line numbers shown */

188: function fa() {
189:    console.log('executing fa...');
190:    fb();
191: }
192:
193: function fb() {
194:    console.log('executing fb...');
195:    fc()
196: }
197:
198: function fc() {
199:    console.log('executing fc...');
200:    throw 'error in fc...'
201: }
202:
203: fa();

mostrará o rastreamento da pilha na saída do console do navegador:

executing fa...                         code.js:189
executing fb...                         code.js:194
executing fc...                         cdoe.js:199
/* this is your stack trace */
Uncaught error in fc...                 code.js:200
    fc                                  code.js:200
    fb                                  code.js:195
    fa                                  code.js:190
    (anonymous function)                code.js:203

Espero que esta ajuda.

Rabih Kodeih
fonte
3

função:

function print_call_stack(err) {
    var stack = err.stack;
    console.error(stack);
}

caso de uso:

     try{
         aaa.bbb;//error throw here
     }
     catch (err){
         print_call_stack(err); 
     }
Jaskey
fonte
2
<script type="text/javascript"
src="https://rawgithub.com/stacktracejs/stacktrace.js/master/stacktrace.js"></script>
<script type="text/javascript">
    try {
        // error producing code
    } catch(e) {
        var trace = printStackTrace({e: e});
        alert('Error!\n' + 'Message: ' + e.message + '\nStack trace:\n' + trace.join('\n'));
        // do something else with error
    }
</script>

este script mostrará o erro

Amir Buzo
fonte
2
function stacktrace(){
  return (new Error()).stack.split('\n').reverse().slice(0,-2).reverse().join('\n');
}
Denis Orlov
fonte
2
Embora esse código possa responder à pergunta, fornecer um contexto adicional sobre como e / ou por que resolve o problema melhoraria o valor a longo prazo da resposta.
Donald Duck
1

Meio atrasado para a festa, mas, eis uma outra solução, que detecta automaticamente se os argumentos.callee estão disponíveis e usa a nova pilha Error ()., Se não estiver. Testado em cromo, safari e firefox.

2 variantes - stackFN (n) fornece o nome da função n fora do chamador imediato, e stackArray () fornece uma matriz, stackArray () [0] sendo o chamador imediato.

Experimente em http://jsfiddle.net/qcP9y/6/

// returns the name of the function at caller-N
// stackFN()  = the immediate caller to stackFN
// stackFN(0) = the immediate caller to stackFN
// stackFN(1) = the caller to stackFN's caller
// stackFN(2) = and so on
// eg console.log(stackFN(),JSON.stringify(arguments),"called by",stackFN(1),"returns",retval);
function stackFN(n) {
    var r = n ? n : 0, f = arguments.callee,avail=typeof f === "function",
        s2,s = avail ? false : new Error().stack;
    if (s) {
        var tl=function(x) { s = s.substr(s.indexOf(x) + x.length);},
        tr = function (x) {s = s.substr(0, s.indexOf(x) - x.length);};
        while (r-- >= 0) {
            tl(")");
        }
        tl(" at ");
        tr("(");
        return s;
    } else {
        if (!avail) return null;
        s = "f = arguments.callee"
        while (r>=0) {
            s+=".caller";
            r--;   
        }
        eval(s);
        return f.toString().split("(")[0].trim().split(" ")[1];
    }
}
// same as stackFN() but returns an array so you can work iterate or whatever.
function stackArray() {
    var res=[],f = arguments.callee,avail=typeof f === "function",
        s2,s = avail ? false : new Error().stack;
    if (s) {
        var tl=function(x) { s = s.substr(s.indexOf(x) + x.length);},
        tr = function (x) {s = s.substr(0, s.indexOf(x) - x.length);};
        while (s.indexOf(")")>=0) {
            tl(")");
            s2= ""+s;
            tl(" at ");
            tr("(");
            res.push(s);
            s=""+s2;
        }
    } else {
        if (!avail) return null;
        s = "f = arguments.callee.caller"
        eval(s);
        while (f) {
            res.push(f.toString().split("(")[0].trim().split(" ")[1]);
            s+=".caller";
            eval(s);
        }
    }
    return res;
}


function apple_makes_stuff() {
    var retval = "iPhones";
    var stk = stackArray();

    console.log("function ",stk[0]+"() was called by",stk[1]+"()");
    console.log(stk);
    console.log(stackFN(),JSON.stringify(arguments),"called by",stackFN(1),"returns",retval);
    return retval;
}



function apple_makes (){
    return apple_makes_stuff("really nice stuff");
}

function apple () {
    return apple_makes();
}

   apple();
não sincronizado
fonte
1

Você pode usar esta biblioteca http://www.stacktracejs.com/ . É muito bom

Da documentação

Você também pode passar seu próprio erro para obter um rastreamento de pilha não disponível no IE ou Safari 5-

<script type="text/javascript" src="https://rawgithub.com/stacktracejs/stacktrace.js/master/stacktrace.js"></script>
<script type="text/javascript">
    try {
        // error producing code
    } catch(e) {
        var trace = printStackTrace({e: e});
        alert('Error!\n' + 'Message: ' + e.message + '\nStack trace:\n' + trace.join('\n'));
        // do something else with error
    }
</script>
Doua Beri
fonte
A fonte ligada https://rawgithub.com/stacktracejs/stacktrace.js/master/stacktrace.jsé uma versão antiga, a mais nova versão estável (correspondente ao trecho de código) está aqui:https://raw.githubusercontent.com/stacktracejs/stacktrace.js/stable/stacktrace.js
Frederic Leitenberger
1

Aqui está uma resposta que fornece desempenho máximo (IE 6+) e compatibilidade máxima. Compatível com IE 6!

    function stacktrace( log_result ) {
    	var trace_result;
    // IE 6 through 9 compatibility
    // this is NOT an all-around solution because
    // the callee property of arguments is depredicated
    /*@cc_on
    	// theese fancy conditinals make this code only run in IE
    	trace_result = (function st2(fTmp) {
    		// credit to Eugene for this part of the code
    		return !fTmp ? [] :
    			st2(fTmp.caller).concat([fTmp.toString().split('(')[0].substring(9) + '(' + fTmp.arguments.join(',') + ')']);
    	})(arguments.callee.caller);
    	if (log_result) // the ancient way to log to the console
    		Debug.write( trace_result );
    	return trace_result;
    @*/
    	console = console || Console;	// just in case
    	if (!(console && console.trace) || !log_result){
    		// for better performance in IE 10
    		var STerror=new Error();
    		var unformated=(STerror.stack || STerror.stacktrace);
    		trace_result = "\u25BC console.trace" + unformated.substring(unformated.indexOf('\n',unformated.indexOf('\n'))); 
    	} else {
    		// IE 11+ and everyone else compatibility
    		trace_result = console.trace();
    	}
    	if (log_result)
    		console.log( trace_result );
    	
    	return trace_result;
    }
// test code
(function testfunc(){
	document.write( "<pre>" + stacktrace( false ) + "</pre>" );
})();

Jack Giffin
fonte
0

É mais fácil obter um rastreamento de pilha no Firefox do que no IE, mas fundamentalmente, aqui está o que você deseja fazer:

Coloque o código "problemático" em um bloco try / catch:

try {
    // some code that doesn't work
    var t = null;
    var n = t.not_a_value;
}
    catch(e) {
}

Se você examinar o conteúdo do objeto "error", ele conterá os seguintes campos:

e.fileName: o arquivo / página de origem de origem do problema e.lineNumber: O número da linha no arquivo / página de origem do problema e.message: Uma mensagem simples descrevendo que tipo de erro ocorreu e.name: o tipo de erro que ocorreu, no exemplo acima, deve ser 'TypeError' e.stack: contém o rastreamento de pilha que causou a exceção

Espero que isso ajude você.

Michael
fonte
1
Errado. Ele está tentando pegar suas próprias exceções. Se ele lançar "asdfg", ele receberá um objeto string, não um objeto de exceção. Ele não está tentando capturar exceções embutidas.
Ivan Vučica 16/03/09
0

Eu tive que investigar uma recursão infinita no smartgwt com o IE11; portanto, para investigar mais profundamente, eu precisava de um rastreamento de pilha. O problema era que eu não conseguia usar o console de desenvolvimento, porque a reprodução era mais difícil dessa maneira.
Use o seguinte em um método javascript:

try{ null.toString(); } catch(e) { alert(e.stack); }
kirilv
fonte
alerta ((novo erro ()). pilha);
rich remer
0

Uau - não vejo uma única pessoa em 6 anos, sugerindo que verifiquemos primeiro para ver se stackestá disponível antes de usá-lo! A pior coisa que você pode fazer em um manipulador de erros é lançar um erro por chamar algo que não existe.

Como outros já disseram, embora stackseja mais seguro usar agora, não é suportado no IE9 ou anterior.

Registro meus erros inesperados e um rastreamento de pilha é bastante essencial. Para obter o máximo suporte, primeiro verifique se Error.prototype.stackexiste e é uma função. Nesse caso, é seguro usá-lo error.stack.

        window.onerror = function (message: string, filename?: string, line?: number, 
                                   col?: number, error?: Error)
        {
            // always wrap error handling in a try catch
            try 
            {
                // get the stack trace, and if not supported make our own the best we can
                var msg = (typeof Error.prototype.stack == 'function') ? error.stack : 
                          "NO-STACK " + filename + ' ' + line + ':' + col + ' + message;

                // log errors here or whatever you're planning on doing
                alert(msg);
            }
            catch (err)
            {

            }
        };

Edit: Parece que uma vez que stacké uma propriedade e não um método, você pode chamá-lo com segurança, mesmo em navegadores mais antigos. Ainda estou confuso, porque tinha certeza de que a verificação Error.prototypefuncionou para mim anteriormente e agora não funciona - então não tenho certeza do que está acontecendo.

Simon_Weaver
fonte
0

Usando o console.error(e.stack)Firefox mostra apenas o rastreamento de pilha nos logs, o Chrome também mostra a mensagem. Isso pode ser uma grande surpresa se a mensagem contiver informações vitais. Sempre registre os dois.

Christophe Roussy
fonte
0

Apenas tente

throw new Error('some error here')

Isso funciona muito bem para o chrome:

insira a descrição da imagem aqui

Anthony Zhan
fonte