mirror of
https://github.com/ZeppelinBot/Zeppelin.git
synced 2025-05-10 12:25:02 +00:00
Run user-supplied regexes in worker threads with a timeout
This commit is contained in:
parent
19b97bc32b
commit
a7fa258f2a
15 changed files with 237 additions and 43 deletions
|
@ -6,6 +6,8 @@ import { GuildSavedMessages } from "src/data/GuildSavedMessages";
|
|||
import { onMessageCreate } from "./util/onMessageCreate";
|
||||
import { onMessageUpdate } from "./util/onMessageUpdate";
|
||||
import { trimPluginDescription } from "../../utils";
|
||||
import { discardRegExpRunner, getRegExpRunner } from "../../regExpRunners";
|
||||
import { LogsPlugin } from "../Logs/LogsPlugin";
|
||||
|
||||
const defaultOptions: PluginOptions<CensorPluginType> = {
|
||||
config: {
|
||||
|
@ -51,6 +53,7 @@ export const CensorPlugin = zeppelinPlugin<CensorPluginType>()("censor", {
|
|||
`),
|
||||
},
|
||||
|
||||
dependencies: [LogsPlugin],
|
||||
configSchema: ConfigSchema,
|
||||
defaultOptions,
|
||||
|
||||
|
@ -60,6 +63,8 @@ export const CensorPlugin = zeppelinPlugin<CensorPluginType>()("censor", {
|
|||
state.serverLogs = new GuildLogs(guild.id);
|
||||
state.savedMessages = GuildSavedMessages.getGuildInstance(guild.id);
|
||||
|
||||
state.regexRunner = getRegExpRunner(`guild-${pluginData.guild.id}`);
|
||||
|
||||
state.onMessageCreateFn = msg => onMessageCreate(pluginData, msg);
|
||||
state.savedMessages.events.on("create", state.onMessageCreateFn);
|
||||
|
||||
|
@ -68,6 +73,8 @@ export const CensorPlugin = zeppelinPlugin<CensorPluginType>()("censor", {
|
|||
},
|
||||
|
||||
onUnload(pluginData) {
|
||||
discardRegExpRunner(`guild-${pluginData.guild.id}`);
|
||||
|
||||
pluginData.state.savedMessages.events.off("create", pluginData.state.onMessageCreateFn);
|
||||
pluginData.state.savedMessages.events.off("update", pluginData.state.onMessageUpdateFn);
|
||||
},
|
||||
|
|
|
@ -1,9 +1,10 @@
|
|||
import * as t from "io-ts";
|
||||
import { BasePluginType, eventListener } from "knub";
|
||||
import { tNullable } from "src/utils";
|
||||
import { TSafeRegex } from "src/validatorUtils";
|
||||
import { TRegex } from "src/validatorUtils";
|
||||
import { GuildLogs } from "src/data/GuildLogs";
|
||||
import { GuildSavedMessages } from "src/data/GuildSavedMessages";
|
||||
import { RegExpRunner } from "../../RegExpRunner";
|
||||
|
||||
export const ConfigSchema = t.type({
|
||||
filter_zalgo: t.boolean,
|
||||
|
@ -18,7 +19,7 @@ export const ConfigSchema = t.type({
|
|||
domain_blacklist: tNullable(t.array(t.string)),
|
||||
blocked_tokens: tNullable(t.array(t.string)),
|
||||
blocked_words: tNullable(t.array(t.string)),
|
||||
blocked_regex: tNullable(t.array(TSafeRegex)),
|
||||
blocked_regex: tNullable(t.array(TRegex)),
|
||||
});
|
||||
export type TConfigSchema = t.TypeOf<typeof ConfigSchema>;
|
||||
|
||||
|
@ -28,6 +29,8 @@ export interface CensorPluginType extends BasePluginType {
|
|||
serverLogs: GuildLogs;
|
||||
savedMessages: GuildSavedMessages;
|
||||
|
||||
regexRunner: RegExpRunner;
|
||||
|
||||
onMessageCreateFn;
|
||||
onMessageUpdateFn;
|
||||
};
|
||||
|
|
|
@ -8,6 +8,7 @@ import cloneDeep from "lodash.clonedeep";
|
|||
import { censorMessage } from "./censorMessage";
|
||||
import escapeStringRegexp from "escape-string-regexp";
|
||||
import { logger } from "src/logger";
|
||||
import { allowTimeout } from "../../../RegExpRunner";
|
||||
|
||||
export async function applyFiltersToMsg(
|
||||
pluginData: PluginData<CensorPluginType>,
|
||||
|
@ -137,17 +138,13 @@ export async function applyFiltersToMsg(
|
|||
}
|
||||
|
||||
// Filter regex
|
||||
const blockedRegex: RegExp[] = config.blocked_regex || [];
|
||||
for (const [i, regex] of blockedRegex.entries()) {
|
||||
if (typeof regex.test !== "function") {
|
||||
logger.info(
|
||||
`[DEBUG] Regex <${regex}> was not a regex; index ${i} of censor.blocked_regex for guild ${pluginData.guild.name} (${pluginData.guild.id})`,
|
||||
);
|
||||
continue;
|
||||
}
|
||||
|
||||
for (const regex of config.blocked_regex || []) {
|
||||
// We're testing both the original content and content + attachments/embeds here so regexes that use ^ and $ still match the regular content properly
|
||||
if (regex.test(savedMessage.data.content) || regex.test(messageContent)) {
|
||||
const matches =
|
||||
(await pluginData.state.regexRunner.exec(regex, savedMessage.data.content).catch(allowTimeout)) ||
|
||||
(await pluginData.state.regexRunner.exec(regex, messageContent).catch(allowTimeout));
|
||||
|
||||
if (matches) {
|
||||
censorMessage(pluginData, savedMessage, `blocked regex (\`${regex.source}\`) found`);
|
||||
return true;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue