I am trying to get data from Airtable in my node.js app but I can't manage to get my results AFTER the resolution of my promise.
Here's my code:
async function getData(code) {
return await airtableBase("Data")
.select({
filterByFormula: `{code} = "${code}"`,
})
.firstPage((err, records) => {
if (err) {
console.log(err);
return {};
}
console.log(records[0].fields);
return records[0].fields;
});
}
stuff.map(async (object) => {
embedData = getEmbedData(object);
data = await getData(embedData.code);
console.log(data);
})
Here's what I get logged:
undefined
undefined
undefined
{
code: '1',
fullname: 'Test 1',
logo: '...'
}
{
code: '2',
fullname: 'Test 2',
logo: '...'
}
{
code: '3',
fullname: 'Test 3',
logo: '...'
}
you assume that
airtableBase(...).select(...).firstPage((error, result) => {})
returns a Promise - it doesn't
rarely does a function that takes a node style callback ... ie
function(error, result)
return a Promise
Change getData to return a Promise
function getData(code) {
return new Promise((resolve, reject) => {
airtableBase("Data")
.select({
filterByFormula: `{code} = "${code}"`,
})
.firstPage((err, records) => {
if (err) {
console.log(err);
return reject({});
}
console.log(records[0].fields);
resolve(records[0].fields);
});
});
}
also, with
stuff.map(async (object) => {
embedData = getEmbedData(object);
data = await getData(embedData.code);
console.log(data);
})
there's no guarantee the order will be correct, it probably will be in this case, but there's no guarantee
The above is better written
Promise.all(stuff.map((object) => {
embedData = getEmbedData(object);
return getData(embedData.code);
}))
.then(results => {
results.forEach(item => console.log(item));
})
or if that code is in a async
function
const results = await Promise.all(stuff.map((object) => {
embedData = getEmbedData(object);
return getData(embedData.code);
}))
results.forEach(item => console.log(item));
Note: absolutely no rejection testing done since your code doesn't, but really, you should try/catch (if using async/await) or .catch if using .then
Please note that
.firstPage
may actually return a Promise if no callback function is given, so your code may be simpler
function getData(code) {
return airtableBase("Data")
.select({
filterByFormula: `{code} = "${code}"`,
})
.firstPage()
.promise() /* this could be needed, again, depending on the library */
.then(records => {
return records[0].fields;
});
}
However, as you have not indicated anything about the db library you are using, I can't be sure the above will work
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.