mirror of
https://github.com/ZeppelinBot/Zeppelin.git
synced 2025-03-16 14:11:50 +00:00
Merge branch 'master' of github.com:Dragory/ZeppelinBot
This commit is contained in:
commit
3ddfb3b65a
19 changed files with 72 additions and 35 deletions
|
@ -65,6 +65,8 @@ These instructions are intended for bot development only.
|
||||||
Configuration is stored in the database in the `configs` table
|
Configuration is stored in the database in the `configs` table
|
||||||
|
|
||||||
```yml
|
```yml
|
||||||
|
prefix: '!'
|
||||||
|
|
||||||
# role id: level
|
# role id: level
|
||||||
levels:
|
levels:
|
||||||
"12345678": 100 # Example admin
|
"12345678": 100 # Example admin
|
||||||
|
|
|
@ -37,7 +37,7 @@ export function initDocs(app: express.Express) {
|
||||||
app.get("/docs/plugins", (req: express.Request, res: express.Response) => {
|
app.get("/docs/plugins", (req: express.Request, res: express.Response) => {
|
||||||
res.json(
|
res.json(
|
||||||
docsPlugins.map(plugin => {
|
docsPlugins.map(plugin => {
|
||||||
const thinInfo = plugin.info ? { prettyName: plugin.info.prettyName } : {};
|
const thinInfo = plugin.info ? { prettyName: plugin.info.prettyName, legacy: plugin.info.legacy ?? false } : {};
|
||||||
return {
|
return {
|
||||||
name: plugin.name,
|
name: plugin.name,
|
||||||
info: thinInfo,
|
info: thinInfo,
|
||||||
|
|
|
@ -73,6 +73,10 @@ const configPreprocessor: ConfigPreprocessorFn<AutomodPluginType> = options => {
|
||||||
rule["enabled"] = true;
|
rule["enabled"] = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (rule["allow_further_rules"] == null) {
|
||||||
|
rule["allow_further_rules"] = false;
|
||||||
|
}
|
||||||
|
|
||||||
if (rule["affects_bots"] == null) {
|
if (rule["affects_bots"] == null) {
|
||||||
rule["affects_bots"] = false;
|
rule["affects_bots"] = false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -72,7 +72,7 @@ export async function runAutomod(pluginData: GuildPluginData<AutomodPluginType>,
|
||||||
|
|
||||||
matchResult.fullSummary = `Triggered automod rule **${ruleName}**\n${matchResult.summary}`.trim();
|
matchResult.fullSummary = `Triggered automod rule **${ruleName}**\n${matchResult.summary}`.trim();
|
||||||
|
|
||||||
break triggerLoop;
|
if (!rule.allow_further_rules) break triggerLoop;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -94,7 +94,7 @@ export async function runAutomod(pluginData: GuildPluginData<AutomodPluginType>,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
if (!rule.allow_further_rules) break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,6 +26,7 @@ export const Rule = t.type({
|
||||||
triggers: t.array(t.partial(AvailableTriggers.props)),
|
triggers: t.array(t.partial(AvailableTriggers.props)),
|
||||||
actions: t.partial(AvailableActions.props),
|
actions: t.partial(AvailableActions.props),
|
||||||
cooldown: tNullable(t.string),
|
cooldown: tNullable(t.string),
|
||||||
|
allow_further_rules: t.boolean,
|
||||||
});
|
});
|
||||||
export type TRule = t.TypeOf<typeof Rule>;
|
export type TRule = t.TypeOf<typeof Rule>;
|
||||||
|
|
||||||
|
|
|
@ -52,6 +52,7 @@ export const CensorPlugin = zeppelinGuildPlugin<CensorPluginType>()({
|
||||||
Censor words, tokens, links, regex, etc.
|
Censor words, tokens, links, regex, etc.
|
||||||
For more advanced filtering, check out the Automod plugin!
|
For more advanced filtering, check out the Automod plugin!
|
||||||
`),
|
`),
|
||||||
|
legacy: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
dependencies: [LogsPlugin],
|
dependencies: [LogsPlugin],
|
||||||
|
|
|
@ -43,6 +43,7 @@ export const RoleAddCmd = selfGrantableRolesCmd({
|
||||||
pluginData,
|
pluginData,
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Unknown ${args.roleNames.length === 1 ? "role" : "roles"}`,
|
`<@!${msg.author.id}> Unknown ${args.roleNames.length === 1 ? "role" : "roles"}`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
lock.unlock();
|
lock.unlock();
|
||||||
return;
|
return;
|
||||||
|
@ -87,6 +88,7 @@ export const RoleAddCmd = selfGrantableRolesCmd({
|
||||||
pluginData,
|
pluginData,
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Got an error while trying to grant you the roles`,
|
`<@!${msg.author.id}> Got an error while trying to grant you the roles`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -118,7 +120,9 @@ export const RoleAddCmd = selfGrantableRolesCmd({
|
||||||
messageParts.push("couldn't recognize some of the roles");
|
messageParts.push("couldn't recognize some of the roles");
|
||||||
}
|
}
|
||||||
|
|
||||||
sendSuccessMessage(pluginData, msg.channel, `<@!${msg.author.id}> ${messageParts.join("; ")}`);
|
sendSuccessMessage(pluginData, msg.channel, `<@!${msg.author.id}> ${messageParts.join("; ")}`, {
|
||||||
|
users: [msg.author.id],
|
||||||
|
});
|
||||||
|
|
||||||
lock.unlock();
|
lock.unlock();
|
||||||
},
|
},
|
||||||
|
|
|
@ -51,12 +51,14 @@ export const RoleRemoveCmd = selfGrantableRolesCmd({
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Removed ${removedRolesStr.join(", ")} ${removedRolesWord};` +
|
`<@!${msg.author.id}> Removed ${removedRolesStr.join(", ")} ${removedRolesWord};` +
|
||||||
` couldn't recognize the other roles you mentioned`,
|
` couldn't recognize the other roles you mentioned`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
sendSuccessMessage(
|
sendSuccessMessage(
|
||||||
pluginData,
|
pluginData,
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Removed ${removedRolesStr.join(", ")} ${removedRolesWord}`,
|
`<@!${msg.author.id}> Removed ${removedRolesStr.join(", ")} ${removedRolesWord}`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
} catch {
|
} catch {
|
||||||
|
@ -64,6 +66,7 @@ export const RoleRemoveCmd = selfGrantableRolesCmd({
|
||||||
pluginData,
|
pluginData,
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Got an error while trying to remove the roles`,
|
`<@!${msg.author.id}> Got an error while trying to remove the roles`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -71,6 +74,7 @@ export const RoleRemoveCmd = selfGrantableRolesCmd({
|
||||||
pluginData,
|
pluginData,
|
||||||
msg.channel,
|
msg.channel,
|
||||||
`<@!${msg.author.id}> Unknown ${args.roleNames.length === 1 ? "role" : "roles"}`,
|
`<@!${msg.author.id}> Unknown ${args.roleNames.length === 1 ? "role" : "roles"}`,
|
||||||
|
{ users: [msg.author.id] },
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -51,6 +51,7 @@ export const SpamPlugin = zeppelinGuildPlugin<SpamPluginType>()({
|
||||||
Basic spam detection and auto-muting.
|
Basic spam detection and auto-muting.
|
||||||
For more advanced spam filtering, check out the Automod plugin!
|
For more advanced spam filtering, check out the Automod plugin!
|
||||||
`),
|
`),
|
||||||
|
legacy: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
dependencies: [LogsPlugin],
|
dependencies: [LogsPlugin],
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
||||||
import { sendErrorMessage } from "../../../pluginUtils";
|
import { sendErrorMessage } from "../../../pluginUtils";
|
||||||
import { customEmojiRegex } from "../../../utils";
|
|
||||||
import { getEmojiInfoEmbed } from "../functions/getEmojiInfoEmbed";
|
import { getEmojiInfoEmbed } from "../functions/getEmojiInfoEmbed";
|
||||||
|
import { getCustomEmojiId } from "../functions/getCustomEmojiId";
|
||||||
import { utilityCmd } from "../types";
|
import { utilityCmd } from "../types";
|
||||||
|
|
||||||
export const EmojiInfoCmd = utilityCmd({
|
export const EmojiInfoCmd = utilityCmd({
|
||||||
|
@ -11,17 +11,17 @@ export const EmojiInfoCmd = utilityCmd({
|
||||||
permission: "can_emojiinfo",
|
permission: "can_emojiinfo",
|
||||||
|
|
||||||
signature: {
|
signature: {
|
||||||
emoji: ct.string({ required: false }),
|
emoji: ct.string({ required: true }),
|
||||||
},
|
},
|
||||||
|
|
||||||
async run({ message, args, pluginData }) {
|
async run({ message, args, pluginData }) {
|
||||||
const emojiIdMatch = args.emoji.match(customEmojiRegex);
|
const emojiId = getCustomEmojiId(args.emoji);
|
||||||
if (!emojiIdMatch?.[2]) {
|
if (!emojiId) {
|
||||||
sendErrorMessage(pluginData, message.channel, "Emoji not found");
|
sendErrorMessage(pluginData, message.channel, "Emoji not found");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const embed = await getEmojiInfoEmbed(pluginData, emojiIdMatch[2]);
|
const embed = await getEmojiInfoEmbed(pluginData, emojiId);
|
||||||
if (!embed) {
|
if (!embed) {
|
||||||
sendErrorMessage(pluginData, message.channel, "Emoji not found");
|
sendErrorMessage(pluginData, message.channel, "Emoji not found");
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -2,26 +2,20 @@ import { Snowflake } from "discord.js";
|
||||||
import { getChannelId, getRoleId } from "knub/dist/utils";
|
import { getChannelId, getRoleId } from "knub/dist/utils";
|
||||||
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
||||||
import { sendErrorMessage } from "../../../pluginUtils";
|
import { sendErrorMessage } from "../../../pluginUtils";
|
||||||
import {
|
import { isValidSnowflake, noop, parseInviteCodeInput, resolveInvite, resolveUser } from "../../../utils";
|
||||||
customEmojiRegex,
|
import { getUserInfoEmbed } from "../functions/getUserInfoEmbed";
|
||||||
isValidSnowflake,
|
|
||||||
noop,
|
|
||||||
parseInviteCodeInput,
|
|
||||||
resolveInvite,
|
|
||||||
resolveUser,
|
|
||||||
} from "../../../utils";
|
|
||||||
import { canReadChannel } from "../../../utils/canReadChannel";
|
import { canReadChannel } from "../../../utils/canReadChannel";
|
||||||
import { resolveMessageTarget } from "../../../utils/resolveMessageTarget";
|
import { resolveMessageTarget } from "../../../utils/resolveMessageTarget";
|
||||||
import { getChannelInfoEmbed } from "../functions/getChannelInfoEmbed";
|
import { getChannelInfoEmbed } from "../functions/getChannelInfoEmbed";
|
||||||
import { getEmojiInfoEmbed } from "../functions/getEmojiInfoEmbed";
|
|
||||||
import { getGuildPreview } from "../functions/getGuildPreview";
|
import { getGuildPreview } from "../functions/getGuildPreview";
|
||||||
import { getInviteInfoEmbed } from "../functions/getInviteInfoEmbed";
|
import { getInviteInfoEmbed } from "../functions/getInviteInfoEmbed";
|
||||||
import { getMessageInfoEmbed } from "../functions/getMessageInfoEmbed";
|
import { getMessageInfoEmbed } from "../functions/getMessageInfoEmbed";
|
||||||
import { getRoleInfoEmbed } from "../functions/getRoleInfoEmbed";
|
import { getRoleInfoEmbed } from "../functions/getRoleInfoEmbed";
|
||||||
|
import { getEmojiInfoEmbed } from "../functions/getEmojiInfoEmbed";
|
||||||
|
import { getCustomEmojiId } from "../functions/getCustomEmojiId";
|
||||||
|
import { utilityCmd } from "../types";
|
||||||
import { getServerInfoEmbed } from "../functions/getServerInfoEmbed";
|
import { getServerInfoEmbed } from "../functions/getServerInfoEmbed";
|
||||||
import { getSnowflakeInfoEmbed } from "../functions/getSnowflakeInfoEmbed";
|
import { getSnowflakeInfoEmbed } from "../functions/getSnowflakeInfoEmbed";
|
||||||
import { getUserInfoEmbed } from "../functions/getUserInfoEmbed";
|
|
||||||
import { utilityCmd } from "../types";
|
|
||||||
|
|
||||||
export const InfoCmd = utilityCmd({
|
export const InfoCmd = utilityCmd({
|
||||||
trigger: "info",
|
trigger: "info",
|
||||||
|
@ -139,9 +133,9 @@ export const InfoCmd = utilityCmd({
|
||||||
|
|
||||||
// 8. Emoji
|
// 8. Emoji
|
||||||
if (userCfg.can_emojiinfo) {
|
if (userCfg.can_emojiinfo) {
|
||||||
const emojiIdMatch = value.match(customEmojiRegex);
|
const emojiId = getCustomEmojiId(value);
|
||||||
if (emojiIdMatch?.[2]) {
|
if (emojiId) {
|
||||||
const embed = await getEmojiInfoEmbed(pluginData, emojiIdMatch[2]);
|
const embed = await getEmojiInfoEmbed(pluginData, emojiId);
|
||||||
if (embed) {
|
if (embed) {
|
||||||
message.channel.send({ embeds: [embed] });
|
message.channel.send({ embeds: [embed] });
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
|
import { Util } from "discord.js";
|
||||||
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
import { commandTypeHelpers as ct } from "../../../commandTypes";
|
||||||
import { canActOn, sendSuccessMessage } from "../../../pluginUtils";
|
|
||||||
import { errorMessage } from "../../../utils";
|
import { errorMessage } from "../../../utils";
|
||||||
|
import { canActOn, sendSuccessMessage } from "../../../pluginUtils";
|
||||||
import { utilityCmd } from "../types";
|
import { utilityCmd } from "../types";
|
||||||
|
|
||||||
export const NicknameCmd = utilityCmd({
|
export const NicknameCmd = utilityCmd({
|
||||||
|
@ -11,10 +12,19 @@ export const NicknameCmd = utilityCmd({
|
||||||
|
|
||||||
signature: {
|
signature: {
|
||||||
member: ct.resolvedMember(),
|
member: ct.resolvedMember(),
|
||||||
nickname: ct.string({ catchAll: true }),
|
nickname: ct.string({ catchAll: true, required: false }),
|
||||||
},
|
},
|
||||||
|
|
||||||
async run({ message: msg, args, pluginData }) {
|
async run({ message: msg, args, pluginData }) {
|
||||||
|
if (!args.nickname) {
|
||||||
|
if (!args.member.nickname) {
|
||||||
|
msg.channel.send(`<@!${args.member.id}> does not have a nickname`);
|
||||||
|
} else {
|
||||||
|
msg.channel.send(`The nickname of <@!${args.member.id}> is **${Util.escapeBold(args.nickname)}**`);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (msg.member.id !== args.member.id && !canActOn(pluginData, msg.member, args.member)) {
|
if (msg.member.id !== args.member.id && !canActOn(pluginData, msg.member, args.member)) {
|
||||||
msg.channel.send(errorMessage("Cannot change nickname: insufficient permissions"));
|
msg.channel.send(errorMessage("Cannot change nickname: insufficient permissions"));
|
||||||
return;
|
return;
|
||||||
|
@ -29,9 +39,7 @@ export const NicknameCmd = utilityCmd({
|
||||||
const oldNickname = args.member.nickname || "<none>";
|
const oldNickname = args.member.nickname || "<none>";
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await args.member.edit({
|
await args.member.setNickname(args.nickname ?? null);
|
||||||
nick: args.nickname,
|
|
||||||
});
|
|
||||||
} catch {
|
} catch {
|
||||||
msg.channel.send(errorMessage("Failed to change nickname"));
|
msg.channel.send(errorMessage("Failed to change nickname"));
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -19,10 +19,13 @@ export const NicknameResetCmd = utilityCmd({
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!args.member.nickname) {
|
||||||
|
msg.channel.send(errorMessage("User does not have a nickname"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await args.member.edit({
|
await args.member.setNickname(null);
|
||||||
nick: "",
|
|
||||||
});
|
|
||||||
} catch {
|
} catch {
|
||||||
msg.channel.send(errorMessage("Failed to reset nickname"));
|
msg.channel.send(errorMessage("Failed to reset nickname"));
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -5,7 +5,7 @@ import { utilityCmd } from "../types";
|
||||||
const { performance } = require("perf_hooks");
|
const { performance } = require("perf_hooks");
|
||||||
|
|
||||||
export const PingCmd = utilityCmd({
|
export const PingCmd = utilityCmd({
|
||||||
trigger: "ping",
|
trigger: ["ping", "pong"],
|
||||||
description: "Test the bot's ping to the Discord API",
|
description: "Test the bot's ping to the Discord API",
|
||||||
permission: "can_ping",
|
permission: "can_ping",
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
const customEmojiRegex = /(?:<a?:[a-z0-9_]{2,32}:)?([1-9]\d+)>?/i;
|
||||||
|
|
||||||
|
export function getCustomEmojiId(str: string): string | null {
|
||||||
|
const emojiIdMatch = str.match(customEmojiRegex);
|
||||||
|
return emojiIdMatch?.[1] ?? null;
|
||||||
|
}
|
|
@ -27,6 +27,7 @@ export interface ZeppelinGuildPluginBlueprint<TPluginData extends GuildPluginDat
|
||||||
description?: TMarkdown;
|
description?: TMarkdown;
|
||||||
usageGuide?: TMarkdown;
|
usageGuide?: TMarkdown;
|
||||||
configurationGuide?: TMarkdown;
|
configurationGuide?: TMarkdown;
|
||||||
|
legacy?: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
configPreprocessor?: (
|
configPreprocessor?: (
|
||||||
|
|
|
@ -49,6 +49,7 @@ export interface ZeppelinPluginInfo {
|
||||||
description?: TMarkdown;
|
description?: TMarkdown;
|
||||||
usageGuide?: TMarkdown;
|
usageGuide?: TMarkdown;
|
||||||
configurationGuide?: TMarkdown;
|
configurationGuide?: TMarkdown;
|
||||||
|
legacy?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CommandInfo {
|
export interface CommandInfo {
|
||||||
|
|
|
@ -321,7 +321,7 @@
|
||||||
actions:
|
actions:
|
||||||
set_counter:
|
set_counter:
|
||||||
counter: "antiraid_decay"
|
counter: "antiraid_decay"
|
||||||
amount: 10 # "Disable after 10min"
|
value: 10 # "Disable after 10min"
|
||||||
|
|
||||||
start_antiraid_timer_high:
|
start_antiraid_timer_high:
|
||||||
triggers:
|
triggers:
|
||||||
|
@ -330,7 +330,7 @@
|
||||||
actions:
|
actions:
|
||||||
set_counter:
|
set_counter:
|
||||||
counter: "antiraid_decay"
|
counter: "antiraid_decay"
|
||||||
amount: 20 # "Disable after 20min"
|
value: 20 # "Disable after 20min"
|
||||||
|
|
||||||
disable_antiraid_after_timer:
|
disable_antiraid_after_timer:
|
||||||
triggers:
|
triggers:
|
||||||
|
|
|
@ -155,7 +155,14 @@
|
||||||
...menu,
|
...menu,
|
||||||
{
|
{
|
||||||
label: 'Plugins',
|
label: 'Plugins',
|
||||||
items: this.plugins.map(plugin => ({
|
items: this.plugins.filter(plugin => !plugin.info.legacy).map(plugin => ({
|
||||||
|
label: plugin.info.prettyName || plugin.name,
|
||||||
|
to: `/docs/plugins/${plugin.name}`,
|
||||||
|
})),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Legacy Plugins",
|
||||||
|
items: this.plugins.filter(plugin => plugin.info.legacy).map(plugin => ({
|
||||||
label: plugin.info.prettyName || plugin.name,
|
label: plugin.info.prettyName || plugin.name,
|
||||||
to: `/docs/plugins/${plugin.name}`,
|
to: `/docs/plugins/${plugin.name}`,
|
||||||
})),
|
})),
|
||||||
|
|
Loading…
Add table
Reference in a new issue