2

I have two JS files running in a Node.js application.

In latlng.js I have this code:

async function getPlaceDetails(input) {

  var locationUrl = 'https://www.google.com';

  request(locationUrl, (error, response, body) => {
    if (!error && response.statusCode == 200) {
      let location_json = JSON.parse(body);
      let placeDetails = {
        lat: location_json.candidates[0].geometry.location.lat,
        lng: location_json.candidates[0].geometry.location.lng,
        name: location_json.candidates[0].name,
      }

      return placeDetails;
    }
    else {
      console.log("Error "+response.statusCode);
    }
  });
}

module.exports.getPlaceDetails = getPlaceDetails;

I'm exporting the function getPlaceDetails() from latlng.js so I can use it in app.js, see here:

var place = require('./latlng');

async function firstFunction(input){
    let data = await place.getPlaceDetails(input);
    return data;
};

async function secondFunction(input){
    let data = await firstFunction(input);
    // now wait for firstFunction to finish...
    console.log(data);
};

secondFunction('museum of modern art');

This returns undefined for me. I've been searching for hours today to get something other then undefined or Promise { undefined } but without success...

Ümit Kiliç
  • 35
  • 2
  • 7
  • " module.exports = getPlaceDetails; " ... it's correct export – Bonjov Feb 26 '19 at 21:28
  • `request` doesn't return a promise, so making `getPlaceDetails` into `async` doesn't help anything. Use the request-promise package instead. – Bergi Feb 26 '19 at 21:58

1 Answers1

2

Your getPlaceDetails function is callback-based and will not immediately return anything useful when you await it without a callback. Instead, you could "promisify" it to fit with the async/await pattern:

async function getPlaceDetails(input) {

 return new Promise((resolve, reject) => {
    var locationUrl = 'https://www.google.com';

    request(locationUrl, (error, response, body) => {
      if (!error && response.statusCode == 200) {
        let location_json = JSON.parse(body);
        let placeDetails = {
          lat: location_json.candidates[0].geometry.location.lat,
          lng: location_json.candidates[0].geometry.location.lng,
          name: location_json.candidates[0].name,
        }

        resolve(placeDetails);
      }
      else {
        console.log("Error "+response.statusCode);
        reject(new Error('something meaningful here'));
      }
    });
  });
}

module.exports.getPlaceDetails = getPlaceDetails;

jakemingolla
  • 1,613
  • 1
  • 10
  • 13
  • Thanks a lot @jakemingolla this one did it! Yet I don't really understand what happens with "promisifying" the `getPlaceDetails` function. Could you explain a bit more in detail what happens. – Ümit Kiliç Feb 27 '19 at 08:34
  • Check out http://bluebirdjs.com/docs/api/promise.promisify.html which has a pretty decent overview, plus a programatic way to apply this in the future! – jakemingolla Feb 27 '19 at 16:46
  • Thank you so much! – Ümit Kiliç Feb 27 '19 at 21:01