2011-03-13 81 views
1

一个一般性的问题,但有问题的代码是这样的:有没有办法在javascript中动态查看调用堆栈?

有被抛出一个错误例程 - 处理产生的异常:

MyObj.prototype.err = function(msg) { ... throw(msg); } 

这么扔,

if(mybad) this.err('my message'); 

想根据函数是否在调用堆栈中,err()的行为有所不同。

例如,可以是

funcA() -> func2() -> func3() -> err() 

funcB() -> func3() -> err() 

如果FuncA的行是上游,想以提醒用户和停止;而如果funcB想将消息写入控制台并继续。

实现其他的方式来解决问题,但恕我直言运气不好创建(和维护),可以从环境中推断

+0

+1分享您的体验:“运气不佳(可以推导出)并且可以推导出状态空间” – 2011-03-13 11:15:20

+0

[这里](http://eriwen.com/javascript/stacktrace-update/)是一篇有趣的博文。然而,因为我同意你的最后一句话,这看起来像是一种“不幸运”的方式,而且肯定会很慢。 – Pointy 2011-03-13 11:16:53

回答

0

在Chrome中,你可以做状态空间:

var err = function(msg) { 
    // ... 
    var error = new Error(); 
    var stack = error.stack; 
    // Do some string manipulation with stack 
    // mayThrow = 'funcB is in stack' 
    if (mayThrow) { 
    throw(msg); 
    } 
}; 

我可以指出我认为这是一个非常不好的做法。我认为你应该赶上FuncB中的错误,而不是将FuncB定义为不从err中抛出的函数。这是更少的代码,更容易管理。所以:

var err = function(msg) { 
    // ... 
    throw(msg); 
}; 

var func3 = function() { 
    // ... 
    err('Double rainbow'); 
}; 

var funcB = function() { 
    try { 
    func3(); 
    catch(e) { 
    console.log(e); 
    } 
}; 

试图理解为什么这是更好的解决方案,它是关于界定责任,其功能属于哪个功能。这正是为什么异常和处理的设计方式。

0

我不确定你想要解决什么问题,但我很肯定有一个更好的方法来做到这一点。

话虽这么说,这里的追踪功能,并检查调用栈,而不诉诸特定浏览器的堆栈跟踪的分析的一种方法:

var callstack = []; 

function traced(name, func) { 
    return function() { 
    callstack.push(name); 
    func.apply(this, arguments); 
    callstack.pop(); 
    } 
} 

,并使用它像这样:

var a = traced("a", function() { 
    b(); 
}); 

var b = traced("b", function() { 
    c(); 
}); 

var c = traced("c", function() { 
    var s = callstack.join("<br>"); 
    document.getElementById('output').innerHTML = s; 
}); 

document.getElementById('a').onclick = a; 
document.getElementById('b').onclick = b; 

你可以在此处查看:http://jsfiddle.net/AsrSp/

相关问题