Doing it Live! Learn Youtube’s API by Making a Chatbot

Jonny Kalambay
19 min readJan 1, 2019

--

You’re live in front of of the whole world.

Well, not you, but the app that you built, for your very own Youtube livestream , and its very own live chat.

But what does it do? Does it analyze the use of emojis? Does it respond to commenters? That’s all up to you to decide.

A few weeks ago, I used mine to control a robot with a camera inside my turtle tank, and the response to that project inspired this tutorial.

Perhaps you don’t share my obsession with stalking aquatic pets, and you’d rather build something different and actually useful. To each their own I guess. I’m just here to help you get started.

By the way, if you’re like me and you prefer video tutorials over written ones., or you just want a video reference to make sure you’re following the steps properly, I’ve got you covered:

So let’s get to it.

Preview

If you’re taking on this role, please make sure that you’ve got the following covered.
- You’re familiar with the basics of HTML and Javascript (and hopefully some ES6 syntax)
- You have Node.js installed and understand how an express server works
- You know the basics of navigating the terminal

Let’s read the screenplay and understand how this show is going to come together.

*A) Find our Live Broadcast*
*B) Read the Chat Messages from that Broadcast*
*C) Write Messages in that Live Chat*

Let’s try doing just that. Just to test things out, go to youtube and start a live stream. To make sure the world doesn’t see you in your boxers while you test your app, you can go into your live stream’s settings and make it unlisted. (Don’t make it private or you won’t be able to insert messages.)

Now we’re ready for some practice.

Step 1: Rehearse Your Lines

Before we get waist-deep in Javascript, we can test out the functionality of our app without writing a single line of code. Through the Youtube API documentation, we have a console we can use to try API calls. Let’s try our three big actions using the console.

A) Find our Live Broadcast
In order to find our live chat, we need to find the live broadcast that it belongs to. This endpoint allows us to do just that.
On the right section titled Try this API’, fill out the following values:

part: snippet 
broadcastType: all
mine: true

Click the “EXECUTE” button at the bottom of the section. You will be asked to log in through your Google account. Note, when testing these endpoints on the dashboard, you’ll be asked to sign in every time we make a, but on our actual app, we’ll only have to sign in once in the beginning.

Once the call is executed, and we should receive a responses that looks like the following:

{
"kind": "youtube#liveBroadcastListResponse",
"etag": "\"XI7nbFXulYBIpL0ayR_gDh3eu1k/d5wdl5CFbJ9jDiASOujFx_1ie1s\"",
"pageInfo": {
"totalResults": 1,
"resultsPerPage": 5
},
"items": [
{
"kind": "youtube#liveBroadcast",
"etag": "\"XI7nbFXulYBIpL0ayR_gDh3eu1k/eRkvD6FrUv7IxuR14GnLKw3QqbY\"",
"id": "ZQdn5iqCKqU",
"snippet": {
"publishedAt": "2018-12-28T00:02:49.000Z",
"channelId": "UCUm0chMKj4MA7q9CWZXWhiA",
"title": "cambridge",
"description": "",
"thumbnails": {
"default": {
"url": "https://i.ytimg.com/vi/ZQdn5iqCKqU/default_live.jpg",
"width": 120,
"height": 90
},
"medium": {
"url": "https://i.ytimg.com/vi/ZQdn5iqCKqU/mqdefault_live.jpg",
"width": 320,
"height": 180
},
"high": {
"url": "https://i.ytimg.com/vi/ZQdn5iqCKqU/hqdefault_live.jpg",
"width": 480,
"height": 360
},
"standard": {
"url": "https://i.ytimg.com/vi/ZQdn5iqCKqU/sddefault_live.jpg",
"width": 640,
"height": 480
},
"maxres": {
"url": "https://i.ytimg.com/vi/ZQdn5iqCKqU/maxresdefault_live.jpg",
"width": 1280,
"height": 720
}
},
"scheduledStartTime": "2018-12-28T00:02:49.000Z",
"actualStartTime": "2018-12-28T00:03:01.000Z",
"isDefaultBroadcast": false,
"liveChatId": "Cg0KC1pRZG41aXFDS3FV"
}
}
]
}

Find the first item inside the “items” array, it should be your most recent live stream. Copy down its “liveChatId” value into a note. We’ll need it to track the messages for the live chat.

B) Read the Chat Messages from that Broadcast
We can use this endpoint to read the chat messages from the live broadcast we just identified. Then, using the “nextPageToken” from the response, we can later make another request in order to retrieve the messages that follow the ones from our previous request.
To prepare, go to our livestream and type in a few messages into the chat.

In the “Try this API’” section on the right, enter the following:

liveChatId: OUR_LIVE_CHAT_ID
part: snippet

Click the “EXECUTE’” button at the bottom, sign in with Google and the API call will be executed. The response should look like this:

{
"kind": "youtube#liveChatMessageListResponse",
"etag": "\"XI7nbFXulYBIpL0ayR_gDh3eu1k/XLpfNzFMnLfUcxFUImUCGD4N7jg\"",
"nextPageToken": "GJzWoLiUwd8CINGwpumUwd8C",
"pollingIntervalMillis": 3000,
"pageInfo": {
"totalResults": 1,
"resultsPerPage": 1
},
"items": [
{
"kind": "youtube#liveChatMessage",
"etag": "\"XI7nbFXulYBIpL0ayR_gDh3eu1k/_ZrJEd-oFkybQypS9RLy2y6ZXgc\"",
"id": "LCC.Cg8KDQoLbFFJWjd6bFFPNEkSOQoaQ0p6V29MaVV3ZDhDRmUwWmd3b2R5M3NIcVESG0NQWHExTzZTd2Q4Q0ZkV3N4QW9kUjJNTlBBMA",
"snippet": {
"type": "textMessageEvent",
"liveChatId": "Cg0KC2xRSVo3emxRTzRJ",
"authorChannelId": "UCUm0chMKj4MA7q9CWZXWhiA",
"publishedAt": "2018-12-27T23:26:35.076Z",
"hasDisplayContent": true,
"displayMessage": "testing",
"textMessageDetails": {
"messageText": "testing"
}
}
}
]
}

The “items” property will contain the actual messages. What we’re mainly interested is the “messageText” property inside of each message.

Eventually we’ll need to go back for seconds. Copy down the “nextPageToken” from the response. Then return to our live chat and type a few more messages in. Then, go pack to the API dashboard and make another request, but this time, put the “nextPageToken” value into the “pageToken” field

Execute the call again and this time, only our newest messages should appear in the response, along with a new nextPageToken.

C) Insert Chat Message
We can insert messages to a live chat on behalf of a user using this enpoint. To test it out, go to the “Try this API” section on the right and fill it in as follows:

part: snippet
Request Body:
{
snippet: {
type: "textMessageEvent",
liveChatId: "YOUR_LIVE_CHAT_ID",
textMessageDetails: {
messageText: "Hello World",
}
}
}

Click the “execute” button and sign in to run the API call. Then, visit your live chat, and your message should appear.

Now that we’re familiar with the three API calls we’ll need. We’re ready to execute these calls with our own app. Let’s register our app so we can do just that.

Step 3: Prepare the Venue

In order for our app to be able to authorize users for API requests, it needs to be registered and have the right credentials set up.

Register Your App

  • First make sure you have a Google account created
  • Visit Google’s developer console and create a new project.
  • From the API Console , click “view all”, find “Youtube Data API v3’” select it and click “enable”.
  • Go to the Credentials Dashboard.
  • Go to the “OAuth consents screen” tab and fill in the “Application name” field with whatever name you’d like to give our application. Then, make sure you click “Save” at the bottom
  • You’ll be taken to a screen where you are asked for info about our app
  • For “Application Type”, select ‘Web application”
  • For “Name”, enter whatever name you would like for your app
  • For “Authorized Javascript Origins”, you can leave it blank, since your API requests will come from a server and not a browser
  • For “Authorized Redirect urls”, enter “http://localhost:3000/callback”
  • You will be given a “client ID” and a “client Secret,” copy them down and keep them somewhere safe

What are all these for, you’re probably wondering. To understand, we need a quick overview of our authentication process.

The Oauth Flow

In order to use the API, google requires that we use an authentication protocol called Oauth 2.0. If you’ve ever used an app that asked you to sign in with Facebook, Google, GitHub or another service, then you’ve seen Oauth in action. Now we’ll get to implement it into our own app.

Before authentication actually happens, we register our app with Google so that it can it can be recognized. In our app, we define a list of scopes, which represent the permissions we’d like to be granted. In other words, we define the different kinds of information actions that our app is requesting to be allowed access to through their Google account. Then, the OAuth process roughly goes as follows:

  1. When we run the app, we send the user to Google to log in , and they are prompted to agree to give our app access to their account, (access restricted to the requested permissions based on the aforementioned scope).
  2. Once the user has accepted, Google sends them back to our app with a code that proves their identity.
  3. Our app uses that code to request an access token from Google.
  4. Google responds with the access token. (Note: it also sends back a refresh token, which we can use to get a new access token once it expires.)
  5. With that access token, our app can perform actions with the Youtube API, through that users’ Google account

We now have everything we need in order to make our app work. The only problem is, we don’t actually have an app yet. Let’s fix that.

Set up our project

In a new, empty folder, create the following three files:

  • server.js
  • youtubeService.js
  • index.html

In our project we’ll need to add some dependencies, that is, some Javascript libraries needed for it to work:

  • express — for running our server
  • googleapis — A library that provides an easy-to-use interface for calls to the YouTube API

Let’s start by creating a “package.json” file to track our dependencies, and then installing these dependencies. In our terminal, navigate to our project folder and enter the following commands:

  • npm init — y
  • npm install — save express googleapis

We should now see a “package.json” file in our project folder (and most likely also a “package-lock.json,” and in it, the two libraries we just installed should be listerd under the “dependencies” key.

Step 4 : Set the Stage

It’s finally time to write some code. Just to make sure everything’s working properly. Let’s just build a simple server that serves the our html page.

Starting Boilerplate

In “index.html”, make a basic html skeleton

<!-- index.html --><!DOCTYPE html>
<html>
<head>
<title>Youtube ChatBot</title>
</head>
<body>
<h1>Youtube Chatbot</h1>
</body>
</html>

In “server.js” write a simple express server that serves our html.

// server.jsconst express = require('express');
const path = require('path');
const server = express();server.get('/', (req, res) =>
res.sendFile(path.join(__dirname + '/index.html'))
);
server.listen(3000, function() {
console.log('Server is Ready');
});

To run your server, from your terminal, make sure you are pointing to your project folder and run the command node server.js. Once you do, open up your browser to “http://localhost:3000” and your should see your html.

Now let’s set up the authorization flow for this app. In your server file. First, in youtubeServer.js, let’s import the API client, and save it’s OAuth2 function function into a variable that we can easily access.

Then, let’s put in the client ID, client secret, and redirect URI from the project we registered on Google. While we’re at it, we’ll also specify the scopes that will define the permissions for this app. We’ll also can create a new Oauth object using those credentials and our OAuth2 function. Finally, we create an object that will store the functions that the server will call.

This is what our “youtubeService.js” should look like:

// youtubeService.jsconst { google } = require('googleapis');
const youtube = google.youtube('v3');
const OAuth2 = google.auth.OAuth2;
const clientId = 'YOUR CLIENT ID';
const clientSecret = 'YOUR CLIENT SECRET';
const redirectURI = 'http://localhost:3000/callback'
// Permissions needed to view and submit live chat comments
const scope = [
'https://www.googleapis.com/auth/youtube.readonly',
'https://www.googleapis.com/auth/youtube',
'https://www.googleapis.com/auth/youtube.force-ssl'
];
const auth = new OAuth2(clientId, clientSecret, redirectURI);const youtubeService = {};// As we progress throug this turtorial, Keep the following line at the nery bottom of the file
// It will allow other files to access to our functions
module.exports = youtubeService;

Now, we need to set up and functions that will allow us to use this auth object to authenticate a user. From this point on, we’ll be hopping back and forth between different files, so make sure that you don’t miss any import or export statements, or your code will break. If you’re new to writing code for OAuth, keep referring back to the diagram and explanation above as we progress through the rest of this section, so that you can better understand how the code being written fits into the overall authorization flow.

Let’s start with the first route, this is one that will trigger the auth process and send the user to google so that they can log in. We need a button to click in order to trigger that request. The server route will pass the response object into the function from youtubeService, so that it can redirect the user. Here’s the code to add to each file:

Add the following button to the html body

<!-- index.html --><a href="/authorize">
<button> Authorize </button>
</a>

Put the following line at the top of the server file, right below your dependency imports, to import the functions that use the API.

// server.jsconst youtubeService = require('./youtubeService.js’);

In the same file add a route will call the getCode function from the youtubeService (which we’ll define in a bit). That function will needs access to the response in order to redirect the user, so need we pass that in as an argument.

// server.jsserver.get('/authorize', (request, response) => {
console.log('/auth');
youtubeService.getCode(response);
});

Now we can define that function. I will use the Google API client generate a url for the user to visit in order to log in and give permissions. It then uses the response object to redirect the user to that URL

// youtubeService.jsyoutubeService.getCode = response => {
const authUrl = auth.generateAuthUrl({
access_type: 'offline',
scope
});
response.redirect(authUrl);
};

After our user has logged in, they’ll be sent back to our app at the /callback endpoint, along with an authorization code in their query string. Let’s write the a route and function to pull the code from there query string and use it to request the tokens we need.

// server.jsserver.get('/callback', (req, response) => {
const { code } = req.query;
youtubeService.getTokensWithCode(code);
response.redirect('/');
});

In the following snippet, you’ll notice that we import the util, and fs modules. These are built into node so no need to ad them to our dependencies. As you’ll notice, we use these to create the functions save and read, which we’ll need to save the auth tokens to a file when we receive them, and read the tokens on the file later on whenever we need them again. That way we’ll have access to them even after we restart the server.

// youtubeService.js// Put the following at the top of the file
// right below the'googleapis' import
const util = require('util');
const fs = require('fs');
const writeFilePromise = util.promisify(fs.writeFile);
const readFilePromise = util.promisify(fs.readFile);
const save = async (path, str) => {
await writeFilePromise(path, str);
console.log('Successfully Saved');
};
const read = async path => {
const fileContents = await readFilePromise(path);
return JSON.parse(fileContents);
};

In the same file put the following code, but put it below all of the code we’d written in the previous parts. (But above the export statement at the bottom !)

// youtubeService.js// Request access from tokens using code from login
youtubeService.getTokensWithCode = async code => {
const credentials = await auth.getToken(code);
youtubeService.authorize(credentials);
};
// Storing access tokens received from google in auth object
youtubeService.authorize = ({ tokens }) => {
auth.setCredentials(tokens);
console.log('Successfully set credentials');
console.log('tokens:', tokens);
save('./tokens.json', JSON.stringify(tokens));
};

We now should have everything we need to start using the API. Time to test it out. Kill your server from your terminal by typing ctrl + c, then run it again with node server.js. Open “http://localhost:3000” in your browser and you should see your header, as well as the “authorize” button that you added.

Click the button, and you should be directed to a Google login page. Log in, accept the permissions, and we will be redirected back to your html page. Then, open our project folder, and there should now be a file called “tokens.json” with your authorization tokens. The contents should look something like this:

{
"access_token": "reallylongstringofrandomcharacters",
"refresh_token": "anotherreallylongstringofrandomcharacters",
"scope": "https://www.googleapis.com/auth/youtube.force-ssl https://www.googleapis.com/auth/youtube.readonly https://www.googleapis.com/auth/youtube",
"token_type": "Bearer",
"expiry_date": 1545022007382
}

If you don’t see the file, or the contents look different, find the debugging tips at the end of the tutorial, under the “Post-Production Refinements” section.

Having the tokens written in a file allows us to access them even after restarting the server. However, we need to write code to access the tokens from the file, using the `read` function that we wrote earlier. We also need to write an event listener, that will automatically use the `refresh_token` to fetch a new `access_token` once it expires. Luckily, that functionality come built in with the `googleapis` library.

Add the following to our “youtubeService.js”

// youtubeService.js// Update the tokens automatically when they expire
auth.on('tokens', (tokens) => {
if (tokens.refresh_token) {
// store the refresh_token in my database!
save('./tokens.json', JSON.stringify(auth.tokens));
console.log(tokens.refresh_token);
}
console.log(tokens.access_token);
});
// Read tokens from stored file
const checkTokens = async () => {
const tokens = await read('./tokens.json');
if (tokens) {
auth.setCredentials(tokens);
console.log('tokens set');
} else {
console.log('no tokens set');
}
};
// Check tokens as soon as server is started
checkTokens();

Our server is now ready to start interacting with Youtube’s API. Let’s add some functionality to do just that.

Step 5 — Doing It Live!

Time to start playing with our live chat. First, let’s define some handy variables near the top of the file. We can put these right below the import statements.

// youtubeService.jslet liveChatId; // Where we'll store the id of our liveChat
let nextPage; // How we'll keep track of pagination for chat messages
const intervalTime = 5000; // Miliseconds between requests to check chat messages
let interval; // variable to store and control the interval that will check messages
let chatMessages = []; // where we'll store all messages

Remember the diagram and our test requests on the Google API console? There were 3 actions that we performed. We’re now going to do the same thing but with real code. Make sure you have an active live stream on our Youtube channel for the following to work.

As we revisit our three big actions, add the code snippets below to each corresponding file. Hopefully our walkthrough with the the diagrams and the with console means that you can understand what the code does without much explanation.

A) Find the live chat Id

<!-- index.html --><a href="/find-active-chat">
<button>
Get Active Chat
</button>
</a>
// server.jsserver.get('/find-active-chat', (req, res) => {
youtubeService.findActiveChat();
res.redirect('/');
});
// youtubeService.jsyoutubeService.findActiveChat = async () => {
const response = await youtube.liveBroadcasts.list({
auth,
part: 'snippet',
mine: 'true',
});
const latestChat = response.data.items[0];
liveChatId = latestChat.snippet.liveChatId;
console.log('Chat ID Found:', liveChatId)
};

B) Track Chat messages

Once we’ve found or live chat, every 5 Seconds, we want to pull all of the new messages from that chat.

<!-- index.html --><a href="/start-tracking-chat">
<button>
Start Tracking Chat
</button>
</a>
// server.jsserver.get('/start-tracking-chat', (req, res) => {
youtubeService.startTrackingChat();
res.redirect('/');
});
// youtubeService.jsconst getChatMessages = async () => {
const response = await youtube.liveChatMessages.list({
auth,
part: 'snippet',
liveChatId,
pageToken: nextPage
});
const { data } = response;
const newMessages = data.items;
chatMessages.push(...newMessages);
nextPage = data.nextPageToken;
console.log('Total Chat Messages:', chatMessages.length)
};
youtubeService.startTrackingChat = () => {
interval = setInterval(getChatMessages, intervalTime);
};

Before the third and final action, let’s add a way to stop the interval, in case we no longer want to track the live chat but don’t want to kill the server altogether. We can do that simply by clearing the interval.

<!-- index.html --><a href="/stop-tracking-chat">
<button>
Stop Tracking Chat
</button>
</a>
server.get('/stop-tracking-chat', (req, res) => {
youtubeService.stopTrackingChat();
res.redirect('/');
});
// youtubeService.jsyoutubeService.stopTrackingChat = () => {
clearInterval(interval);
};

C) Adding our own comments to the liveChat

Just to test it out if messages can be sent, we’ll write a hard-coded one, write a route to trigger it, and make a button on the front-end to hit that route.

<!-- index.html --><a href="/insert-message">
<button>
Insert Message
</button>
</a>
// server.jsserver.get('/insert-message', (req, res) => {
youtubeService.insertMessage("Hello World");
res.redirect('/');
});
// youtubeService.jsyoutubeService.insertMessage = messageText => {
youtube.liveChatMessages.insert(
{
auth,
part: 'snippet',
resource: {
snippet: {
type: 'textMessageEvent',
liveChatId,
textMessageDetails: {
messageText
}
}
}
},
() => {}
);
}

Time to try the real thing.
Kill your server, then start it up again, and test out each piece of functionality by pressing the buttons:

  1. Click the ‘Get Active Chat’ button and make sure that the chat Id of our active live stream is printed in the console.
  2. Click the ’Start Tracking Chat’. From that point on, every 5 seconds, the number of total messages should be printed to our console. Add some comments to our live chat manually to make sure that our app picks them up.
  3. Click the ‘Insert Message’ button, and then go to our live chat to make sure that the message ’Hello World’ has been imported.

Watch your terminal for any errors and see the debugging tips in section 6 if you notice any.

Congratulations! You now have your first Youtube chatbot. At this point, it’s pretty barebones. All the necessary functionality is there, now it’s up to you to write code that ties it all together. If you’ know exactly how you want your chatbot to work, then you’re good to go. However, if you need example use cases to start with and spark your creativity, I have a couple of code recipes at the end of this tutorial. But first, a bit of cleanup…

Step 6 — Post-Production Refinements

So far we’ve taken the most simple path to explain and exemplify the functionality of the Youtube API. As a result, we skipped a few tedious but good practices that shouldn’t be ignored:

Debugging

If you’re familiar with using the debugger that comes with your code editor, or you know how to debug Node JS using Chrome, then I would recommend that. Otherwise, you can use console.log statements in different functions to pinpoint the error. When running a Node script in the terminal, since console.log doesn’t always print out all the deeply nested properties in an object, you can use util.inspect to log them in detail. That being said, the best way to save yourself the headache of tracking down a bug is to have some good error handling.

Error handling

When building our app, we should make sure that we have graceful error handling error handling for all API requests. For example, since we’re using async await, we could wrap each request with try/catch statements, which logs errors if they are found.

Here’s an example

Safely storing sensitive data
Things like client_id, client_secret, tokens, and important urls shouldn’t be hard-coded into our app, or they’ll be exposed to whoever sees our code. You can store your app information from google in an “.env” file and then access them using the library dotenv, and, instead of storing your tokens in a son file, it would be safer to store them in a database, using something like Mongo DB.

You’ll find examples of these implementations in the example code. Speaking of which…

Step 7: End Credits

Before showing you the examples as promised, I just wanted to thank you for following the tutorial. You can find all of the code in this Repo.

Check out my YouTube Channel for more programming tutorials (including the video version of this one), and reach out to me there, here or on Twitter if you have questions!

Now for your bonus content.

Bonus Scenes

By this point, with all of the necessary functionality set up, you’re meant to put together according to how you want your chatbot to work, but maybe you could use a couple of small examples to get you started. I’ve provided two, one for how you an interact with the chat, and another for how you can interact with other apps and services.

1) Respond to grateful users

We can create a function to process the new messages, find words of gratitude, and respond to the authors accordingly

Fist, we need to start fetching the author details for every chat message. In the getChatMessages function, change this line:

part: 'snippet'

to this:

part: ‘snippet,authorDetails’,

Then, create a new function:

// youtubeService.jsconst respond = (newMessages) => {
newMessages.forEach(message => {
const messageText = message.snippet.displayMessage.toLowerCase();
if (messageText.includes('thank')) {
const author = message.authorDetails.displayName;
const message = `we're welcome ${author}!`;
youtubeService.insertMessage(response)
}
});
}

And finally, call this new function every time you fetch new messages:

// youtubeService.jsconst getChatMessages = async () => {
// Keep the code from before in here, and add the following line
respond(newMessages);
};

2) Send an email report of your live chat

The way to really make our app shine is to have it interact with other apps and services. To start with a simple example, let’s have our app send an email at the end of our live stream, with stats about the chat comments.

We’ll set up a Webhook at IFTTT, which will send us en email when it receives a request. Then, we’ll write code in our app calculate the stats and then make that request to IFTT as soon as we trigger the stopTrackingMessages function.

Let’s head over to IFTT and set up our webhook:
— Create a free account at IFTT

How IFTT T Works
An IFTTT Applet is a basically just process flow you define as follows:

  • If this then that.
  • If triggering event ] then [desired action]
  • In our case - If [the applet receives a request] then [send out an email]
  • More specifically - If [the applet receives a request, containing certain values] then [send an email that contains those values]

Knowing this, let’s make an applet, once it receives a request containing two determined values, send an email reporting the number of messages and the number of participants from our live chat (based on those values).

Creating an Applet

  • Open the Create a New Applet page
  • Click on the blue “This” to define the triggering event
  • Under “choose a service”, find and select “webhooks”
  • Under “choose a trigger”, select “Receive a web request”
  • Define the event name as “youtube_live_chat_report”

Then comes the action..

  • Click on the blue “That” to define the action
  • Under “choose a service”, find and select “email”
  • Under “choose action”, select “Send me an email”
  • Fill in the email template as follows:
Subject: `Youtube Live Chat Report — {{OccurredAt}}`
Body:
Youtube Live Chat Report<br>
Time: {{OccurredAt}}<br>
Chat Messages: {{Value1}}<br>
Participants: {{Value2}}<br>
— Finish it by clicking on “Create Action”, then clicking “Finish”

One last thing we need to do here is get the URL to which which should direct our request.

*Now back to our code.*

First, we need a couple of libraries that will make it easier to make these request. In our terminal, run the following command:

npm install —-save request request-promise

Then, import request-promise at the top of “youtubeService.js”

// youtubeService.jsvar request = require('request-promise');

Also, near the top (but below the import statements), add a variable to store the URI of our webhook.

// youtubeService.jsconst webhookURI = 'our link here'

Then, create function to add the stats from our chatMessages

// youtubeService.jsconst calculateChatStats = () => {
const authors = {};
messages.forEach(message => {
const author = message.authorDetails.displayName;
if (!messagesByAuthor[author]) {
messagesByAuthor[author] = 1;
} else {
messagesByAuthor[author] += 1;
}
})
const authorCount = Object.keys(messagesByAuthor).length;
return {
messageCount: messages.length,
authorCount,
}
}
sendLiveStreamReport = async () => {
const {
messageCount: value1,
authorCount: value2
} = calculateChatStats();
const options = {
method: 'POST',
uri: webhookURI,
body: { value1, value2 }
}
await request(option)
console.log('Successfully sent report')
}

Finally, trigger that function whenever you stop tracking the messages

youtubeService.stopTrackingChat = () => {
// Keep the code from before and add the following
sendLiveStreamReport();
};

And that’s it! Best of luck, and once again, if you found this useful, you can find more of my tutorials on Youtube!

--

--