Getting Started

Welcome to Magmastream's documentation! Magmastream is a fork of Erela.Js. This fork is powerful and contains a lot of tweaks.

npm
npm install magmastream
⚠️ Magmastream has dropped support for lavalink version 3.x.x.
✅ Magmastream only supports lavalink version 4.

Basics

The first place to start with Magmastream is the Manager class.

// Require both libraries
const { Client } = require('discord.js');
const { Manager } = require('magmastream');

// Initiate both main classes
const client = new Client();

// Define some options for the node
const nodes = [
    {
        host: '127.0.0.1',
        identifier: 'Node 1',
        password: 'somepassword',
        port: 25033,
        retryAmount: 1000,
        retrydelay: 10000,
        resumeStatus: true, // default: false,
        resumeTimeout: 1000,
        secure: false, // default: false
    },
];

// Assign Manager to the client variable
client.manager = new Manager({
    // The nodes to connect to.
    nodes,
    // Method to send voice data to Discord
    send: (id, payload) => {
        const guild = client.guilds.cache.get(id);
        // NOTE: FOR ERIS YOU NEED JSON.stringify() THE PAYLOAD
        if (guild) guild.shard.send(payload);
    },
});

// Emitted whenever a node connects
client.manager.on('nodeConnect', (node) => {
    console.log(`Node "${node.options.identifier}" connected.`);
});

// Emitted whenever a node encountered an error
client.manager.on('nodeError', (node, error) => {
    console.log(`Node "${node.options.identifier}" encountered an error: ${error.message}.`);
});

// Listen for when the client becomes ready
client.once('ready', () => {
    // Initiates the manager and connects to all the nodes
    client.manager.init(client.user.id);
    console.log(`Logged in as ${client.user.tag}`);
});

// THIS IS REQUIRED. Send raw events to Magmastream
client.on('raw', (d) => client.manager.updateVoiceState(d));

// Finally login at the END of your code
client.login('your bot token here');

The whole idea of a music bot is to play music right? So let's write a command to play songs.

First you want to listen to the message event.

// Add the previous code block to this

client.on('message', async (message) => {
    // Some checks to see if it's a valid message
    if (!message.content.startsWith('!') || !message.guild || message.author.bot) return;

    // Get the command name and arguments
    const [command, ...args] = message.content.slice(1).split(/\s+/g);

    // Check if it's the play command
    if (command === 'play') {
        if (!message.member.voice.channel) return message.reply('you need to join a voice channel.');
        if (!args.length) return message.reply('you need to give me a URL or a search term.');

        const search = args.join(' ');
        let res;

        try {
            // Search for tracks using a query or url, using a query searches youtube automatically and the track requester object
            res = await client.manager.search(search, message.author);
            // Check the load type as this command is not that advanced for basics
            if (res.loadType === 'empty') throw res.exception;
            if (res.loadType === 'playlist') {
                throw { message: 'Playlists are not supported with this command.' };
            }
        } catch (err) {
            return message.reply(`there was an error while searching: ${err.message}`);
        }

        if (res.loadType === 'error') {
            return message.reply('there was no tracks found with that query.');
        }

        // Create the player
        const player = client.manager.create({
            guild: message.guild.id,
            voiceChannel: message.member.voice.channel.id,
            textChannel: message.channel.id,
            volume: 100,
        });

        // Connect to the voice channel and add the track to the queue
        player.connect();
        player.queue.add(res.tracks[0]);

        // Checks if the client should play the track if it's the first one added
        if (!player.playing && !player.paused && !player.queue.size) player.play();

        return message.reply(`enqueuing ${res.tracks[0].title}.`);
    }
});

You can play songs but what about knowing when a song starts or end? Those are events that the Manager class emits.

client.manager = new Manager(/* options above */)
    // Chain it off of the Manager instance
    // Emitted when a node connects
    .on('nodeConnect', (node) => console.log(`Node "${node.options.identifier}" connected.`));

// Emitted when a track starts
client.manager.on('trackStart', (player, track) => {
    const channel = client.channels.cache.get(player.textChannel);
    channel.send(`Now playing: \`${track.title}\`, requested by \`${track.requester.username}\`.`);
});

// Emitted the player queue ends
client.manager.on('queueEnd', (player) => {
    const channel = client.channels.cache.get(player.textChannel);
    channel.send('Queue has ended.');
    player.destroy();
});