当前位置: 首页 > 知识库问答 >
问题:

如何在JavaScript中从外部代码捕获所有内部错误?

罗翔
2023-03-14

我对JavaScript文件中的API(Node.js中运行的npm模块)进行了以下调用,我希望在其中捕获所有错误,以便能够优雅地处理它们。但是,如果(例如)传递了一个错误的API-KEY或一个不存在的城市名称,则该API的内部代码中存在一个错误,该错误未被try/catch捕获:

const weather = require('openweather-apis');

const getTemperature = (city, cbSuccess, cbFailure) => {
    try {
        weather.setLang('de');
        weather.setCity(city);
        weather.setUnits('metric');
        weather.setAPPID('BADKEY');
        weather.getTemperature((err, temperature) => {
            if (err) {
                console.log(err);
            } else {
                console.log(`The temperature in ${city} is ${temperature}° C.`);
            }
        });
    } catch (error) {
        console.log('there was an error');
    }

}

getTemperature('Berlin');

相反,显示错误并停止执行:

C:\edward\nwo\jsasync\node_modules\openweather-apis\index.js:162
      return callback(err,jsonObj.main.temp);
                                       ^

TypeError: Cannot read property 'temp' of undefined
    at C:\edward\nwo\jsasync\node_modules\openweather-apis\index.js:162:40
    at IncomingMessage.<anonymous> (C:\edward\nwo\jsasync\node_modules\openweather-apis\index.js:250:18)
    at IncomingMessage.emit (events.js:194:15)
    at endReadableNT (_stream_readable.js:1125:12)
    at process._tickCallback (internal/process/next_tick.js:63:19)

JavaScript中是否有一种方法可以像Java和C中那样捕获所有错误?

共有3个答案

司徒泰
2023-03-14

API内部代码有错误

  return callback(err,jsonObj.main.temp);
                                   ^
TypeError: Cannot read property 'temp' of undefined
  at C:\edward\nwo\jsasync\node_modules\openweather-apis\index.js:162:40

这显然是OpenWeatherAPI库中的一个bug。报告它。你很难解决这个问题。库需要检查jsonObjjsonObj。在尝试访问之前,存在main。temp,如果jsonObj看起来不符合预期,它应该调用您的回调,并显示一个错误。

孔运良
2023-03-14

如果异步代码中出现异常,那么您就不走运了。这将停止脚本的执行(如上所示)。

您正在使用的模块可能会以更好的方式处理错误,并在回调err参数中传递错误。除非你分叉代码或文件错误,否则你会被卡住。

同样的效果可以在这里演示:

async function testAsyncException() {
    try { 
        setTimeout(() => { 
            throw new Error("Error in asynchronous code"); 
        }, 100);
    } catch (e) {
        // This will never be caught...
        console.error("testAsyncException: A bad error occurred:", e);
    }
}

process.on('uncaughtException', (e) => { 
    console.log("uncaughtException:", e);
})

testAsyncException();

setTimeout调用周围的try... cat块不会处理生成的异常。

您可以“捕获”这种类型异常的唯一方法是使用这样的过程事件:

process.on('uncaughtException', (e) => { 
    console.log("uncaughtException:", e);
})

然而,这应该仅用于登录,然后退出。此时尝试恢复程序状态不是一个好主意,因为应用程序处于未知状态。

如果您使用的是非常有用的PM2之类的流程管理器,则脚本可以在出现错误时自动重新启动。

相反,如果我们尝试以下方法:

function testSyncException() {
    try { 
        throw new Error("Error in synchronous code");    
    } catch (e) {
        // This will be caught...
        console.error("testSyncException: A bad error occurred:", e);
    }
}

testSyncException();

我们可以看到异常将被捕获。

我强烈推荐这篇关于Node.js(Joyent)创建者错误处理的优秀文章:

https://www.joyent.com/node-js/production/design/errors

它详细介绍了处理操作错误和程序员错误的最佳策略。

宗政燕七
2023-03-14

我相信这样的事情可能会奏效:

async execute(weather, city, temperature) {
    return await new Promise(function(resolve, reject) {
        weather.getTemperature((err, temperature) => {
            if (err) {
                reject(err);
            } else {
                resolve(`The temperature in ${city} is ${temperature}° C.`);
            }
        });
    };
}

const getTemperature = async (city, cbSuccess, cbFailure) => {
    try {
        weather.setLang('de');
        weather.setCity(city);
        weather.setUnits('metric');
        weather.setAPPID('BADKEY');
        const res = await execute(weather, city, temperature);
        console.log(res);
    } catch (error) {
        console.log('there was an error');
    }
}
 类似资料:
  • 问题内容: 关于使用/的最佳实践,我有一个非常基本的问题。我有一个像这样的简单函数(DAO) 并在Web服务中使用DAO功能: OR最好在DAO函数中使用/,如下所示: 问题答案: 没有完美的规则。 如果需要尽早但尽可能晚地捕获异常,通常代码会更清晰,更简单。 您应该考虑在发生这种情况时谁必须采取行动,这决定了您是在方法(addVehicle)内进行操作还是调用方必须执行该操作。 例如: 在此示例

  • 问题内容: 很简单的问题,我如何在当前go代码运行的地方获得Pod? 我需要它是因为出于某种原因,我需要直接对Pod的代码执行ping操作,而不是使用我的常规端点(即负载平衡器)。 我当前的配置: 我试过了 但我可悲的是 紧急:禁止使用pods:用户“ system:serviceaccount:default:default”无法在名称空间“ default”中的API组“”中列出资源“ pod

  • 大多数新的android设备都有一个内部sdcard和一个外部sdcard。我想做一个文件资源管理器应用程序,但我不能找到如何获得路径使用在我的应用程序,因为 在大多数设备中只返回,但另一个外部sdcard有另一个路径,如。感谢任何帮助。

  • 问题内容: 通过使用Java Scripting API,我能够在Java中执行JavaScript。但是,有人可以解释一下我需要添加到此代码中以便能够调用C:/Scripts/Jsfunctions.js中的函数吗? 问题答案: 使用读剧本

  • 通过使用Java脚本API,我能够在Java中执行JavaScript。但是,有人能解释一下,为了能够调用C:/scripts/jsfunctions.js中的函数,我需要在这段代码中添加什么内容吗

  • 我正在使用C#和regex,试图捕获外部的paren组,同时忽略内部的paren组。我有遗留生成的文本文件,其中包含数千个字符串构造,如下所示: null