问题描述
我希望有一个配置文件,其中包含通过API获取的数据进行设置的变量.
I would like to have a configuration file with variables set with data I fetch from an API.
我认为我必须使用async
和await
功能,否则我的变量将保持不确定状态.
I think I must use async
and await
features to do so, otherwise my variable would stay undefined.
但是我不知道如何集成它并使节点exports.myVariable = myData
在async function
中可用?
But I don't know how to integrate this and keep the node exports.myVariable = myData
available within an async function
?
下面是我尝试编写的代码(都在同一文件中):
Below is the code I tried to write to do so (all in the same file) :
const fetchAPI = function(jsonQuery) {
return new Promise(function (resolve, reject) {
var reqOptions = {
headers: apiHeaders,
json:jsonQuery,
}
request.post(apiURL, function (error, res, body) {
if (!error && res.statusCode == 200) {
resolve(body);
} else {
reject(error);
}
});
});
}
var wallsData = {}
const fetchWalls = async function (){
var jsonQuery = [{ "recordType": "page","query": "pageTemplate = 1011"}]
let body = await utils.fetchAPI(jsonQuery)
let pageList = await body[0].dataHashes
for(i=0;i<pageList.length;i++){
var page = pageList[i]
wallsData[page.title.fr] = [page.difficultyList,page.wallType]
}
return wallsData
throw new Error("WOOPS")
}
try{
const wallsData = fetchWalls()
console.log(wallsData)
exports.wallsData = wallsData
}catch(err){
console.log(err)
}
console.log(wallsData)
的输出显示为Promise { <pending> }
,因此无法解析,并且在wallsData中没有数据的情况下仍继续执行配置文件...
The output of console.log(wallsData)
shows Promise { <pending> }
, therefore it is not resolved and the configuration file keep being executed without the data in wallsData...
我想念什么?
谢谢,干杯
推荐答案
promise是一个特殊的对象,它要么成功要么失败,要么失败. async-await-syntax是语法糖,可帮助兑现承诺.
A promise is a special object that either succeeds with a result or fails with a rejection. The async-await-syntax is syntactic sugar to help to deal with promises.
如果您将函数定义为aync,则始终都会返回承诺.
If you define a function as aync it always will return a promise.
即使是这样的函数,其读取结果也类似
Even a function like that reads like
const foo = async() => {
return "hello";
}
返回一个字符串的承诺,而不仅仅是一个字符串.您需要等待它解决或拒绝.
returns a promise of a string, not only a string. And you need to wait until it's been resolved or rejected.
类似于:
const foo = async() => {
return Promise.resolve("Hello");
}
或:
const foo = async() => {
return new Promise(resolve => resolve("Hello"));
}
您的fetchWalls
同样是一个承诺,将持续一段时间.您必须通过在外部作用域中设置then
或catch
处理程序来确保它成功还是失败:
Your fetchWalls
similarly is a promise that will remain pending for a time. You'll have to make sure it either succeeds or fails by setting up the then
or catch
handlers in your outer scope:
fetchWalls()
.then(console.log)
.catch(console.error);
外部作用域永远不会异步,因此您不能在那里使用await.您只能在其他异步函数中使用await.
The outer scope is never async, so you cannot use await there. You can only use await inside other async functions.
对于外部作用域承诺处理,我也不会使用try-catch.我认为您会混淆打算在内部异步函数中使用的try-catch方法,因为该方法有助于避免嵌套和类似同步代码的读取:
I would also not use your try-catch for that outer scope promise handling. I think you are confusing the try-catch approach that is intended to be used within async functions, as there it helps to avoid nesting and reads like synchronous code:
例如您可以在fetchWalls
定义内进行操作:
E.g. you could do inside your fetchWalls
defintion:
const fetchWalls = async function (){
var jsonQuery = [{ "recordType": "page","query": "pageTemplate = 1011"}]
try {
let body = await utils.fetchAPI(jsonQuery)
} catch(e) {
// e is the reason of the promise rejection if you want to decide what to do based on it. If you would not catch it, the rejection would chain through to the first error handler.
}
...
}
这篇关于NodeJS异步/等待-使用API调用构建配置文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!