Integrating Google Analytics with Several YouTube Videos Using the YouTube API

I’m trying to track 11 YouTube videos on my webpage using Google Analytics along with the YouTube API. I’ve attempted a few methods, but I’m not clear on how to effectively debug the tracking setup. My implementation utilizes the latest analytics.js version. Can anyone guide me on identifying the mistakes in my configuration?

HTML Example

<div style="margin-bottom: 24px;">
  <iframe id="video01" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video1Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video02" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video2Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video03" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video3Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video04" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video4Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video05" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video5Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video06" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video6Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video07" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video7Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video08" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video8Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video09" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video9Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video10" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video10Id?enablejsapi=1" frameborder="0"></iframe>
  <iframe id="video11" class="video-embed" width="340" height="220" src="https://www.youtube.com/embed/video11Id?enablejsapi=1" frameborder="0"></iframe>
</div>

JavaScript Snippet

$(function () {
  try {
    var scriptElement = document.createElement('script');
    scriptElement.src = "https://www.youtube.com/iframe_api";
    var firstScript = document.getElementsByTagName('script')[0];
    firstScript.parentNode.insertBefore(scriptElement, firstScript);

    var players = [];
    var videoDataList = [
      { id: 'video01', height: '390', width: '640', videoId: 'video1Id' },
      { id: 'video02', height: '390', width: '640', videoId: 'video2Id' },
      { id: 'video03', height: '390', width: '640', videoId: 'video3Id' },
      { id: 'video04', height: '390', width: '640', videoId: 'video4Id' },
      { id: 'video05', height: '390', width: '640', videoId: 'video5Id' },
      { id: 'video06', height: '390', width: '640', videoId: 'video6Id' },
      { id: 'video07', height: '390', width: '640', videoId: 'video7Id' },
      { id: 'video08', height: '390', width: '640', videoId: 'video8Id' },
      { id: 'video09', height: '390', width: '640', videoId: 'video9Id' },
      { id: 'video10', height: '390', width: '640', videoId: 'video10Id' },
      { id: 'video11', height: '390', width: '640', videoId: 'video11Id' }
    ];

    function onYouTubeIframeAPIReady() {
      if (typeof videoDataList === 'undefined') return;

      $.each(videoDataList, function (index, videoInfo) {
        var player = new YT.Player(videoInfo.id, {
          height: videoInfo.height,
          width: videoInfo.width,
          videoId: videoInfo.videoId,
          events: {
            'onReady': onPlayerReady,
            'onStateChange': onPlayerStateChange
          }
        });
        players.push(player);
      });
    }

    function onPlayerReady(event) {
      event.target.playVideo();
    }

    var isPlaying = false;
    function onPlayerStateChange(event) {
      if (event.data == YT.PlayerState.PLAYING) {
        ga('send', 'event', 'Video', 'Play', 'Video Tracking');
        isPlaying = true;
      }
      if (event.data == YT.PlayerState.PAUSED && isPlaying) {
        ga('send', 'event', 'Video', 'Pause', 'Video Tracking');
        isPlaying = false;
      }
      if (event.data == YT.PlayerState.ENDED) {
        ga('send', 'event', 'Video', 'End', 'Video Tracking');
      }
    }
  } catch (error) {
    console.error('Initialization error:', error);
  }
});

I’ve noticed some error messages in the browser console, but I’m uncertain of their meaning. Any tips for debugging the implementation would be greatly appreciated!

I’ve dealt with this YouTube API tracking mess before. The problem’s usually timing and video identification. Right now you’re tracking everything as ‘Video Tracking’ - that’s why Analytics can’t tell your 11 videos apart. You need unique identifiers for each video in your ga events. Also check if your Analytics property ID loads before the jQuery block runs. The iframe API loves to timeout with multiple players - try adding a small setTimeout delay between player initializations. Quick debug: open Chrome DevTools and type YT in the console after page load. If it’s undefined, your API script isn’t loading or something else is conflicting with it.

The problem is your onYouTubeIframeAPIReady function is stuck inside the jQuery document ready block. The YouTube API can’t find it there - move it outside so it’s global. Also, you’re auto-playing the video in onPlayerReady, which most users won’t expect. Let them click play themselves. For debugging: check the Network tab to make sure the YouTube API script actually loads, then look at Console for CORS errors or other API issues. One more thing - your HTML iframe dimensions don’t match what you set in JavaScript, so the video might look weird.

hey, just a tip - make sure your GA tracking code loads before any events trigger. also, try adding some console.logs in onPlayerStateChange to check if events fire. iframe API can be slow to load sometimes.

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.