123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213 |
- // Load up the discord.js library
- const Discord = require("discord.js");
- // Load up the shell command library
- var exec = require('child_process').exec;
- // Define a function to execute a command
- function execute(command, callback)
- {
- exec(command, function(error, stdout, stderr)
- {
- callback(stdout);
- });
- };
- // This is your client. Some people call it `bot`, some people call it `self`,
- // some might call it `cootchie`. Either way, when you see `client.something`, or `bot.something`,
- // this is what we're refering to. Your client.
- const client = new Discord.Client();
- // this allows us to define a voice connection with global scope
- var connection;
- var dispatcher;
- // Here we load the config.json file that contains our token and our prefix values.
- const config = require("./config.json");
- // config.token contains the bot's token
- // config.prefix contains the message prefix.
- client.on("ready", () =>
- {
- // This event will run if the bot starts, and logs in, successfully.
- console.log(`Bot has started, with ${client.users.size} users, in ${client.channels.size} channels of ${client.guilds.size} guilds.`);
-
- // Example of changing the bot's playing game to something useful. `client.user` is what the
- // docs refer to as the "ClientUser".
- client.user.setActivity("Taking Over Chicago");
- });
- client.on("guildCreate", guild =>
- {
- // This event triggers when the bot joins a guild.
- console.log(`New guild joined: ${guild.name} (id: ${guild.id}). This guild has ${guild.memberCount} members!`);
- client.user.setActivity(`Serving ${client.guilds.size} servers`);
- });
- client.on("guildDelete", guild => {
- // this event triggers when the bot is removed from a guild.
- console.log(`I have been removed from: ${guild.name} (id: ${guild.id})`);
- client.user.setActivity("Taking Over Chicago");
- });
- client.on("message", async message =>
- {
- // This event will run on every single message received, from any channel or DM.
-
- // It's good practice to ignore other bots. This also makes your bot ignore itself
- // and not get into a spam loop (we call that "botception").
- if (message.author.bot) return;
-
- // Also good practice to ignore any message that does not start with our prefix,
- // which is set in the configuration file.
- if (message.content.indexOf(config.prefix) !== 0) return;
-
- // Here we separate our "command" name, and our "arguments" for the command.
- // e.g. if we have the message "+say Is this the real life?" , we'll get the following:
- // command = say
- // args = ["Is", "this", "the", "real", "life?"]
- const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
- const command = args.shift().toLowerCase();
-
- // Let's go with a few common example commands! Feel free to delete or change those.
-
- if (command === "ping") {
- // Calculates ping between sending a message and editing it, giving a nice round-trip latency.
- // The second ping is an average latency between the bot and the websocket server (one-way, not round-trip)
- const m = await message.channel.send("Ping?");
- m.edit(`Pong! Latency is ${m.createdTimestamp - message.createdTimestamp}ms. API Latency is ${Math.round(client.ping)}ms`);
- }
-
- if (command === "say") {
- // makes the bot say something and delete the message. As an example, it's open to anyone to use.
- // To get the "message" itself we join the `args` back into a string with spaces:
- const sayMessage = args.join(" ");
- // Then we delete the command message (sneaky, right?). The catch just ignores the error with a cute smiley thing.
- message.delete().catch(O_o=>{});
- // And we get the bot to say the thing:
- message.channel.send(sayMessage);
- }
-
- if (command === "kick") {
- // This command must be limited to mods and admins. In this example we just hardcode the role names.
- // Please read on Array.some() returns true if any element meets the passed condition (map-like)
- if (!message.member.roles.some(r=>["Administrator", "Moderator","Admin","Mod"].includes(r.name)) )
- return message.reply("Sorry, you don't have permissions to use this!");
-
- // Let's first check if we have a member and if we can kick them!
- // message.mentions.members is a collection of people that have been mentioned, as GuildMembers.
- // We can also support getting the member by ID, which would be args[0]
- let member = message.mentions.members.first() || message.guild.members.get(args[0]);
- if (!member)
- return message.reply("Please mention a valid member of this server");
- if (!member.kickable)
- return message.reply("I cannot kick this user! Do they have a higher role? Do I have kick permissions?");
-
- // slice(1) removes the first part, which here should be the user mention or ID
- // join(' ') takes all the various parts to make it a single string.
- let reason = args.slice(1).join(' ');
- if (!reason) reason = "No reason provided";
-
- // Now, time for a swift kick in the nuts!
- await member.kick(reason)
- .catch(error => message.reply(`Sorry ${message.author} I couldn't kick because of : ${error}`));
- message.reply(`${member.user.tag} has been kicked by ${message.author.tag} because: ${reason}`);
- }
-
- if (command === "ban") {
- // Most of this command is identical to kick, except that here we'll only let admins do it.
- // In the real world mods could ban too, but this is just an example, right? ;)
- if (!message.member.roles.some(r=>["Administrator"].includes(r.name)) )
- return message.reply("Sorry, you don't have permissions to use this!");
-
- let member = message.mentions.members.first();
- if (!member)
- return message.reply("Please mention a valid member of this server");
- if (!member.bannable)
- return message.reply("I cannot ban this user! Do they have a higher role? Do I have ban permissions?");
- let reason = args.slice(1).join(' ');
- if (!reason) reason = "No reason provided";
-
- await member.ban(reason)
- .catch(error => message.reply(`Sorry ${message.author} I couldn't ban because of : ${error}`));
- message.reply(`${member.user.tag} has been banned by ${message.author.tag} because: ${reason}`);
- }
-
- if (command === "join")
- {
- // This command moves the bot to the channel given as the first arg.
-
- // This is the passed channel
- const channel = args.join(' ');
- const channelVar = message.guild.channels.find("name", channel);
- // Checks if channel is valid.
- if (!(message.guild.channels.exists("name", channel) && channelVar.type === "voice"))
- return message.reply(`Sorry ${message.author}, that channel doesn't appear to exist.`);
-
- // Joins the channel
- channelVar.join().then(conn =>
- {
- connection = conn;
- console.log('Connected!');
- }).catch(console.error);
- }
- if (command === "leave")
- {
- // this command remove the bot from the channel passed
- const channel = args.join(' ');
- const channelVar = message.guild.channels.find("name", channel);
- if (!(message.guild.channels.exists("name", channel) && channelVar.type === "voice"))
- return message.reply(`Sorry ${message.author}, that channel doesn't appear to exist.`);
- channelVar.leave();
- }
-
- if (command === "play")
- {
- // this command plays the song if one song matches the query given in beets
-
- const song = args.join(' '); // creates a single string of all args (the song)
- var path; // this will hold the filepath of our song
- exec(`beet ls -p title:${song} | wc -l`, function (error, stdout, stderr)
- {
- if (error)
- {
- return message.reply(`Sorry, I encountered an issue looking for that song: ${error}`);
- }
- else if (stdout !== '1\n')
- {
- return message.reply(`There were ${stdout} songs that matched your search. Please give the full song name, or wait until I become a less lazy dev.`);
- }
- else
- {
- exec(`beet ls -p title:${song}`, function (error, stdout, stderr)
- {
- if (error)
- {
- return message.reply(`Sorry, I encountered an issue looking for that song: ${error}`);
- }
- else
- {
- path = stdout.trim();
- console.log(song);
- console.log(path);
- dispatcher = connection.playFile(path);
- dispatcher.setVolume(0.75);
- dispatcher.setBitrate(2048);
- }
- });
- }
- });
- }
- });
- client.login(config.token);
|