mirror of
https://github.com/ZeppelinBot/Zeppelin.git
synced 2025-03-15 05:41:51 +00:00
Improve error handling with mutes
This commit is contained in:
parent
599c365640
commit
61804d9e64
4 changed files with 61 additions and 18 deletions
|
@ -5,6 +5,8 @@ import { asyncMap, convertDelayStringToMS, resolveMember, tDelayString, tNullabl
|
||||||
import { resolveActionContactMethods } from "../functions/resolveActionContactMethods";
|
import { resolveActionContactMethods } from "../functions/resolveActionContactMethods";
|
||||||
import { ModActionsPlugin } from "../../ModActions/ModActionsPlugin";
|
import { ModActionsPlugin } from "../../ModActions/ModActionsPlugin";
|
||||||
import { MutesPlugin } from "../../Mutes/MutesPlugin";
|
import { MutesPlugin } from "../../Mutes/MutesPlugin";
|
||||||
|
import { ERRORS, RecoverablePluginError } from "../../../RecoverablePluginError";
|
||||||
|
import { LogsPlugin } from "../../Logs/LogsPlugin";
|
||||||
|
|
||||||
export const MuteAction = automodAction({
|
export const MuteAction = automodAction({
|
||||||
configType: t.type({
|
configType: t.type({
|
||||||
|
@ -18,7 +20,7 @@ export const MuteAction = automodAction({
|
||||||
notify: null, // Use defaults from ModActions
|
notify: null, // Use defaults from ModActions
|
||||||
},
|
},
|
||||||
|
|
||||||
async apply({ pluginData, contexts, actionConfig, matchResult }) {
|
async apply({ pluginData, contexts, actionConfig, ruleName, matchResult }) {
|
||||||
const duration = actionConfig.duration ? convertDelayStringToMS(actionConfig.duration) : null;
|
const duration = actionConfig.duration ? convertDelayStringToMS(actionConfig.duration) : null;
|
||||||
const reason = actionConfig.reason || "Muted automatically";
|
const reason = actionConfig.reason || "Muted automatically";
|
||||||
const contactMethods = resolveActionContactMethods(pluginData, actionConfig);
|
const contactMethods = resolveActionContactMethods(pluginData, actionConfig);
|
||||||
|
@ -32,7 +34,17 @@ export const MuteAction = automodAction({
|
||||||
|
|
||||||
const mutes = pluginData.getPlugin(MutesPlugin);
|
const mutes = pluginData.getPlugin(MutesPlugin);
|
||||||
for (const userId of userIdsToMute) {
|
for (const userId of userIdsToMute) {
|
||||||
await mutes.muteUser(userId, duration, reason, { contactMethods, caseArgs });
|
try {
|
||||||
|
await mutes.muteUser(userId, duration, reason, { contactMethods, caseArgs });
|
||||||
|
} catch (e) {
|
||||||
|
if (e instanceof RecoverablePluginError && e.code === ERRORS.NO_MUTE_ROLE_IN_CONFIG) {
|
||||||
|
pluginData.getPlugin(LogsPlugin).log(LogType.BOT_ALERT, {
|
||||||
|
body: `Failed to mute <@!${userId}> in Automod rule \`${ruleName}\` because a mute role has not been specified in server config`,
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -9,6 +9,7 @@ import { onMessageCreate } from "./util/onMessageCreate";
|
||||||
import { clearOldRecentActions } from "./util/clearOldRecentActions";
|
import { clearOldRecentActions } from "./util/clearOldRecentActions";
|
||||||
import { SpamVoiceJoinEvt, SpamVoiceSwitchEvt } from "./events/SpamVoiceEvt";
|
import { SpamVoiceJoinEvt, SpamVoiceSwitchEvt } from "./events/SpamVoiceEvt";
|
||||||
import { trimPluginDescription } from "../../utils";
|
import { trimPluginDescription } from "../../utils";
|
||||||
|
import { LogsPlugin } from "../Logs/LogsPlugin";
|
||||||
|
|
||||||
const defaultOptions: PluginOptions<SpamPluginType> = {
|
const defaultOptions: PluginOptions<SpamPluginType> = {
|
||||||
config: {
|
config: {
|
||||||
|
@ -51,6 +52,8 @@ export const SpamPlugin = zeppelinPlugin<SpamPluginType>()("spam", {
|
||||||
`),
|
`),
|
||||||
},
|
},
|
||||||
|
|
||||||
|
dependencies: [LogsPlugin],
|
||||||
|
|
||||||
configSchema: ConfigSchema,
|
configSchema: ConfigSchema,
|
||||||
defaultOptions,
|
defaultOptions,
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
import { SavedMessage } from "src/data/entities/SavedMessage";
|
import { SavedMessage } from "src/data/entities/SavedMessage";
|
||||||
import { RecentActionType, TBaseSingleSpamConfig, SpamPluginType } from "../types";
|
import { RecentActionType, SpamPluginType, TBaseSingleSpamConfig } from "../types";
|
||||||
import moment from "moment-timezone";
|
import moment from "moment-timezone";
|
||||||
import { MuteResult } from "src/plugins/Mutes/types";
|
import { MuteResult } from "src/plugins/Mutes/types";
|
||||||
import { convertDelayStringToMS, trimLines, stripObjectToScalars, resolveMember, noop, DBDateFormat } from "src/utils";
|
import { convertDelayStringToMS, DBDateFormat, noop, resolveMember, stripObjectToScalars, trimLines } from "src/utils";
|
||||||
import { LogType } from "src/data/LogType";
|
import { LogType } from "src/data/LogType";
|
||||||
import { CaseTypes } from "src/data/CaseTypes";
|
import { CaseTypes } from "src/data/CaseTypes";
|
||||||
import { logger } from "src/logger";
|
import { logger } from "src/logger";
|
||||||
|
@ -14,6 +14,8 @@ import { getRecentActionCount } from "./getRecentActionCount";
|
||||||
import { getRecentActions } from "./getRecentActions";
|
import { getRecentActions } from "./getRecentActions";
|
||||||
import { clearRecentUserActions } from "./clearRecentUserActions";
|
import { clearRecentUserActions } from "./clearRecentUserActions";
|
||||||
import { saveSpamArchives } from "./saveSpamArchives";
|
import { saveSpamArchives } from "./saveSpamArchives";
|
||||||
|
import { LogsPlugin } from "../../Logs/LogsPlugin";
|
||||||
|
import { ERRORS, RecoverablePluginError } from "../../../RecoverablePluginError";
|
||||||
|
|
||||||
export async function logAndDetectMessageSpam(
|
export async function logAndDetectMessageSpam(
|
||||||
pluginData: PluginData<SpamPluginType>,
|
pluginData: PluginData<SpamPluginType>,
|
||||||
|
@ -38,6 +40,7 @@ export async function logAndDetectMessageSpam(
|
||||||
async () => {
|
async () => {
|
||||||
const timestamp = moment.utc(savedMessage.posted_at, DBDateFormat).valueOf();
|
const timestamp = moment.utc(savedMessage.posted_at, DBDateFormat).valueOf();
|
||||||
const member = await resolveMember(pluginData.client, pluginData.guild, savedMessage.user_id);
|
const member = await resolveMember(pluginData.client, pluginData.guild, savedMessage.user_id);
|
||||||
|
const logs = pluginData.getPlugin(LogsPlugin);
|
||||||
|
|
||||||
// Log this action...
|
// Log this action...
|
||||||
addRecentAction(
|
addRecentAction(
|
||||||
|
@ -69,12 +72,23 @@ export async function logAndDetectMessageSpam(
|
||||||
if (spamConfig.mute && member) {
|
if (spamConfig.mute && member) {
|
||||||
const mutesPlugin = pluginData.getPlugin(MutesPlugin);
|
const mutesPlugin = pluginData.getPlugin(MutesPlugin);
|
||||||
const muteTime = spamConfig.mute_time ? convertDelayStringToMS(spamConfig.mute_time.toString()) : 120 * 1000;
|
const muteTime = spamConfig.mute_time ? convertDelayStringToMS(spamConfig.mute_time.toString()) : 120 * 1000;
|
||||||
muteResult = await mutesPlugin.muteUser(member.id, muteTime, "Automatic spam detection", {
|
|
||||||
caseArgs: {
|
try {
|
||||||
modId: pluginData.client.user.id,
|
muteResult = await mutesPlugin.muteUser(member.id, muteTime, "Automatic spam detection", {
|
||||||
postInCaseLogOverride: false,
|
caseArgs: {
|
||||||
},
|
modId: pluginData.client.user.id,
|
||||||
});
|
postInCaseLogOverride: false,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
} catch (e) {
|
||||||
|
if (e instanceof RecoverablePluginError && e.code === ERRORS.NO_MUTE_ROLE_IN_CONFIG) {
|
||||||
|
logs.log(LogType.BOT_ALERT, {
|
||||||
|
body: `Failed to mute <@!${member.id}> in \`spam\` plugin because a mute role has not been specified in server config`,
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the offending message IDs
|
// Get the offending message IDs
|
||||||
|
@ -150,7 +164,7 @@ export async function logAndDetectMessageSpam(
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create a log entry
|
// Create a log entry
|
||||||
pluginData.state.logs.log(LogType.MESSAGE_SPAM_DETECTED, {
|
logs.log(LogType.MESSAGE_SPAM_DETECTED, {
|
||||||
member: stripObjectToScalars(member, ["user", "roles"]),
|
member: stripObjectToScalars(member, ["user", "roles"]),
|
||||||
channel: stripObjectToScalars(channel),
|
channel: stripObjectToScalars(channel),
|
||||||
description,
|
description,
|
||||||
|
|
|
@ -8,6 +8,8 @@ import { CasesPlugin } from "src/plugins/Cases/CasesPlugin";
|
||||||
import { CaseTypes } from "src/data/CaseTypes";
|
import { CaseTypes } from "src/data/CaseTypes";
|
||||||
import { clearRecentUserActions } from "./clearRecentUserActions";
|
import { clearRecentUserActions } from "./clearRecentUserActions";
|
||||||
import { LogType } from "src/data/LogType";
|
import { LogType } from "src/data/LogType";
|
||||||
|
import { ERRORS, RecoverablePluginError } from "../../../RecoverablePluginError";
|
||||||
|
import { LogsPlugin } from "../../Logs/LogsPlugin";
|
||||||
|
|
||||||
export async function logAndDetectOtherSpam(
|
export async function logAndDetectOtherSpam(
|
||||||
pluginData: PluginData<SpamPluginType>,
|
pluginData: PluginData<SpamPluginType>,
|
||||||
|
@ -31,16 +33,28 @@ export async function logAndDetectOtherSpam(
|
||||||
if (recentActionsCount > spamConfig.count) {
|
if (recentActionsCount > spamConfig.count) {
|
||||||
const member = await resolveMember(pluginData.client, pluginData.guild, userId);
|
const member = await resolveMember(pluginData.client, pluginData.guild, userId);
|
||||||
const details = `${description} (over ${spamConfig.count} in ${spamConfig.interval}s)`;
|
const details = `${description} (over ${spamConfig.count} in ${spamConfig.interval}s)`;
|
||||||
|
const logs = pluginData.getPlugin(LogsPlugin);
|
||||||
|
|
||||||
if (spamConfig.mute && member) {
|
if (spamConfig.mute && member) {
|
||||||
const mutesPlugin = pluginData.getPlugin(MutesPlugin);
|
const mutesPlugin = pluginData.getPlugin(MutesPlugin);
|
||||||
const muteTime = spamConfig.mute_time ? convertDelayStringToMS(spamConfig.mute_time.toString()) : 120 * 1000;
|
const muteTime = spamConfig.mute_time ? convertDelayStringToMS(spamConfig.mute_time.toString()) : 120 * 1000;
|
||||||
await mutesPlugin.muteUser(member.id, muteTime, "Automatic spam detection", {
|
|
||||||
caseArgs: {
|
try {
|
||||||
modId: pluginData.client.user.id,
|
await mutesPlugin.muteUser(member.id, muteTime, "Automatic spam detection", {
|
||||||
extraNotes: [`Details: ${details}`],
|
caseArgs: {
|
||||||
},
|
modId: pluginData.client.user.id,
|
||||||
});
|
extraNotes: [`Details: ${details}`],
|
||||||
|
},
|
||||||
|
});
|
||||||
|
} catch (e) {
|
||||||
|
if (e instanceof RecoverablePluginError && e.code === ERRORS.NO_MUTE_ROLE_IN_CONFIG) {
|
||||||
|
logs.log(LogType.BOT_ALERT, {
|
||||||
|
body: `Failed to mute <@!${member.id}> in \`spam\` plugin because a mute role has not been specified in server config`,
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// If we're not muting the user, just add a note on them
|
// If we're not muting the user, just add a note on them
|
||||||
const casesPlugin = pluginData.getPlugin(CasesPlugin);
|
const casesPlugin = pluginData.getPlugin(CasesPlugin);
|
||||||
|
@ -55,7 +69,7 @@ export async function logAndDetectOtherSpam(
|
||||||
// Clear recent cases
|
// Clear recent cases
|
||||||
clearRecentUserActions(pluginData, RecentActionType.VoiceChannelMove, userId, actionGroupId);
|
clearRecentUserActions(pluginData, RecentActionType.VoiceChannelMove, userId, actionGroupId);
|
||||||
|
|
||||||
pluginData.state.logs.log(LogType.OTHER_SPAM_DETECTED, {
|
logs.log(LogType.OTHER_SPAM_DETECTED, {
|
||||||
member: stripObjectToScalars(member, ["user", "roles"]),
|
member: stripObjectToScalars(member, ["user", "roles"]),
|
||||||
description,
|
description,
|
||||||
limit: spamConfig.count,
|
limit: spamConfig.count,
|
||||||
|
|
Loading…
Add table
Reference in a new issue