繁体   English   中英

数组推送导致空数组javascript

[英]array push results in empty array javascript

我正在尝试将API结果存储到数组中。

数据显示在控制台中,但在将数据推入数组时,数组仍为空。

这是代码:

app.post('/fetchFavoriteTweets/', verifyToken, function(req, res) {

var favorites = [];
  dbConn.then( function (database) {
            var dbo = database.db("twitter_search");
            dbo.collection('users').findOne(
              { _id: ObjectId(req.userId) }, function(err, result) {
                if(err) throw err;
                if(!result.hasOwnProperty('favorite_tweets')) {
                  res.status(404).json({msg:'record not found'});
                } 
                else {
                  result.favorite_tweets.forEach(function (tweet) {
                    T.get('statuses/show', {id: tweet.id}, function(err, data, response) {
                      if(!err){
                        favorites.push(data);
                        console.log(data); //this returns data
                      } else {
                        console.log(err);
                      }
                    });
                  });
                  console.log(favorites); 
                  // res.status(200).json({msg:'success', data:favorites});
                }
              });
    }).catch(function(e){console.log(e)})
});

看起来您正在函数回调范围内定义favorites数组。 尝试把var favorites = []; app.post()之上调用。

另外,请记住,在回调完成后它只会有一个值,因此后面的任何同步代码只会看到空数组值。

我已经更新了你的代码,通过单独存储承诺并随后调用它来获取收藏:

UPDATE

正如你在演示中看到的那样,我在底部有2x console.log,第一个( C1 )包含在promise favoritesPromise () ,第二个( C2 )包含在promise之后。 同步操作永远不会等待异步操作发生,因此在我的示例中, C2将始终在C1之前输出,即使console.log(1 ...)在console.log(2 ...)之前,它们也会在控制台中出现反转。

在promise中我添加了1ms的setTimeout来模拟一个请求,它只需要实现当前输出。 你可以测试的另一件事是删除setTimeout然后输出会改变一点,你的promise会变成同步,直到它达到resolve(favorites) ,这意味着favorites现在拥有所有数据,但是当resolve发生时,它变为异步,并且你的控制台你仍然会首先看到C2 (但现在有数据)和C1秒。

在我之前的回答中,我试图对你的代码实现这种推理。 保持它不同步的人!

 var favorites = []; var favoritesPromise = () => { return new Promise((resolve, reject) => { console.log('Retrieving data from the internet.'); // This timeout mocks your request to anything that is async or promie setTimeout(() => { console.log('Request done') let resultFavorite_tweets = [{ id: 1, name: 'a dog' }, { id: 2, name: 'a cat' }]; resultFavorite_tweets.forEach(item => { favorites.push(item.name); }) resolve(favorites); // if you have an error use // reject(err) }, 1); }); } favoritesPromise().then(favList => { console.log(1, 'this will always contain data from the internet, but will always be last', favList); }) console.log(2, 'this will be empty (unless you remove setTimeout), but will always be first', favorites); 

 app.post('/fetchFavoriteTweets/', verifyToken, function(req, res) {


  const favoritesPromise = () => {

    return new Promise((resolve, reject) => {

      var favorites = [];
      dbConn.then(function(database) {
        var dbo = database.db("twitter_search");
        dbo.collection('users').findOne({
          _id: ObjectId(req.userId)
        }, function(err, result) {
          if (err) reject(err);
          if (!result.hasOwnProperty('favorite_tweets')) {
            res.status(404).json({
              msg: 'record not found'
            });
          } else {
            result.favorite_tweets.forEach(function(tweet) {
              T.get('statuses/show', {
                id: tweet.id
              }, function(err, data, response) {
                if (!err) {

                  favorites.push(data);
                  console.log(data); //this returns data

                } else {

                  console.log(err);
                  reject(err);

                }

              });

              resolve(data);

            });
            console.log(favorites);
            // res.status(200).json({msg:'success', data:favorites});
          }
        });
      }).catch(function(e) {
        reject(e)
      })

    });

  }


  // Here you call the promise to retrieve "favorites"
  favoritesPromise().then(favoritesList => {

    console.log('your favorites array', favoritesList)

  })


})

尝试下一个代码

app.post('/fetchFavoriteTweets/', verifyToken, function (req, res) {
  var favorites = [];
  dbConn.then(function (database) {
    var dbo = database.db("twitter_search");
    dbo.collection('users').findOne(
      { _id: ObjectId(req.userId) }, function (err, result) {
        if (err) throw err;
        if (!result.hasOwnProperty('favorite_tweets')) {
          res.status(404).json({ msg: 'record not found' });
        }
        else {
          // Counter
          let count = result.favorite_tweets.length;
          result.favorite_tweets.forEach(function (tweet) {
            T.get('statuses/show', { id: tweet.id }, function (err, data, response) {
              // Decrease count
              count -= 1;
              if (!err) {
                favorites.push(data);
                // Check if count is zero
                if (count === 0) {
                  console.log(favorites);
                  res.status(200).json({msg:'success', data:favorites});        
                }
              } else {
                console.log(err);
              }
            });
          });
        }
      });
  }).catch(function (e) { console.log(e) })
});

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM