YouTube 動画の再生回数とコメントのトラッキング

コーディング レベル: 初級
所要時間: 20 分
プロジェクト タイプ: 時間主導型トリガーによる自動化

目標

  • ソリューションの機能を理解します。
  • ソリューション内で Apps Script サービスが何を行うかを理解します。
  • スクリプトを設定します。
  • スクリプトを実行します。

このソリューションについて

このソリューションは、Google スプレッドシートで、公開 YouTube 動画のパフォーマンス(視聴回数、高評価、コメントなど)を追跡します。トリガーは毎日更新された情報を確認し、動画に新しいコメント アクティビティがある場合はメールを送信します。これにより、質問やコメントに対応できます。

Google スプレッドシートの YouTube データのスクリーンショット

仕組み

このスクリプトは、高度な YouTube サービスを使用して、各シートの [動画リンク] 列に記載されている動画 URL の YouTube 動画の詳細と統計情報を取得します。リストに登録されている動画のコメント数が増加した場合、スクリプトはシートの名前になっているメールアドレスにメール通知を送信します。

Apps Script サービス

このソリューションでは、次のサービスを使用します。

前提条件

このサンプルを使用するには、次の前提条件を満たしている必要があります。

  • Google アカウント(Google Workspace アカウントの場合、管理者の承認が必要となる可能性があります)。
  • インターネットにアクセスできるウェブブラウザ。

スクリプトを設定する

Apps Script プロジェクトを作成する

  1. 次のボタンをクリックして、YouTube 動画の視聴回数とコメントを追跡するスプレッドシートのコピーを作成します。このソリューションの Apps Script プロジェクトは、スプレッドシートに添付されています。
    コピーを作成
  2. コピーしたスプレッドシートで、[Your_Email_Address] シートの名前を自分のメールアドレスに変更します。
  3. トラッキングする YouTube 動画の URL を追加するか、テスト用に提供された URL を使用します。URL は www.youtube.com/watch?v= 形式で始まる必要があります。
  4. [拡張機能] > [Apps Script] をクリックします。[サービス] に YouTube がすでに表示されている場合は、次の 2 つの手順をスキップできます。
  5. [サービス] の横にある「サービスを追加」アイコン をクリックします。
  6. リストから [YouTube Data API] を選択し、[追加] をクリックします。

トリガーを作成する

  1. Apps Script プロジェクトで、[トリガー] > [トリガーを追加] をクリックします。
  2. [実行する関数を選択] で、[markVideos] を選択します。
  3. [イベントのソースを選択] で、[時間主導型] を選択します。
  4. [時間ベースのトリガーのタイプを選択] で、[日ベースのタイマー] を選択します。
  5. [Select time of day] で、ご希望の時間を選択します。
  6. メッセージが表示されたら、スクリプトを承認します。OAuth 同意画面に「このアプリは確認されていません」という警告が表示された場合は、[詳細] > [{プロジェクト名} に移動(安全でない)] を選択して続行します。

スクリプトを実行する

設定したトリガーは、スクリプトを 1 日 1 回実行します。スクリプトを手動で実行してテストできます。

  1. Apps Script プロジェクトで、[エディタ] をクリックします。
  2. 関数プルダウンで、[markVideos] を選択します。
  3. [実行] をクリックします。
  4. スプレッドシートに戻り、スクリプトによってシートに追加された情報を確認します。
  5. メールを開いて、コメントが 1 件以上ある動画のリストが記載されたメールを確認します。今後スクリプトを実行すると、前回スクリプトを実行したときからコメント数が増加した動画のみを含むメールが送信されます。

コードを確認する

このソリューションの Apps Script コードを確認するには、下の [ソースコードを表示] をクリックします。

ソースコードを表示

コード.gs

solutions/automations/youtube-tracker/Code.js
// To learn how to use this script, refer to the documentation:
// https://developers.google.com/apps-script/samples/automations/youtube-tracker

/*
Copyright 2022 Google LLC

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

    https://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

// Sets preferences for email notification. Choose 'Y' to send emails, 'N' to skip emails.
const EMAIL_ON = 'Y';

// Matches column names in Video sheet to variables. If the column names change, update these variables.
const COLUMN_NAME = {
  VIDEO: 'Video Link',
  TITLE: 'Video Title',
};

/**
 * Gets YouTube video details and statistics for all
 * video URLs listed in 'Video Link' column in each
 * sheet. Sends email summary, based on preferences above, 
 * when videos have new comments or replies.
 */
function markVideos() {
  let ss = SpreadsheetApp.getActiveSpreadsheet();
  let sheets = SpreadsheetApp.getActiveSpreadsheet().getSheets();

  // Runs through process for each tab in Spreadsheet.
  sheets.forEach(function(dataSheet) {
    let tabName = dataSheet.getName();
    let range = dataSheet.getDataRange();
    let numRows = range.getNumRows();
    let rows = range.getValues();
    let headerRow = rows[0];

    // Finds the column indices.
    let videoColumnIdx = headerRow.indexOf(COLUMN_NAME.VIDEO);
    let titleColumnIdx = headerRow.indexOf(COLUMN_NAME.TITLE);

    // Creates empty array to collect data for email table.
    let emailContent = [];

    // Processes each row in spreadsheet.
    for (let i = 1; i < numRows; ++i) {
      let row = rows[i];
      // Extracts video ID.
      let videoId = extractVideoIdFromUrl(row[videoColumnIdx])
      // Processes each row that contains a video ID.
      if(!videoId) { 
        continue;
      }
      // Calls getVideoDetails function and extracts target data for the video.
      let detailsResponse = getVideoDetails(videoId);
      let title = detailsResponse.items[0].snippet.title;
      let publishDate = detailsResponse.items[0].snippet.publishedAt;
      let publishDateFormatted = new Date(publishDate);
      let views = detailsResponse.items[0].statistics.viewCount;
      let likes = detailsResponse.items[0].statistics.likeCount;
      let comments = detailsResponse.items[0].statistics.commentCount;
      let channel = detailsResponse.items[0].snippet.channelTitle;

      // Collects title, publish date, channel, views, comments, likes details and pastes into tab.
      let detailsRow = [title,publishDateFormatted,channel,views,comments,likes];
      dataSheet.getRange(i+1,titleColumnIdx+1,1,6).setValues([detailsRow]);

      // Determines if new count of comments/replies is greater than old count of comments/replies.
      let addlCommentCount = comments - row[titleColumnIdx+4];

      // Adds video title, link, and additional comment count to table if new counts > old counts.
      if (addlCommentCount > 0) {
        let emailRow = [title,row[videoColumnIdx],addlCommentCount]
        emailContent.push(emailRow);
      }
    }
    // Sends notification email if Content is not empty.
    if (emailContent.length > 0 && EMAIL_ON == 'Y') {
      sendEmailNotificationTemplate(emailContent, tabName);
    }
  });
}

/**
 * Gets video details for YouTube videos
 * using YouTube advanced service.
 */
function getVideoDetails(videoId) {
  let part = "snippet,statistics";
  let response = YouTube.Videos.list(part,
      {'id': videoId});
 return response;
}

/**
 * Extracts YouTube video ID from url.
 * (h/t https://stackoverflow.com/a/3452617)
 */
function extractVideoIdFromUrl(url) {
  let videoId = url.split('v=')[1];
  let ampersandPosition = videoId.indexOf('&');
  if (ampersandPosition != -1) {
    videoId = videoId.substring(0, ampersandPosition);
  }   
 return videoId;
}

/**
 * Assembles notification email with table of video details. 
 * (h/t https://stackoverflow.com/questions/37863392/making-table-in-google-apps-script-from-array)
 */
function sendEmailNotificationTemplate(content, emailAddress) {
  let template = HtmlService.createTemplateFromFile('email');
  template.content = content;
  let msg = template.evaluate();  
  MailApp.sendEmail(emailAddress,'New comments or replies on YouTube',msg.getContent(),{htmlBody:msg.getContent()});
}

email.html

solutions/automations/youtube-tracker/email.html
<!--
 Copyright 2022 Google LLC

 Licensed under the Apache License, Version 2.0 (the "License");
 you may not use this file except in compliance with the License.
 You may obtain a copy of the License at

      http://www.apache.org/licenses/LICENSE-2.0

 Unless required by applicable law or agreed to in writing, software
 distributed under the License is distributed on an "AS IS" BASIS,
 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 See the License for the specific language governing permissions and
 limitations under the License.
-->

<body>
  Hello,<br><br>You have new comments and/or replies on videos: <br><br>
  <table border="1">
    <tr>
      <th>Video Title</th>
      <th>Link</th>
      <th>Number of new replies and comments</th>
    </tr>
    <? for (var i = 0; i < content.length; i++) { ?>
    <tr>
      <? for (var j = 0; j < content[i].length; j++) { ?>
      <td align="center"><?= content[i][j] ?></td>
      <? } ?>
    </tr>
    <? } ?>
  </table>
</body>

寄稿者

このサンプルは、Google デベロッパー エキスパートの協力を得て Google が管理しています。

次のステップ