mirror of
https://github.com/LBRYFoundation/lbry-wunderbot.git
synced 2025-08-23 17:47:27 +00:00
Added ban, kick and purge capabilities to wunderbot-v2. Fixes #206
This commit is contained in:
parent
6a13432247
commit
c46e1266aa
9 changed files with 7096 additions and 8 deletions
6854
package-lock.json
generated
Normal file
6854
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load diff
|
@ -42,7 +42,7 @@
|
||||||
"eslint-plugin-import": "^2.8.0",
|
"eslint-plugin-import": "^2.8.0",
|
||||||
"husky": "^0.14.3",
|
"husky": "^0.14.3",
|
||||||
"nodemon": "^1.14.8",
|
"nodemon": "^1.14.8",
|
||||||
"prettier-eslint": "^8.7.0"
|
"prettier-eslint": "^8.8.2"
|
||||||
},
|
},
|
||||||
"repository": "https://github.com/lbryio/lbry-wunderbot",
|
"repository": "https://github.com/lbryio/lbry-wunderbot",
|
||||||
"author": "Filip Nyquist <filip@lbry.io>",
|
"author": "Filip Nyquist <filip@lbry.io>",
|
||||||
|
|
|
@ -74,7 +74,12 @@ module.exports = class Wunderbot extends Commando.Client {
|
||||||
`);
|
`);
|
||||||
});
|
});
|
||||||
|
|
||||||
this.setProvider(MongoClient.connect(config.get("Wunderbot.dbUrl"), { useNewUrlParser: true }).then(client => new MongoDBProvider(client.db(config.get("Wunderbot.dbName"))))).catch(console.error);
|
this.setProvider(
|
||||||
|
MongoClient.connect(
|
||||||
|
config.get("Wunderbot.dbUrl"),
|
||||||
|
{ useNewUrlParser: true }
|
||||||
|
).then(client => new MongoDBProvider(client.db(config.get("Wunderbot.dbName"))))
|
||||||
|
).catch(console.error);
|
||||||
this.registry
|
this.registry
|
||||||
.registerDefaults()
|
.registerDefaults()
|
||||||
.registerGroup("info", "Info")
|
.registerGroup("info", "Info")
|
||||||
|
|
|
@ -41,8 +41,8 @@ module.exports = class RankCommand extends Command {
|
||||||
if (!msg.guild.member(this.client.user).hasPermission("MANAGE_ROLES")) return msg.reply("I do not have permission to manage roles! Contact a mod or admin.");
|
if (!msg.guild.member(this.client.user).hasPermission("MANAGE_ROLES")) return msg.reply("I do not have permission to manage roles! Contact a mod or admin.");
|
||||||
const rankToGive = msg.guild.roles.find("name", args.rank);
|
const rankToGive = msg.guild.roles.find("name", args.rank);
|
||||||
if (rankToGive === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
if (rankToGive === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
||||||
if (!await msg.guild.settings.get("ranks", null)) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}rank add role\` to add a role.`);
|
if (!(await msg.guild.settings.get("ranks", null))) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}rank add role\` to add a role.`);
|
||||||
if (!await msg.guild.settings.get("ranks", []).includes(args.rank)) return msg.reply(`That role can not be added! Use \`${msg.guild.commandPrefix}rank list\` to see a list of ranks you can add.`);
|
if (!(await msg.guild.settings.get("ranks", []).includes(args.rank))) return msg.reply(`That role can not be added! Use \`${msg.guild.commandPrefix}rank list\` to see a list of ranks you can add.`);
|
||||||
msg.guild
|
msg.guild
|
||||||
.member(msg.author)
|
.member(msg.author)
|
||||||
.addRole(msg.guild.roles.find("name", args.rank))
|
.addRole(msg.guild.roles.find("name", args.rank))
|
||||||
|
@ -54,8 +54,8 @@ module.exports = class RankCommand extends Command {
|
||||||
if (!msg.guild.member(this.client.user).hasPermission("MANAGE_ROLES")) return msg.reply("I do not have permission to manage roles! Contact a mod or admin.");
|
if (!msg.guild.member(this.client.user).hasPermission("MANAGE_ROLES")) return msg.reply("I do not have permission to manage roles! Contact a mod or admin.");
|
||||||
const rankToTake = msg.guild.roles.find("name", args.rank);
|
const rankToTake = msg.guild.roles.find("name", args.rank);
|
||||||
if (rankToTake === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
if (rankToTake === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
||||||
if (!await msg.guild.settings.get("ranks", null)) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}rank add role\` to add a role.`);
|
if (!(await msg.guild.settings.get("ranks", null))) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}rank add role\` to add a role.`);
|
||||||
if (!await msg.guild.settings.get("ranks", []).includes(args.rank)) return msg.reply(`That role can not be taken! Use \`${msg.guild.commandPrefix}rank list\` to see a list of ranks you can add.`);
|
if (!(await msg.guild.settings.get("ranks", []).includes(args.rank))) return msg.reply(`That role can not be taken! Use \`${msg.guild.commandPrefix}rank list\` to see a list of ranks you can add.`);
|
||||||
msg.guild
|
msg.guild
|
||||||
.member(msg.author)
|
.member(msg.author)
|
||||||
.removeRole(msg.guild.roles.find("name", args.rank))
|
.removeRole(msg.guild.roles.find("name", args.rank))
|
||||||
|
|
93
src/commands/moderation/ban.js
Normal file
93
src/commands/moderation/ban.js
Normal file
|
@ -0,0 +1,93 @@
|
||||||
|
import { Command } from "discord.js-commando";
|
||||||
|
import { RichEmbed } from "discord.js";
|
||||||
|
import { oneLine, stripIndents } from "common-tags";
|
||||||
|
import { deleteCommandMessages, stopTyping, startTyping } from "../../components/util.js";
|
||||||
|
|
||||||
|
module.exports = class banCommand extends Command {
|
||||||
|
constructor(client) {
|
||||||
|
super(client, {
|
||||||
|
name: "ban",
|
||||||
|
memberName: "ban",
|
||||||
|
group: "moderation",
|
||||||
|
aliases: ["b", "banana"],
|
||||||
|
description: "Bans a member from the server",
|
||||||
|
format: "MemberID|MemberName(partial or full) [ReasonForBanning]",
|
||||||
|
examples: ["ban JohnDoe annoying"],
|
||||||
|
guildOnly: true,
|
||||||
|
throttling: {
|
||||||
|
usages: 2,
|
||||||
|
duration: 3
|
||||||
|
},
|
||||||
|
args: [
|
||||||
|
{
|
||||||
|
key: "member",
|
||||||
|
prompt: "Which member should I ban?",
|
||||||
|
type: "member"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "reason",
|
||||||
|
prompt: "What is the reason for this banishment?",
|
||||||
|
type: "string",
|
||||||
|
default: ""
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
hasPermission(msg) {
|
||||||
|
return this.client.isOwner(msg.author) || msg.member.hasPermission("BAN_MEMBERS");
|
||||||
|
}
|
||||||
|
|
||||||
|
run(msg, { member, reason, keepmessages }) {
|
||||||
|
startTyping(msg);
|
||||||
|
if (member.id === msg.author.id) {
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.reply("I don't think you want to ban yourself.");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!member.bannable) {
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.reply("I cannot ban that member, their role is probably higher than my own!");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (/--nodelete/im.test(msg.argString)) {
|
||||||
|
reason = reason.substring(0, reason.indexOf("--nodelete")) + reason.substring(reason.indexOf("--nodelete") + "--nodelete".length + 1);
|
||||||
|
keepmessages = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
member.ban({
|
||||||
|
days: keepmessages ? 0 : 1,
|
||||||
|
reason: reason !== "" ? reason : "No reason given by staff"
|
||||||
|
});
|
||||||
|
|
||||||
|
const banEmbed = new RichEmbed(),
|
||||||
|
modlogChannel = msg.guild.settings.get("modlogchannel", msg.guild.channels.find(c => c.name === "mod-logs") ? msg.guild.channels.find(c => c.name === "mod-logs").id : null);
|
||||||
|
|
||||||
|
banEmbed
|
||||||
|
.setColor("#FF1900")
|
||||||
|
.setAuthor(msg.author.tag, msg.author.displayAvatarURL)
|
||||||
|
.setDescription(
|
||||||
|
stripIndents`
|
||||||
|
**Member:** ${member.user.tag} (${member.id})
|
||||||
|
**Action:** Ban
|
||||||
|
**Reason:** ${reason !== "" ? reason : "No reason given by staff"}`
|
||||||
|
)
|
||||||
|
.setTimestamp();
|
||||||
|
|
||||||
|
if (msg.guild.settings.get("modlogs", true)) {
|
||||||
|
if (!msg.guild.settings.get("hasSentModLogMessage", false)) {
|
||||||
|
msg.reply(oneLine`📃 I can keep a log of moderator actions if you create a channel named \'mod-logs\'
|
||||||
|
(or some other name configured by the ${msg.guild.commandPrefix}setmodlogs command) and give me access to it.
|
||||||
|
This message will only show up this one time and never again after this so if you desire to set up mod logs make sure to do so now.`);
|
||||||
|
msg.guild.settings.set("hasSentModLogMessage", true);
|
||||||
|
}
|
||||||
|
modlogChannel ? msg.guild.channels.get(modlogChannel).send("", { embed: banEmbed }) : null;
|
||||||
|
}
|
||||||
|
deleteCommandMessages(msg, this.client);
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.embed(banEmbed);
|
||||||
|
}
|
||||||
|
};
|
85
src/commands/moderation/kick.js
Normal file
85
src/commands/moderation/kick.js
Normal file
|
@ -0,0 +1,85 @@
|
||||||
|
import { Command } from "discord.js-commando";
|
||||||
|
import { RichEmbed } from "discord.js";
|
||||||
|
import { oneLine, stripIndents } from "common-tags";
|
||||||
|
import { deleteCommandMessages, stopTyping, startTyping } from "../../components/util.js";
|
||||||
|
|
||||||
|
module.exports = class KickCommand extends Command {
|
||||||
|
constructor(client) {
|
||||||
|
super(client, {
|
||||||
|
name: "kick",
|
||||||
|
memberName: "kick",
|
||||||
|
group: "moderation",
|
||||||
|
aliases: ["k"],
|
||||||
|
description: "Kicks a member from the server",
|
||||||
|
format: "MemberID|MemberName(partial or full) [ReasonForKicking]",
|
||||||
|
examples: ["kick JohnDoe annoying"],
|
||||||
|
guildOnly: true,
|
||||||
|
throttling: {
|
||||||
|
usages: 2,
|
||||||
|
duration: 3
|
||||||
|
},
|
||||||
|
args: [
|
||||||
|
{
|
||||||
|
key: "member",
|
||||||
|
prompt: "Which member do you want me to kick?",
|
||||||
|
type: "member"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "reason",
|
||||||
|
prompt: "What is the reason for this kick?",
|
||||||
|
type: "string",
|
||||||
|
default: ""
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
hasPermission(msg) {
|
||||||
|
return this.client.isOwner(msg.author) || msg.member.hasPermission("KICK_MEMBERS");
|
||||||
|
}
|
||||||
|
|
||||||
|
run(msg, { member, reason }) {
|
||||||
|
startTyping(msg);
|
||||||
|
|
||||||
|
if (member.id === msg.author.id) {
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.reply("I don't think you want to kick yourself.");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!member.kickable) {
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.reply("I cannot kick that member, their role is probably higher than my own!");
|
||||||
|
}
|
||||||
|
|
||||||
|
member.kick(reason !== "" ? reason : "No reason given by staff");
|
||||||
|
const kickEmbed = new RichEmbed(),
|
||||||
|
modlogChannel = msg.guild.settings.get("modlogchannel", msg.guild.channels.find(c => c.name === "mod-logs") ? msg.guild.channels.find(c => c.name === "mod-logs").id : null);
|
||||||
|
|
||||||
|
kickEmbed
|
||||||
|
.setColor("#FF8300")
|
||||||
|
.setAuthor(msg.author.tag, msg.author.displayAvatarURL)
|
||||||
|
.setDescription(
|
||||||
|
stripIndents`
|
||||||
|
**Member:** ${member.user.tag} (${member.id})
|
||||||
|
**Action:** Kick
|
||||||
|
**Reason:** ${reason !== "" ? reason : "No reason given by staff"}`
|
||||||
|
)
|
||||||
|
.setTimestamp();
|
||||||
|
|
||||||
|
if (msg.guild.settings.get("modlogs", true)) {
|
||||||
|
if (!msg.guild.settings.get("hasSentModLogMessage", false)) {
|
||||||
|
msg.reply(oneLine`📃 I can keep a log of moderator actions if you create a channel named \'mod-logs\'
|
||||||
|
(or some other name configured by the ${msg.guild.commandPrefix}setmodlogs command) and give me access to it.
|
||||||
|
This message will only show up this one time and never again after this so if you desire to set up mod logs make sure to do so now.`);
|
||||||
|
msg.guild.settings.set("hasSentModLogMessage", true);
|
||||||
|
}
|
||||||
|
modlogChannel ? msg.guild.channels.get(modlogChannel).send("", { embed: kickEmbed }) : null;
|
||||||
|
}
|
||||||
|
deleteCommandMessages(msg, this.client);
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.embed(kickEmbed);
|
||||||
|
}
|
||||||
|
};
|
|
@ -55,7 +55,7 @@ module.exports = class PubRanksCommand extends Command {
|
||||||
if (rankToRemove === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
if (rankToRemove === null) return msg.reply("That is not a role! Was your capatalization and spelling correct?");
|
||||||
guildRanks.splice(rankIndex, 1);
|
guildRanks.splice(rankIndex, 1);
|
||||||
msg.reply("Role removed.");
|
msg.reply("Role removed.");
|
||||||
-await msg.guild.settings.set("ranks", guildRanks);
|
-(await msg.guild.settings.set("ranks", guildRanks));
|
||||||
} else if (args.action.toLowerCase() === "list") {
|
} else if (args.action.toLowerCase() === "list") {
|
||||||
const guildRanks = await msg.guild.settings.get("ranks", null);
|
const guildRanks = await msg.guild.settings.get("ranks", null);
|
||||||
if (!guildRanks) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}pubranks add role\` to add a role.`);
|
if (!guildRanks) return msg.reply(`There are no public roles! Maybe try adding some? Do \`${msg.guild.commandPrefix}pubranks add role\` to add a role.`);
|
||||||
|
|
51
src/commands/moderation/purge.js
Normal file
51
src/commands/moderation/purge.js
Normal file
|
@ -0,0 +1,51 @@
|
||||||
|
import { Command } from "discord.js-commando";
|
||||||
|
import { stopTyping, startTyping } from "../../components/util.js";
|
||||||
|
|
||||||
|
module.exports = class PurgeCommand extends Command {
|
||||||
|
constructor(client) {
|
||||||
|
super(client, {
|
||||||
|
name: "purge",
|
||||||
|
memberName: "purge",
|
||||||
|
group: "moderation",
|
||||||
|
aliases: ["prune", "delete"],
|
||||||
|
description: "Purge a certain amount of messages",
|
||||||
|
format: "AmountOfMessages",
|
||||||
|
examples: ["purge 5"],
|
||||||
|
guildOnly: true,
|
||||||
|
args: [
|
||||||
|
{
|
||||||
|
key: "amount",
|
||||||
|
prompt: "How many messages should I purge?",
|
||||||
|
min: 1,
|
||||||
|
max: 100,
|
||||||
|
type: "integer"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
hasPermission(msg) {
|
||||||
|
return this.client.isOwner(msg.author) || msg.member.hasPermission("MANAGE_MESSAGES");
|
||||||
|
}
|
||||||
|
|
||||||
|
async run(msg, { amount }) {
|
||||||
|
startTyping(msg);
|
||||||
|
if (!msg.channel.permissionsFor(msg.guild.me).has("MANAGE_MESSAGES")) {
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return msg.reply("I do not have permission to delete messages from this channel. Better go and fix that!");
|
||||||
|
}
|
||||||
|
|
||||||
|
amount = amount === 100 ? 99 : amount;
|
||||||
|
msg.channel.bulkDelete(amount + 1, true);
|
||||||
|
|
||||||
|
const reply = await msg.say(`\`Deleted ${amount + 1} messages\``);
|
||||||
|
|
||||||
|
stopTyping(msg);
|
||||||
|
|
||||||
|
return reply.delete({
|
||||||
|
timeout: 1000,
|
||||||
|
reason: "Deleting own return message after purge"
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
|
@ -22,7 +22,7 @@ const capitalizeFirstLetter = function(string) {
|
||||||
};
|
};
|
||||||
|
|
||||||
const countCaps = function(capcount, total) {
|
const countCaps = function(capcount, total) {
|
||||||
return capcount.replace(/[^A-Z]/g, "").length / total.length * 100;
|
return (capcount.replace(/[^A-Z]/g, "").length / total.length) * 100;
|
||||||
};
|
};
|
||||||
|
|
||||||
const countEmojis = function(str) {
|
const countEmojis = function(str) {
|
||||||
|
|
Loading…
Add table
Reference in a new issue