TubeChat is an efficient and user-friendly library for YouTube chat integration. Designed for developers and content creators, it streamlines the capture, analysis, and interaction with live chat messages.
Explore the docs »
Report Bug
.
Request Feature
The TubeChat NodeJS library offers a highly efficient way to integrate with YouTube's live chat.
Its key differentiator is the use of yt-chat-signaler, which listens to YouTube's internal RPC signals. Unlike other libraries that rely on constant, resource-intensive polling (setInterval), TubeChat only fetches new messages when they are actually available, resulting in superior performance and efficiency.
First install our library
npm install tubechatImport the library
import { TubeChat } from 'tubechat'Instantiate the class
const tubeChat = new TubeChat({
// All settings are optional
useSignaler: true,
});You can pass an options object to the TubeChat constructor to customize its behavior:
useSignaler(boolean): Whether to use theyt-chat-signalerfor intelligent, push-based fetching. It is highly recommended to keep this enabled for performance. Defaults totrue.headers(HeadersInit): Custom headers to be used for all HTTP requests made by the library.intervalChat(number): The base interval in milliseconds for fetching chat messages. This is mainly a fallback for when the signaler is not in use. Defaults to1000.signalerConnectedInterval(number): The long-polling interval in milliseconds for when the signaler is connected and waiting for a push signal. Defaults to15000.signalerDisconnectedInterval(number): The faster polling interval for when the signaler is temporarily disconnected, ensuring messages are not missed. Defaults to1000.maxRetries(number): Maximum number of retry attempts for the initial connection to a chat. Defaults to4.
To connect to a chat, you need a Video ID. The method returns a promise indicating if the join was successful.
tubeChat.join(videoId, skipFirstResults, options)videoId(string, required): The ID of the YouTube live stream.skipFirstResults(boolean, optional): Iftrue, it will ignore the initial batch of messages that YouTube sends upon connection (which are often historical messages). Defaults tofalse.options(object, optional):headers(HeadersInit): Custom headers specifically for this video's connection requests.interval(number): A custom polling interval for this specific video, overriding the global setting.
If you need to monitor a channel and get its videoId when it goes live, we recommend using a library like Flow Monitor. It can watch a channel and notify you when a stream starts, providing the necessary videoId.
Here’s a brief example of how you could integrate it:
import { FlowMonitor } from 'flow-monitor';
import { TubeChat } from 'tubechat';
const fMonitor = new FlowMonitor();
const tubeChat = new TubeChat();
// Tell Flow Monitor to watch a channel
fMonitor.connect('LofiGirl', 'youtube');
// When Flow Monitor detects a live stream, it gives you the videoId
fMonitor.on('streamUp', (liveData) => {
console.log(`${liveData.channel} is live with video ID: ${liveData.vodId}`);
// Now, use the videoId to join the chat with TubeChat
tubeChat.join(liveData.vodId);
});
// Start monitoring
fMonitor.start();All events, in addition to their specific data, also return chatId (the video ID), userChannel (the channel's vanity name, e.g., "@LofiGirl"), and videoData (an object with details about the video).
// Emitted when a connection to the chat is successfully established.
tubeChat.on('join', (chatId, userChannel, videoData) => {
console.log(`Joined chat for ${userChannel} (Video: ${chatId})`);
});
// Emitted when the client disconnects from a chat.
tubeChat.on('disconnected', (chatId, userChannel, videoData) => {
console.log(`Disconnected from ${userChannel} (Video: ${chatId})`);
});
// Emitted when there's an error joining a chat.
tubeChat.on('joinError', (chatId, error) => {
console.error(`Failed to join chat ${chatId}:`, error.message);
});
// Emitted on connection retry attempts.
tubeChat.on('retry', (chatId, error, retry, maxRetries) => {
console.log(`Retrying connection to ${chatId} (${retry}/${maxRetries})...`);
});
// Emitted on general errors, usually during message fetching.
tubeChat.on('error', (chatId, message) => {
console.error(`An error occurred in chat ${chatId}:`, message);
});// A regular chat message.
tubeChat.on('message', (message, chatId, userChannel, videoData) => {
const author = message.author.channelName;
const text = message.message.map(part => part.text).join('');
console.log(`[${userChannel}] ${author}: ${text}`);
});
// A Super Chat message (paid message or sticker).
tubeChat.on('superchat', (message, chatId, userChannel, videoData) => {
console.log(`${message.author.channelName} sent a Super Chat of ${message.formatted}!`);
});
// A new or returning member announcement.
tubeChat.on('member', (message, chatId, userChannel, videoData) => {
if (message.isResub) {
console.log(`${message.author.channelName} has been a member for ${message.author.badges.months} months!`);
} else {
console.log(`Welcome ${message.author.channelName}, our newest member!`);
}
});
// When a user gifts one or more subscriptions to the community.
tubeChat.on('subgift_announce', (message, chatId, userChannel, videoData) => {
console.log(`${message.author.channelName} gifted ${message.count} subs to the community!`);
});
// When a specific user receives a gifted subscription.
tubeChat.on('subgift', (message, chatId, userChannel, videoData) => {
console.log(`${message.author.channelName} received a gifted sub from ${message.gifter}!`);
});
// For "Jewels" donations, typically from YouTube Shorts.
tubeChat.on('jewels', (message, chatId, userChannel, videoData) => {
console.log(`${message.author.channelName} sent Jewels!`);
});// When a message is deleted by a moderator.
tubeChat.on('deletedMessage', (messageId, chatId, userChannel, videoData) => {
console.log(`Message ${messageId} was deleted from chat ${chatId}.`);
});
// When all messages from a specific user are deleted (ban/timeout).
tubeChat.on('deleteUserMessages', (channelId, chatId, userChannel, videoData) => {
console.log(`All messages from user ${channelId} were removed in chat ${chatId}.`);
});
// For changes in chat mode (e.g., slow mode, subscribers-only).
tubeChat.on('system', (message, chatId, userChannel, videoData) => {
console.log(`System message in ${chatId}: ${message.message}`);
});// Emits the raw action object from YouTube for custom parsing.
tubeChat.on('raw', (actions) => {
// console.log('Received raw actions:', actions);
});This library integrates yt-chat-signaler to listen for new messages efficiently, reducing the need for constant polling. When useSignaler is true (the default), TubeChat will receive a push notification when a new message is available. You can listen to the signaler's own events if you need fine-grained control or diagnostics.
if (tubeChat.signaler) {
tubeChat.signaler.on('connected', (chatData) => {
console.log(`Signaler connected for video: ${chatData.chatId}`);
});
tubeChat.signaler.on('data', ({ chatData }) => {
console.log(`Signaler received new message notification for ${chatData.chatId}`);
});
}-
leave(videoId)Disconnects from a specific video's chat.tubeChat.leave('VIDEO_ID_HERE');
-
videosA publicMapcontaining the state and data of all currently connected video chats.// Get a list of all connected video IDs const connectedVideoIds = Array.from(tubeChat.videos.keys()); console.log('Connected to:', connectedVideoIds); // Get data for a specific video const videoDetails = tubeChat.videos.get('VIDEO_ID_HERE');
Distributed under the MIT License. See LICENSE for more information.
- ZackSB - Master's degree in life - ZackSB - Built tubechat