skip to Main Content

I’m currently trying to practice using an API with Twitter API.

I’m using Twit package to connect to twitters API but when I try to do a get request I get

Promise { pending }

I have tried using Async-Await but I’m not sure what I’m doing wrong here.

Here is my code:

const Twit = require('twit');
const twitterAPI = require('../secrets');


//Twit uses OAuth to stablish connection with twitter
let T = new Twit({
    consumer_key: twitterAPI.apiKey,
    consumer_secret: twitterAPI.apiSecretKey,
    access_token: twitterAPI.accessToken,
    access_token_secret: twitterAPI.accessTokenSecret
})

const getUsersTweets = async (userName) => {
    let params = { screen_name: userName, count: 1 }
    const userTweets = await T.get('search/tweets', params, await function (err, data, response) {
        if (err) {
            return 'There was an Error', err.stack
        }
        return data
    })
    return userTweets
}

console.log(getUsersTweets('Rainbow6Game'));

2

Answers


  1. From what I can see on your code, getUserTweets is an async function, so it will eventually return a promise. I’m assuming you will use this value on another function, so you will need to use it inside an async function and use await, otherwise you will always get a promise.

    const logTweets = async (username) => {
      try {
        const userTweets = await getUsersTweets(username);
        // Do something with the tweets
        console.log(userTweets);
      catch (err) {
        // catch any error
        console.log(err);
      }
    }
    

    If logging is all you want and you wrapped it inside a function in which you console.log it, you can call that function directly:

    logTweets('someUsername');
    
    Login or Signup to reply.
  2. Problem

    The biggest assumption that is wrong with the sample code is that T.get is expected to eventually resolve with some data.

    const userTweets = await T.get('search/tweets', params, await function (err, data, response) {
        if (err) {
            return 'There was an Error', err.stack
        }
        return data // 'data' returned from here is not necessarily going to be received in 'userTweets' variable
    })
    
    1. callback function provided as last argument in T.get function call doesn’t have to be preceded by an ‘await’.

    2. ‘data’ returned from callback function is not necessarily going to be received in ‘userTweets’ variable. It totally depends on how T.get is implemented and can not be controlled.

    Reason

    Thing to be noted here is that async / await works well with Promise returning functions which eventually get resolved with expected data, however, that is not guaranteed here

    Relying on the result of asynchronous T.get function call will probably not work because it returns a Promise { pending } object immediately and will get resolved with no data. The best case scenario is that everything with your function will work but getUsersTweets function will return ‘undefined’.

    Solution

    The best solution is to make sure that your getUsersTweets function returns a promise which eventually gets resolved with correct data. Following changes are suggested:

    const getUsersTweets = (userName) => {
      return new Promise ((resolve, reject) => {
        let params = { screen_name: userName, count: 1 }
        T.get('search/tweets', params, function (err, data, response) {
          if (err) {
            reject(err);
          }
          resolve(data);
        })
      }
    }
    

    The above function is now guaranteed to return expected data and can be used in the following way:

    const printTweets = async () => {
      const tweets = await getUsersTweet(userName);
      console.log(tweets);
    }
    
    printTweets();
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search