mirror of
https://github.com/ZeppelinBot/Zeppelin.git
synced 2025-05-14 22:05:01 +00:00
Merge branch 'master' of github.com:ZeppelinBot/Zeppelin into feat/application-commands
This commit is contained in:
commit
2c0e4b37ca
235 changed files with 3464 additions and 4799 deletions
|
@ -6,7 +6,7 @@ import { onGuildEvent } from "../../data/GuildEvents";
|
|||
import { GuildLogs } from "../../data/GuildLogs";
|
||||
import { GuildMutes } from "../../data/GuildMutes";
|
||||
import { GuildTempbans } from "../../data/GuildTempbans";
|
||||
import { makeIoTsConfigParser, mapToPublicFn } from "../../pluginUtils";
|
||||
import { mapToPublicFn } from "../../pluginUtils";
|
||||
import { MINUTES, trimPluginDescription } from "../../utils";
|
||||
import { CasesPlugin } from "../Cases/CasesPlugin";
|
||||
import { LogsPlugin } from "../Logs/LogsPlugin";
|
||||
|
@ -74,11 +74,11 @@ import { warnMember } from "./functions/warnMember";
|
|||
import {
|
||||
AttachmentLinkReactionType,
|
||||
BanOptions,
|
||||
ConfigSchema,
|
||||
KickOptions,
|
||||
ModActionsPluginType,
|
||||
WarnOptions,
|
||||
modActionsSlashGroup,
|
||||
zModActionsConfig,
|
||||
} from "./types";
|
||||
|
||||
const defaultOptions = {
|
||||
|
@ -155,11 +155,11 @@ export const ModActionsPlugin = zeppelinGuildPlugin<ModActionsPluginType>()({
|
|||
description: trimPluginDescription(`
|
||||
This plugin contains the 'typical' mod actions such as warning, muting, kicking, banning, etc.
|
||||
`),
|
||||
configSchema: ConfigSchema,
|
||||
configSchema: zModActionsConfig,
|
||||
},
|
||||
|
||||
dependencies: () => [TimeAndDatePlugin, CasesPlugin, MutesPlugin, LogsPlugin],
|
||||
configParser: makeIoTsConfigParser(ConfigSchema),
|
||||
configParser: (input) => zModActionsConfig.parse(input),
|
||||
defaultOptions,
|
||||
|
||||
events: [CreateBanCaseOnManualBanEvt, CreateUnbanCaseOnManualUnbanEvt, PostAlertOnMemberJoinEvt, AuditLogEvents],
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
import { commandTypeHelpers as ct } from "../../../../commandTypes";
|
||||
import { resolveUser } from "../../../../utils";
|
||||
import { resolveMember, resolveUser, UnknownUser } from "../../../../utils";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { actualCasesCmd } from "../../functions/actualCommands/actualCasesCmd";
|
||||
import { modActionsMsgCmd } from "../../types";
|
||||
|
@ -31,8 +31,11 @@ export const CasesUserMsgCmd = modActionsMsgCmd({
|
|||
],
|
||||
|
||||
async run({ pluginData, message: msg, args }) {
|
||||
const user = await resolveUser(pluginData.client, args.user);
|
||||
if (!user.id) {
|
||||
const user =
|
||||
(await resolveMember(pluginData.client, pluginData.guild, args.user)) ||
|
||||
(await resolveUser(pluginData.client, args.user));
|
||||
|
||||
if (user instanceof UnknownUser) {
|
||||
pluginData.getPlugin(CommonPlugin).sendErrorMessage(msg, `User not found`);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -42,7 +42,9 @@ export const AuditLogEvents = modActionsEvt({
|
|||
caseId: existingCaseId,
|
||||
modId: auditLogEntry.executor?.id || "0",
|
||||
body: auditLogEntry.reason || "",
|
||||
noteDetails: [`Timeout set to expire on <t:${moment.utc(muteChange.new as string).valueOf()}>`],
|
||||
noteDetails: [
|
||||
`Timeout set to expire on <t:${Math.ceil(moment.utc(muteChange.new as string).valueOf() / 1_000)}>`,
|
||||
],
|
||||
});
|
||||
} else {
|
||||
await casesPlugin.createCase({
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
import { PermissionsBitField, Snowflake, TextChannel } from "discord.js";
|
||||
import { renderUserUsername, resolveMember } from "../../../utils";
|
||||
import { renderUsername, resolveMember } from "../../../utils";
|
||||
import { hasDiscordPermissions } from "../../../utils/hasDiscordPermissions";
|
||||
import { LogsPlugin } from "../../Logs/LogsPlugin";
|
||||
import { modActionsEvt } from "../types";
|
||||
|
@ -46,9 +46,7 @@ export const PostAlertOnMemberJoinEvt = modActionsEvt({
|
|||
}
|
||||
|
||||
await alertChannel.send(
|
||||
`<@!${member.id}> (${renderUserUsername(member.user)} \`${member.id}\`) joined with ${
|
||||
actions.length
|
||||
} prior record(s)`,
|
||||
`<@!${member.id}> (${renderUsername(member)} \`${member.id}\`) joined with ${actions.length} prior record(s)`,
|
||||
);
|
||||
}
|
||||
},
|
||||
|
|
|
@ -3,7 +3,7 @@ import { GuildPluginData } from "knub";
|
|||
import { CaseTypes } from "../../../../data/CaseTypes";
|
||||
import { Case } from "../../../../data/entities/Case";
|
||||
import { canActOn } from "../../../../pluginUtils";
|
||||
import { UnknownUser, renderUserUsername, resolveMember } from "../../../../utils";
|
||||
import { UnknownUser, renderUsername, resolveMember } from "../../../../utils";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { LogsPlugin } from "../../../Logs/LogsPlugin";
|
||||
|
@ -49,7 +49,7 @@ export async function actualAddCaseCmd(
|
|||
if (user) {
|
||||
pluginData
|
||||
.getPlugin(CommonPlugin)
|
||||
.sendSuccessMessage(context, `Case #${theCase.case_number} created for **${renderUserUsername(user)}**`);
|
||||
.sendSuccessMessage(context, `Case #${theCase.case_number} created for **${renderUsername(user)}**`);
|
||||
} else {
|
||||
pluginData.getPlugin(CommonPlugin).sendSuccessMessage(context, `Case #${theCase.case_number} created`);
|
||||
}
|
||||
|
|
|
@ -5,7 +5,7 @@ import { getMemberLevel } from "knub/helpers";
|
|||
import { CaseTypes } from "../../../../data/CaseTypes";
|
||||
import { clearExpiringTempban, registerExpiringTempban } from "../../../../data/loops/expiringTempbansLoop";
|
||||
import { canActOn, getContextChannel } from "../../../../pluginUtils";
|
||||
import { UnknownUser, UserNotificationMethod, renderUserUsername, resolveMember } from "../../../../utils";
|
||||
import { UnknownUser, UserNotificationMethod, renderUsername, resolveMember } from "../../../../utils";
|
||||
import { banLock } from "../../../../utils/lockNameHelpers";
|
||||
import { waitForButtonConfirm } from "../../../../utils/waitForInteraction";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
|
@ -183,7 +183,7 @@ export async function actualBanCmd(
|
|||
// Confirm the action to the moderator
|
||||
let response = "";
|
||||
if (!forceban) {
|
||||
response = `Banned **${renderUserUsername(user)}** ${forTime}(Case #${banResult.case.case_number})`;
|
||||
response = `Banned **${renderUsername(user)}** ${forTime}(Case #${banResult.case.case_number})`;
|
||||
if (banResult.notifyResult.text) response += ` (${banResult.notifyResult.text})`;
|
||||
} else {
|
||||
response = `Member forcebanned ${forTime}(Case #${banResult.case.case_number})`;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { APIEmbed, ChatInputCommandInteraction, Message, User } from "discord.js";
|
||||
import { APIEmbed, ChatInputCommandInteraction, GuildMember, Message, User } from "discord.js";
|
||||
import { GuildPluginData } from "knub";
|
||||
import { In } from "typeorm";
|
||||
import { FindOptionsWhere } from "typeorm/find-options/FindOptionsWhere";
|
||||
|
@ -9,13 +9,13 @@ import {
|
|||
UnknownUser,
|
||||
chunkArray,
|
||||
emptyEmbedValue,
|
||||
renderUserUsername,
|
||||
renderUsername,
|
||||
resolveMember,
|
||||
resolveUser,
|
||||
trimLines,
|
||||
} from "../../../../utils";
|
||||
import { asyncMap } from "../../../../utils/async";
|
||||
import { createPaginatedMessage } from "../../../../utils/createPaginatedMessage";
|
||||
import { getChunkedEmbedFields } from "../../../../utils/getChunkedEmbedFields";
|
||||
import { getGuildPrefix } from "../../../../utils/getGuildPrefix";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
|
@ -49,7 +49,7 @@ async function casesUserCmd(
|
|||
context: Message | ChatInputCommandInteraction,
|
||||
author: User,
|
||||
modId: string | null,
|
||||
user: User | UnknownUser,
|
||||
user: GuildMember | User | UnknownUser,
|
||||
modName: string,
|
||||
typesToShow: CaseTypes[],
|
||||
hidden: boolean | null,
|
||||
|
@ -67,7 +67,7 @@ async function casesUserCmd(
|
|||
const hiddenCases = cases.filter((c) => c.is_hidden);
|
||||
|
||||
const userName =
|
||||
user instanceof UnknownUser && cases.length ? cases[cases.length - 1].user_name : renderUserUsername(user);
|
||||
user instanceof UnknownUser && cases.length ? cases[cases.length - 1].user_name : renderUsername(user);
|
||||
|
||||
if (cases.length === 0) {
|
||||
await sendContextResponse(context, `No cases found for **${userName}**${modId ? ` by ${modName}` : ""}.`);
|
||||
|
@ -92,7 +92,6 @@ async function casesUserCmd(
|
|||
|
||||
// Compact view (= regular message with a preview of each case)
|
||||
const lines = await asyncMap(casesToDisplay, (c) => casesPlugin.getCaseSummary(c, true, author.id));
|
||||
|
||||
const prefix = getGuildPrefix(pluginData);
|
||||
const linesPerChunk = 10;
|
||||
const lineChunks = chunkArray(lines, linesPerChunk);
|
||||
|
@ -124,12 +123,10 @@ async function casesUserCmd(
|
|||
lineChunks.length === 1
|
||||
? `Cases for ${userName}${modId ? ` by ${modName}` : ""} (${lines.length} total)`
|
||||
: `Cases ${chunkStart}–${chunkEnd} of ${lines.length} for ${userName}`,
|
||||
icon_url: user instanceof User ? user.displayAvatarURL() : undefined,
|
||||
icon_url: user instanceof UnknownUser ? undefined : user.displayAvatarURL(),
|
||||
},
|
||||
fields: [
|
||||
...getChunkedEmbedFields(emptyEmbedValue, linesInChunk.join("\n")),
|
||||
...(isLastChunk ? [footerField] : []),
|
||||
],
|
||||
description: linesInChunk.join("\n"),
|
||||
fields: [...(isLastChunk ? [footerField] : [])],
|
||||
} satisfies APIEmbed;
|
||||
|
||||
sendContextResponse(context, { embeds: [embed] });
|
||||
|
@ -141,7 +138,7 @@ async function casesModCmd(
|
|||
context: Message | ChatInputCommandInteraction,
|
||||
author: User,
|
||||
modId: string | null,
|
||||
mod: User | UnknownUser,
|
||||
mod: GuildMember | User | UnknownUser,
|
||||
modName: string,
|
||||
typesToShow: CaseTypes[],
|
||||
hidden: boolean | null,
|
||||
|
@ -188,10 +185,10 @@ async function casesModCmd(
|
|||
const embed = {
|
||||
author: {
|
||||
name: title,
|
||||
icon_url: mod instanceof User ? mod.displayAvatarURL() : undefined,
|
||||
icon_url: mod instanceof UnknownUser ? undefined : mod.displayAvatarURL(),
|
||||
},
|
||||
description: lines.join("\n"),
|
||||
fields: [
|
||||
...getChunkedEmbedFields(emptyEmbedValue, lines.join("\n")),
|
||||
{
|
||||
name: emptyEmbedValue,
|
||||
value: trimLines(`
|
||||
|
@ -214,7 +211,7 @@ export async function actualCasesCmd(
|
|||
pluginData: GuildPluginData<ModActionsPluginType>,
|
||||
context: Message | ChatInputCommandInteraction,
|
||||
modId: string | null,
|
||||
user: User | UnknownUser | null,
|
||||
user: GuildMember | User | UnknownUser | null,
|
||||
author: User,
|
||||
notes: boolean | null,
|
||||
warns: boolean | null,
|
||||
|
@ -226,8 +223,10 @@ export async function actualCasesCmd(
|
|||
hidden: boolean | null,
|
||||
expand: boolean | null,
|
||||
) {
|
||||
const mod = modId ? await resolveUser(pluginData.client, modId) : null;
|
||||
const modName = modId ? (mod instanceof User ? renderUserUsername(mod) : modId) : renderUserUsername(author);
|
||||
const mod = modId
|
||||
? (await resolveMember(pluginData.client, pluginData.guild, modId)) || (await resolveUser(pluginData.client, modId))
|
||||
: null;
|
||||
const modName = modId ? (mod instanceof UnknownUser ? modId : renderUsername(mod!)) : renderUsername(author);
|
||||
|
||||
let typesToShow: CaseTypes[] = [];
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@ import { ChatInputCommandInteraction, GuildMember, Message } from "discord.js";
|
|||
import { GuildPluginData, helpers } from "knub";
|
||||
import { Case } from "../../../../data/entities/Case";
|
||||
import { getContextChannel, sendContextResponse } from "../../../../pluginUtils";
|
||||
import { SECONDS } from "../../../../utils";
|
||||
import { SECONDS, renderUsername } from "../../../../utils";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { LogsPlugin } from "../../../Logs/LogsPlugin";
|
||||
|
@ -58,7 +58,7 @@ export async function actualDeleteCaseCmd(
|
|||
}
|
||||
}
|
||||
|
||||
const deletedByName = author.user.tag;
|
||||
const deletedByName = renderUsername(author);
|
||||
|
||||
const timeAndDate = pluginData.getPlugin(TimeAndDatePlugin);
|
||||
const deletedAt = timeAndDate.inGuildTz().format(timeAndDate.getDateFormat("pretty_datetime"));
|
||||
|
|
|
@ -2,14 +2,7 @@ import { Attachment, ChatInputCommandInteraction, GuildMember, Message, User } f
|
|||
import { GuildPluginData } from "knub";
|
||||
import { LogType } from "../../../../data/LogType";
|
||||
import { canActOn } from "../../../../pluginUtils";
|
||||
import {
|
||||
DAYS,
|
||||
SECONDS,
|
||||
UnknownUser,
|
||||
UserNotificationMethod,
|
||||
renderUserUsername,
|
||||
resolveMember,
|
||||
} from "../../../../utils";
|
||||
import { DAYS, SECONDS, UnknownUser, UserNotificationMethod, renderUsername, resolveMember } from "../../../../utils";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { IgnoredEventType, ModActionsPluginType } from "../../types";
|
||||
import { handleAttachmentLinkDetectionAndGetRestriction } from "../attachmentLinkReaction";
|
||||
|
@ -91,7 +84,7 @@ export async function actualKickCmd(
|
|||
}
|
||||
|
||||
// Confirm the action to the moderator
|
||||
let response = `Kicked **${renderUserUsername(memberToKick.user)}** (Case #${kickResult.case.case_number})`;
|
||||
let response = `Kicked **${renderUsername(memberToKick.user)}** (Case #${kickResult.case.case_number})`;
|
||||
|
||||
if (kickResult.notifyResult.text) response += ` (${kickResult.notifyResult.text})`;
|
||||
pluginData.getPlugin(CommonPlugin).sendSuccessMessage(context, response);
|
||||
|
|
|
@ -8,7 +8,7 @@ import {
|
|||
UserNotificationMethod,
|
||||
asSingleLine,
|
||||
isDiscordAPIError,
|
||||
renderUserUsername,
|
||||
renderUsername,
|
||||
} from "../../../../utils";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { MutesPlugin } from "../../../Mutes/MutesPlugin";
|
||||
|
@ -80,24 +80,24 @@ export async function actualMuteCmd(
|
|||
if (time) {
|
||||
if (muteResult.updatedExistingMute) {
|
||||
response = asSingleLine(`
|
||||
Updated **${renderUserUsername(user)}**'s
|
||||
Updated **${renderUsername(user)}**'s
|
||||
mute to ${timeUntilUnmute} (Case #${muteResult.case.case_number})
|
||||
`);
|
||||
} else {
|
||||
response = asSingleLine(`
|
||||
Muted **${renderUserUsername(user)}**
|
||||
Muted **${renderUsername(user)}**
|
||||
for ${timeUntilUnmute} (Case #${muteResult.case.case_number})
|
||||
`);
|
||||
}
|
||||
} else {
|
||||
if (muteResult.updatedExistingMute) {
|
||||
response = asSingleLine(`
|
||||
Updated **${renderUserUsername(user)}**'s
|
||||
Updated **${renderUsername(user)}**'s
|
||||
mute to indefinite (Case #${muteResult.case.case_number})
|
||||
`);
|
||||
} else {
|
||||
response = asSingleLine(`
|
||||
Muted **${renderUserUsername(user)}**
|
||||
Muted **${renderUsername(user)}**
|
||||
indefinitely (Case #${muteResult.case.case_number})
|
||||
`);
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { Attachment, ChatInputCommandInteraction, Message, User } from "discord.js";
|
||||
import { GuildPluginData } from "knub";
|
||||
import { CaseTypes } from "../../../../data/CaseTypes";
|
||||
import { UnknownUser, renderUserUsername } from "../../../../utils";
|
||||
import { UnknownUser, renderUsername } from "../../../../utils";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { LogsPlugin } from "../../../Logs/LogsPlugin";
|
||||
|
@ -21,7 +21,7 @@ export async function actualNoteCmd(
|
|||
return;
|
||||
}
|
||||
|
||||
const userName = renderUserUsername(user);
|
||||
const userName = renderUsername(user);
|
||||
const reason = await formatReasonWithMessageLinkForAttachments(pluginData, note, context, attachments);
|
||||
|
||||
const casesPlugin = pluginData.getPlugin(CasesPlugin);
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { Attachment, ChatInputCommandInteraction, GuildMember, Message, User } from "discord.js";
|
||||
import humanizeDuration from "humanize-duration";
|
||||
import { GuildPluginData } from "knub";
|
||||
import { UnknownUser, asSingleLine, renderUserUsername } from "../../../../utils";
|
||||
import { UnknownUser, asSingleLine, renderUsername } from "../../../../utils";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
import { MutesPlugin } from "../../../Mutes/MutesPlugin";
|
||||
import { ModActionsPluginType } from "../../types";
|
||||
|
@ -45,7 +45,7 @@ export async function actualUnmuteCmd(
|
|||
pluginData.getPlugin(CommonPlugin).sendSuccessMessage(
|
||||
context,
|
||||
asSingleLine(`
|
||||
Unmuting **${renderUserUsername(user)}**
|
||||
Unmuting **${renderUsername(user)}**
|
||||
in ${timeUntilUnmute} (Case #${result.case.case_number})
|
||||
`),
|
||||
);
|
||||
|
@ -53,7 +53,7 @@ export async function actualUnmuteCmd(
|
|||
pluginData.getPlugin(CommonPlugin).sendSuccessMessage(
|
||||
context,
|
||||
asSingleLine(`
|
||||
Unmuted **${renderUserUsername(user)}**
|
||||
Unmuted **${renderUsername(user)}**
|
||||
(Case #${result.case.case_number})
|
||||
`),
|
||||
);
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { Attachment, ChatInputCommandInteraction, GuildMember, Message } from "discord.js";
|
||||
import { GuildPluginData } from "knub";
|
||||
import { CaseTypes } from "../../../../data/CaseTypes";
|
||||
import { UserNotificationMethod, renderUserUsername } from "../../../../utils";
|
||||
import { UserNotificationMethod, renderUsername } from "../../../../utils";
|
||||
import { waitForButtonConfirm } from "../../../../utils/waitForInteraction";
|
||||
import { CasesPlugin } from "../../../Cases/CasesPlugin";
|
||||
import { CommonPlugin } from "../../../Common/CommonPlugin";
|
||||
|
@ -63,6 +63,6 @@ export async function actualWarnCmd(
|
|||
.getPlugin(CommonPlugin)
|
||||
.sendSuccessMessage(
|
||||
context,
|
||||
`Warned **${renderUserUsername(memberToWarn.user)}** (Case #${warnResult.case.case_number})${messageResultText}`,
|
||||
`Warned **${renderUsername(memberToWarn.user)}** (Case #${warnResult.case.case_number})${messageResultText}`,
|
||||
);
|
||||
}
|
||||
|
|
|
@ -5,7 +5,7 @@ import { CaseTypes } from "../../../data/CaseTypes";
|
|||
import { LogType } from "../../../data/LogType";
|
||||
import { registerExpiringTempban } from "../../../data/loops/expiringTempbansLoop";
|
||||
import { logger } from "../../../logger";
|
||||
import { TemplateSafeValueContainer, renderTemplate } from "../../../templateFormatter";
|
||||
import { TemplateParseError, TemplateSafeValueContainer, renderTemplate } from "../../../templateFormatter";
|
||||
import {
|
||||
DAYS,
|
||||
SECONDS,
|
||||
|
@ -53,30 +53,52 @@ export async function banUserId(
|
|||
|
||||
if (contactMethods.length) {
|
||||
if (!banTime && config.ban_message) {
|
||||
const banMessage = await renderTemplate(
|
||||
config.ban_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: banOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, banOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
let banMessage: string;
|
||||
try {
|
||||
banMessage = await renderTemplate(
|
||||
config.ban_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: banOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, banOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
} catch (err) {
|
||||
if (err instanceof TemplateParseError) {
|
||||
return {
|
||||
status: "failed",
|
||||
error: `Invalid ban_message format: ${err.message}`,
|
||||
};
|
||||
}
|
||||
throw err;
|
||||
}
|
||||
|
||||
notifyResult = await notifyUser(member.user, banMessage, contactMethods);
|
||||
} else if (banTime && config.tempban_message) {
|
||||
const banMessage = await renderTemplate(
|
||||
config.tempban_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: banOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, banOptions.caseArgs.modId))
|
||||
: null,
|
||||
banTime: humanizeDuration(banTime),
|
||||
}),
|
||||
);
|
||||
let banMessage: string;
|
||||
try {
|
||||
banMessage = await renderTemplate(
|
||||
config.tempban_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: banOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, banOptions.caseArgs.modId))
|
||||
: null,
|
||||
banTime: humanizeDuration(banTime),
|
||||
}),
|
||||
);
|
||||
} catch (err) {
|
||||
if (err instanceof TemplateParseError) {
|
||||
return {
|
||||
status: "failed",
|
||||
error: `Invalid tempban_message format: ${err.message}`,
|
||||
};
|
||||
}
|
||||
throw err;
|
||||
}
|
||||
|
||||
notifyResult = await notifyUser(member.user, banMessage, contactMethods);
|
||||
} else {
|
||||
|
|
|
@ -2,10 +2,10 @@ import { Snowflake } from "discord.js";
|
|||
import humanizeDuration from "humanize-duration";
|
||||
import { GuildPluginData } from "knub";
|
||||
import moment from "moment-timezone";
|
||||
import { LogType } from "src/data/LogType";
|
||||
import { logger } from "src/logger";
|
||||
import { CaseTypes } from "../../../data/CaseTypes";
|
||||
import { LogType } from "../../../data/LogType";
|
||||
import { Tempban } from "../../../data/entities/Tempban";
|
||||
import { logger } from "../../../logger";
|
||||
import { resolveUser } from "../../../utils";
|
||||
import { CasesPlugin } from "../../Cases/CasesPlugin";
|
||||
import { LogsPlugin } from "../../Logs/LogsPlugin";
|
||||
|
|
|
@ -2,7 +2,7 @@ import { GuildMember } from "discord.js";
|
|||
import { GuildPluginData } from "knub";
|
||||
import { CaseTypes } from "../../../data/CaseTypes";
|
||||
import { LogType } from "../../../data/LogType";
|
||||
import { renderTemplate, TemplateSafeValueContainer } from "../../../templateFormatter";
|
||||
import { renderTemplate, TemplateParseError, TemplateSafeValueContainer } from "../../../templateFormatter";
|
||||
import { createUserNotificationError, notifyUser, resolveUser, ucfirst, UserNotificationResult } from "../../../utils";
|
||||
import { userToTemplateSafeUser } from "../../../utils/templateSafeObjects";
|
||||
import { CasesPlugin } from "../../Cases/CasesPlugin";
|
||||
|
@ -32,16 +32,27 @@ export async function kickMember(
|
|||
|
||||
if (contactMethods.length) {
|
||||
if (config.kick_message) {
|
||||
const kickMessage = await renderTemplate(
|
||||
config.kick_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: kickOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, kickOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
let kickMessage: string;
|
||||
try {
|
||||
kickMessage = await renderTemplate(
|
||||
config.kick_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: kickOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, kickOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
} catch (err) {
|
||||
if (err instanceof TemplateParseError) {
|
||||
return {
|
||||
status: "failed",
|
||||
error: `Invalid kick_message format: ${err.message}`,
|
||||
};
|
||||
}
|
||||
throw err;
|
||||
}
|
||||
|
||||
notifyResult = await notifyUser(member.user, kickMessage, contactMethods);
|
||||
} else {
|
||||
|
|
|
@ -2,7 +2,7 @@ import { GuildMember, Snowflake } from "discord.js";
|
|||
import { GuildPluginData } from "knub";
|
||||
import { CaseTypes } from "../../../data/CaseTypes";
|
||||
import { getContextChannel, isContextInteraction } from "../../../pluginUtils";
|
||||
import { TemplateSafeValueContainer, renderTemplate } from "../../../templateFormatter";
|
||||
import { TemplateParseError, TemplateSafeValueContainer, renderTemplate } from "../../../templateFormatter";
|
||||
import { UserNotificationResult, createUserNotificationError, notifyUser, resolveUser, ucfirst } from "../../../utils";
|
||||
import { userToTemplateSafeUser } from "../../../utils/templateSafeObjects";
|
||||
import { waitForButtonConfirm } from "../../../utils/waitForInteraction";
|
||||
|
@ -22,16 +22,27 @@ export async function warnMember(
|
|||
|
||||
let notifyResult: UserNotificationResult;
|
||||
if (config.warn_message) {
|
||||
const warnMessage = await renderTemplate(
|
||||
config.warn_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: warnOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, warnOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
let warnMessage: string;
|
||||
try {
|
||||
warnMessage = await renderTemplate(
|
||||
config.warn_message,
|
||||
new TemplateSafeValueContainer({
|
||||
guildName: pluginData.guild.name,
|
||||
reason: reasonWithAttachments,
|
||||
moderator: warnOptions.caseArgs?.modId
|
||||
? userToTemplateSafeUser(await resolveUser(pluginData.client, warnOptions.caseArgs.modId))
|
||||
: null,
|
||||
}),
|
||||
);
|
||||
} catch (err) {
|
||||
if (err instanceof TemplateParseError) {
|
||||
return {
|
||||
status: "failed",
|
||||
error: `Invalid warn_message format: ${err.message}`,
|
||||
};
|
||||
}
|
||||
throw err;
|
||||
}
|
||||
const contactMethods = warnOptions?.contactMethods
|
||||
? warnOptions.contactMethods
|
||||
: getDefaultContactMethods(pluginData, "warn");
|
||||
|
|
|
@ -1,55 +1,54 @@
|
|||
import { ChatInputCommandInteraction, Message } from "discord.js";
|
||||
import { EventEmitter } from "events";
|
||||
import * as t from "io-ts";
|
||||
import { BasePluginType, guildPluginEventListener, guildPluginMessageCommand, guildPluginSlashGroup } from "knub";
|
||||
import z from "zod";
|
||||
import { Queue } from "../../Queue";
|
||||
import { GuildCases } from "../../data/GuildCases";
|
||||
import { GuildLogs } from "../../data/GuildLogs";
|
||||
import { GuildMutes } from "../../data/GuildMutes";
|
||||
import { GuildTempbans } from "../../data/GuildTempbans";
|
||||
import { Case } from "../../data/entities/Case";
|
||||
import { UserNotificationMethod, UserNotificationResult, tNullable } from "../../utils";
|
||||
import { UserNotificationMethod, UserNotificationResult } from "../../utils";
|
||||
import { CaseArgs } from "../Cases/types";
|
||||
|
||||
export type AttachmentLinkReactionType = "none" | "warn" | "restrict" | null | undefined;
|
||||
export type AttachmentLinkReactionType = "none" | "warn" | "restrict" | null;
|
||||
|
||||
export const ConfigSchema = t.type({
|
||||
dm_on_warn: t.boolean,
|
||||
dm_on_kick: t.boolean,
|
||||
dm_on_ban: t.boolean,
|
||||
message_on_warn: t.boolean,
|
||||
message_on_kick: t.boolean,
|
||||
message_on_ban: t.boolean,
|
||||
message_channel: tNullable(t.string),
|
||||
warn_message: tNullable(t.string),
|
||||
kick_message: tNullable(t.string),
|
||||
ban_message: tNullable(t.string),
|
||||
tempban_message: tNullable(t.string),
|
||||
alert_on_rejoin: t.boolean,
|
||||
alert_channel: tNullable(t.string),
|
||||
warn_notify_enabled: t.boolean,
|
||||
warn_notify_threshold: t.number,
|
||||
warn_notify_message: t.string,
|
||||
ban_delete_message_days: t.number,
|
||||
attachment_link_reaction: tNullable(t.union([t.literal("none"), t.literal("warn"), t.literal("restrict")])),
|
||||
attachment_storing_channel: tNullable(t.string),
|
||||
can_note: t.boolean,
|
||||
can_warn: t.boolean,
|
||||
can_mute: t.boolean,
|
||||
can_kick: t.boolean,
|
||||
can_ban: t.boolean,
|
||||
can_unban: t.boolean,
|
||||
can_view: t.boolean,
|
||||
can_addcase: t.boolean,
|
||||
can_massunban: t.boolean,
|
||||
can_massban: t.boolean,
|
||||
can_massmute: t.boolean,
|
||||
can_hidecase: t.boolean,
|
||||
can_deletecase: t.boolean,
|
||||
can_act_as_other: t.boolean,
|
||||
create_cases_for_manual_actions: t.boolean,
|
||||
export const zModActionsConfig = z.strictObject({
|
||||
dm_on_warn: z.boolean(),
|
||||
dm_on_kick: z.boolean(),
|
||||
dm_on_ban: z.boolean(),
|
||||
message_on_warn: z.boolean(),
|
||||
message_on_kick: z.boolean(),
|
||||
message_on_ban: z.boolean(),
|
||||
message_channel: z.nullable(z.string()),
|
||||
warn_message: z.nullable(z.string()),
|
||||
kick_message: z.nullable(z.string()),
|
||||
ban_message: z.nullable(z.string()),
|
||||
tempban_message: z.nullable(z.string()),
|
||||
alert_on_rejoin: z.boolean(),
|
||||
alert_channel: z.nullable(z.string()),
|
||||
warn_notify_enabled: z.boolean(),
|
||||
warn_notify_threshold: z.number(),
|
||||
warn_notify_message: z.string(),
|
||||
ban_delete_message_days: z.number(),
|
||||
attachment_link_reaction: z.nullable(z.union([z.literal("none"), z.literal("warn"), z.literal("restrict")])),
|
||||
attachment_storing_channel: z.nullable(z.string()),
|
||||
can_note: z.boolean(),
|
||||
can_warn: z.boolean(),
|
||||
can_mute: z.boolean(),
|
||||
can_kick: z.boolean(),
|
||||
can_ban: z.boolean(),
|
||||
can_unban: z.boolean(),
|
||||
can_view: z.boolean(),
|
||||
can_addcase: z.boolean(),
|
||||
can_massunban: z.boolean(),
|
||||
can_massban: z.boolean(),
|
||||
can_massmute: z.boolean(),
|
||||
can_hidecase: z.boolean(),
|
||||
can_deletecase: z.boolean(),
|
||||
can_act_as_other: z.boolean(),
|
||||
create_cases_for_manual_actions: z.boolean(),
|
||||
});
|
||||
export type TConfigSchema = t.TypeOf<typeof ConfigSchema>;
|
||||
|
||||
export interface ModActionsEvents {
|
||||
note: (userId: string, reason?: string) => void;
|
||||
|
@ -66,7 +65,7 @@ export interface ModActionsEventEmitter extends EventEmitter {
|
|||
}
|
||||
|
||||
export interface ModActionsPluginType extends BasePluginType {
|
||||
config: TConfigSchema;
|
||||
config: z.infer<typeof zModActionsConfig>;
|
||||
state: {
|
||||
mutes: GuildMutes;
|
||||
cases: GuildCases;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue