Javascript 组件didcatch+;window.addEventListener(';error';,cb)don';I don’我没有表现得像预期的那样

Javascript 组件didcatch+;window.addEventListener(';error';,cb)don';I don’我没有表现得像预期的那样,javascript,reactjs,error-handling,Javascript,Reactjs,Error Handling,我的根组件上有一个componentDidCatch错误边界,以在发生可怕的事情时呈现一个漂亮的错误页面 但我也有一个窗口。addEventListener('error',cb)事件处理程序,以防更糟糕的事情发生(外部) 我现在的问题是,每当componentDidCatch获取错误时,窗口错误处理程序也会获取错误,因此我总是以最坏情况下的错误处理而不是“in-react”错误处理结束 此外,全局错误处理程序似乎在React错误边界之前触发,因此无法将错误标记为“已处理”,以便稍后手动忽略它

我的根组件上有一个
componentDidCatch
错误边界,以在发生可怕的事情时呈现一个漂亮的错误页面

但我也有一个
窗口。addEventListener('error',cb)
事件处理程序,以防更糟糕的事情发生(外部)

我现在的问题是,每当
componentDidCatch
获取错误时,
窗口
错误处理程序也会获取错误,因此我总是以最坏情况下的错误处理而不是“in-react”错误处理结束

此外,全局错误处理程序似乎在React错误边界之前触发,因此无法将错误标记为“已处理”,以便稍后手动忽略它

这是一个代码笔,显示了我的问题:

最简单的代码示例是:

类应用程序扩展了React.Component{
组件DIDCATCH(错误){
log('react handled error',err);
}
render(){
返回“foobar”;
}
}
addEventListener('error',err=>console.log('global error',err));
//错误时,我得到:
//“全局错误”,错误
//“反应已处理错误”,错误
相反,仅使用JavaScript,本地错误处理程序将阻止错误到达窗口错误处理程序

试试看{
抛出新错误(“错误”);
}捕捉(错误){
警报(“范围错误”);
}
addEventListener('error',()=>alert('global error'))

这是预期的行为吗?你能想出一种方法让它按照我的意愿工作吗?

似乎这只是一种
开发行为。请看一看

在开发环境中,React使用了一个技巧:捕获的异常是 抛出到一个伪DOM事件中,该事件由 但React实际上抓住了它们,使它们 不要向上传播(如果存在错误边界-否则 它们正在被回收)

由错误边界捕获的生产中错误保持捕获状态


我刚刚在
production
中测试了您的示例,并且
alert
render
方法中抛出
error
时不会显示。

您的代码通常会按其应有的方式运行
componentDidCatch
和您附加到文档的
eventListener
将捕获相同的错误,这就是它们当前所做的,它们的行为符合程序的预期,但出乎您的意料,
eventListener
捕获的实际场景是什么,而
componentDidMount
不会吗?@SultanH。我不希望
componentDidCatch
处理/捕获的错误反弹到
window
,因为它们是在React组件中处理的。React error boundary仅捕获渲染阶段发生的错误,而
窗口
错误处理程序将捕获任何其他未处理的错误(理论上)太好了,我查看了您的ErrorBoundry组件,我将重构问题,就在那里,让你知道在一段时间内发生了什么变化。你能在componentDidMount of Boundary component中注册监听器,然后你就可以在state中存储已处理的错误吗?@Zuber我真的需要尽可能广泛的错误处理逻辑,以捕获任何与React无关的内容。但是如果你想用一个例子来说明你的意思,那就太好了。这是一个非常有用的信息!它应该在文档中!(我将发送一份PR)PR:这个答案解释了意外行为,但我仍然在努力找出如何区分和处理React之外的错误,由于全局错误处理程序将在开发中调用,因此我提出了一个问题,讨论是否有一种方法可以使错误在生产和开发中表现相同: