guilima
guilima

Reputation: 186

YouTupe API V3, multiple youtube.playlistItems.list requests not in the same order

I'm using the javascript youtube API v3 to request 3 different playlists within some videos data. It's successfully working, but the method execute() is requesting the video data out of the order that was called in the looping (refresh the page). The code is pretty simple and can be debugged here, or if preferred here:

var playlistsID = [...]
for (var i = 0; i < playlistsID.length; i++) {
  function playlistItem() {
    var request = gapi.client.youtube.playlistItems.list({
      part: 'snippet',
      playlistId: playlistsID[i],
      maxResults: 4
    });

    request.execute(function(response) {
      if ('error' in response) {
        console.log(response.error.message);
      }
      else {
        for (var j = 0; j < response.items.length; j++) {
          showVideo(response.items[j]);
        }
      }
    });
  }
}

function showVideo(response) {
  var videoThumb = response.snippet.thumbnails.medium.url,
      container = document.getElementById("video-container"),
      videoDiv = document.createElement("div"),
      image = document.createElement("img");
  image.setAttribute("src", videoThumb);
  container.appendChild(videoDiv);
  videoDiv.appendChild(image);
}

My theory is that the execute() method is requesting the informations async, but if this is correct, What should I do to set a order in the requests?

Upvotes: 1

Views: 813

Answers (1)

Bertrand Martel
Bertrand Martel

Reputation: 45382

You can use Javascript Promise to wait for asynchronous request to be performed and use Bluebird library to loop them in the right order from this post :

var promiseFor = Promise.method(function(condition, action, value) {
  if (!condition(value)) return value;
  return action(value).then(promiseFor.bind(null, condition, action));
});

//Load and grant access to youtube api
function googleApiKey() {

  var apiKey = 'YOUR_API_KEY';
  gapi.client.setApiKey(apiKey);
  gapi.client.load('youtube', 'v3', function() {

    promiseFor(function(count) {
      return count < playlists.length;
    }, function(count) {
      return requestVideo(playlists[count])
        .then(function(response) {

          //show video
          for (var j = 0; j < response.items.length; j++) {
            showVideo(response.items[j]);
          }

          return ++count;
        }, function(error) {
          console.log(response.error.message);
        });
    }, 0).then(console.log.bind(console, 'all done'));
  });
}

function requestVideo(playlist) {

  return new Promise(function(resolve, reject) {

    var request = gapi.client.youtube.playlistItems.list({
      part: 'snippet',
      playlistId: playlist,
      maxResults: 4
    });

    request.execute(function(response) {

      if ('error' in response) {
        reject(Error(response.error.message));
      }
      else {
        resolve(response);
      }
    });
  });
}

Don't forget to add bluebird link

You can find a Fiddle here

Upvotes: 1

Related Questions