How to return data from the done() callback when working with Airtable.js?


#1

(This is a copy of my question on Stackoverflow. It’s not getting any attention there so I decided to bring it here.)

First, let me start with what I want to achieve. I want to query a table in Airtable that includes data from a linked table. Airtable returns the IDs of records in linked tables so I need to do a second lookup on each of those records to get the data I want (e.g. Name). Ultimately, I want to return to the client the ID and the other fields from the linked record. Problem is, I’m failing to achieve this because of the asynchronous nature of the API and my lack of understanding.

The best I’ve been able to do so far is execute a bit of code in the done() callback of their API. The problem is that this isn’t scalable because it means I’ll get myself into callback-hell. (At least, that’s what I think I’ve been able to determine so far.)

Here’s my code (FYI this is code to be run in an Azure Function):

var Airtable = require("airtable");
var airtableApiKey = process.env.airtableApiKey;

module.exports = function (context, req) {
  context.log('JavaScript HTTP trigger function processed a request.');

  var base = new Airtable({
    apiKey: airtableApiKey
  }).base('appBASEID');
  var resultObj;
  var accumulator = [];

  base('Products').select({
    sort: [{
      field: 'Identifier',
      direction: 'asc'
    }]
  }).eachPage(function page(records, fetchNextPage) {
    records.forEach(function (record) {
      context.log('Retrieved ', record.get('Identifier'));
      context.log('Retrieved ', record.get('Vendor'));

      accumulator.push(record._rawJson);

      // base('Vendors').find(record.get('Vendor')[0], function( err, record) {
      //   if (err) { context.error(err); return; }
      //   context.log(record.get('Name'));
      // });
    });
    fetchNextPage();
  }, function done(error) {

    context.res = {
      // status: 200, /* Defaults to 200 */
      body: JSON.parse(JSON.stringify(accumulator))
    };

    context.done();
  });
};

You can see that I’ve commented some lines in the .eachPage() section because, as I learned while working on this, that code doesn’t execute in the order I expected it to.

How can I foreach through accumulator and .find() the records I need?