mirror of
https://github.com/matrix-org/mjolnir.git
synced 2024-09-29 20:56:23 +00:00
move LogProxy.logMessage to Mjolnir.logMessage (#194)
This commit is contained in:
parent
e9dff8fd5a
commit
a58c7d3f1a
@ -1,55 +0,0 @@
|
||||
/*
|
||||
Copyright 2019, 2020 The Matrix.org Foundation C.I.C.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
*/
|
||||
|
||||
import { LogLevel, LogService, TextualMessageEventContent } from "matrix-bot-sdk";
|
||||
import config from "./config";
|
||||
import { htmlEscape, replaceRoomIdsWithPills } from "./utils";
|
||||
|
||||
const levelToFn = {
|
||||
[LogLevel.DEBUG.toString()]: LogService.debug,
|
||||
[LogLevel.INFO.toString()]: LogService.info,
|
||||
[LogLevel.WARN.toString()]: LogService.warn,
|
||||
[LogLevel.ERROR.toString()]: LogService.error,
|
||||
};
|
||||
|
||||
export async function logMessage(level: LogLevel, module: string, message: string | any, additionalRoomIds: string[] | string | null = null, isRecursive = false) {
|
||||
if (!additionalRoomIds) additionalRoomIds = [];
|
||||
if (!Array.isArray(additionalRoomIds)) additionalRoomIds = [additionalRoomIds];
|
||||
|
||||
if (config.RUNTIME.client && (config.verboseLogging || LogLevel.INFO.includes(level))) {
|
||||
let clientMessage = message;
|
||||
if (level === LogLevel.WARN) clientMessage = `⚠ | ${message}`;
|
||||
if (level === LogLevel.ERROR) clientMessage = `‼ | ${message}`;
|
||||
|
||||
const client = config.RUNTIME.client;
|
||||
const managementRoomId = await client.resolveRoom(config.managementRoom);
|
||||
const roomIds = new Set([managementRoomId, ...additionalRoomIds]);
|
||||
|
||||
let evContent: TextualMessageEventContent = {
|
||||
body: message,
|
||||
formatted_body: htmlEscape(message),
|
||||
msgtype: "m.notice",
|
||||
format: "org.matrix.custom.html",
|
||||
};
|
||||
if (!isRecursive) {
|
||||
evContent = await replaceRoomIdsWithPills(client, clientMessage, roomIds, "m.notice");
|
||||
}
|
||||
|
||||
await client.sendMessage(managementRoomId, evContent);
|
||||
}
|
||||
|
||||
levelToFn[level.toString()](module, message);
|
||||
}
|
@ -23,7 +23,8 @@ import {
|
||||
MatrixGlob,
|
||||
MembershipEvent,
|
||||
Permalinks,
|
||||
UserID
|
||||
UserID,
|
||||
TextualMessageEventContent
|
||||
} from "matrix-bot-sdk";
|
||||
|
||||
import BanList, { ALL_RULE_TYPES as ALL_BAN_LIST_RULE_TYPES, ListRuleChange, RULE_ROOM, RULE_SERVER, RULE_USER } from "./models/BanList";
|
||||
@ -32,7 +33,6 @@ import { RoomUpdateError } from "./models/RoomUpdateError";
|
||||
import { COMMAND_PREFIX, handleCommand } from "./commands/CommandHandler";
|
||||
import { applyUserBans } from "./actions/ApplyBan";
|
||||
import config from "./config";
|
||||
import { logMessage } from "./LogProxy";
|
||||
import ErrorCache, { ERROR_KIND_FATAL, ERROR_KIND_PERMISSION } from "./ErrorCache";
|
||||
import { IProtection } from "./protections/IProtection";
|
||||
import { PROTECTIONS } from "./protections/protections";
|
||||
@ -43,8 +43,16 @@ import { EventRedactionQueue, RedactUserInRoom } from "./queues/EventRedactionQu
|
||||
import { htmlEscape } from "./utils";
|
||||
import { ReportManager } from "./report/ReportManager";
|
||||
import { WebAPIs } from "./webapis/WebAPIs";
|
||||
import { replaceRoomIdsWithPills } from "./utils";
|
||||
import RuleServer from "./models/RuleServer";
|
||||
|
||||
const levelToFn = {
|
||||
[LogLevel.DEBUG.toString()]: LogService.debug,
|
||||
[LogLevel.INFO.toString()]: LogService.info,
|
||||
[LogLevel.WARN.toString()]: LogService.warn,
|
||||
[LogLevel.ERROR.toString()]: LogService.error,
|
||||
};
|
||||
|
||||
export const STATE_NOT_STARTED = "not_started";
|
||||
export const STATE_CHECKING_PERMISSIONS = "checking_permissions";
|
||||
export const STATE_SYNCING = "syncing";
|
||||
@ -144,10 +152,10 @@ export class Mjolnir {
|
||||
if (!joinedRooms.includes(managementRoomId)) {
|
||||
await client.joinRoom(config.managementRoom);
|
||||
}
|
||||
await logMessage(LogLevel.INFO, "index", "Mjolnir is starting up. Use !mjolnir to query status.");
|
||||
|
||||
const ruleServer = config.web.ruleServer ? new RuleServer() : null;
|
||||
const mjolnir = new Mjolnir(client, managementRoomId, protectedRooms, banLists, ruleServer);
|
||||
await mjolnir.logMessage(LogLevel.INFO, "index", "Mjolnir is starting up. Use !mjolnir to query status.");
|
||||
Mjolnir.addJoinOnInviteListener(mjolnir, client, config);
|
||||
return mjolnir;
|
||||
}
|
||||
@ -270,7 +278,7 @@ export class Mjolnir {
|
||||
// Load the state.
|
||||
this.currentState = STATE_CHECKING_PERMISSIONS;
|
||||
|
||||
await logMessage(LogLevel.DEBUG, "Mjolnir@startup", "Loading protected rooms...");
|
||||
await this.logMessage(LogLevel.DEBUG, "Mjolnir@startup", "Loading protected rooms...");
|
||||
await this.resyncJoinedRooms(false);
|
||||
try {
|
||||
const data: { rooms?: string[] } | null = await this.client.getAccountData(PROTECTED_ROOMS_EVENT_TYPE);
|
||||
@ -287,25 +295,25 @@ export class Mjolnir {
|
||||
this.applyUnprotectedRooms();
|
||||
|
||||
if (config.verifyPermissionsOnStartup) {
|
||||
await logMessage(LogLevel.INFO, "Mjolnir@startup", "Checking permissions...");
|
||||
await this.logMessage(LogLevel.INFO, "Mjolnir@startup", "Checking permissions...");
|
||||
await this.verifyPermissions(config.verboseLogging);
|
||||
}
|
||||
|
||||
this.currentState = STATE_SYNCING;
|
||||
if (config.syncOnStartup) {
|
||||
await logMessage(LogLevel.INFO, "Mjolnir@startup", "Syncing lists...");
|
||||
await this.logMessage(LogLevel.INFO, "Mjolnir@startup", "Syncing lists...");
|
||||
await this.syncLists(config.verboseLogging);
|
||||
await this.registerProtections();
|
||||
}
|
||||
|
||||
this.currentState = STATE_RUNNING;
|
||||
Healthz.isHealthy = true;
|
||||
await logMessage(LogLevel.INFO, "Mjolnir@startup", "Startup complete. Now monitoring rooms.");
|
||||
await this.logMessage(LogLevel.INFO, "Mjolnir@startup", "Startup complete. Now monitoring rooms.");
|
||||
} catch (err) {
|
||||
try {
|
||||
LogService.error("Mjolnir", "Error during startup:");
|
||||
LogService.error("Mjolnir", extractRequestError(err));
|
||||
await logMessage(LogLevel.ERROR, "Mjolnir@startup", "Startup failed due to error - see console");
|
||||
await this.logMessage(LogLevel.ERROR, "Mjolnir@startup", "Startup failed due to error - see console");
|
||||
} catch (e) {
|
||||
// If we failed to handle the error, just crash
|
||||
console.error(e);
|
||||
@ -323,6 +331,36 @@ export class Mjolnir {
|
||||
this.webapis.stop();
|
||||
}
|
||||
|
||||
public async logMessage(level: LogLevel, module: string, message: string | any, additionalRoomIds: string[] | string | null = null, isRecursive = false): Promise<any> {
|
||||
if (!additionalRoomIds) additionalRoomIds = [];
|
||||
if (!Array.isArray(additionalRoomIds)) additionalRoomIds = [additionalRoomIds];
|
||||
|
||||
if (config.RUNTIME.client && (config.verboseLogging || LogLevel.INFO.includes(level))) {
|
||||
let clientMessage = message;
|
||||
if (level === LogLevel.WARN) clientMessage = `⚠ | ${message}`;
|
||||
if (level === LogLevel.ERROR) clientMessage = `‼ | ${message}`;
|
||||
|
||||
const client = config.RUNTIME.client;
|
||||
const managementRoomId = await client.resolveRoom(config.managementRoom);
|
||||
const roomIds = [managementRoomId, ...additionalRoomIds];
|
||||
|
||||
let evContent: TextualMessageEventContent = {
|
||||
body: message,
|
||||
formatted_body: htmlEscape(message),
|
||||
msgtype: "m.notice",
|
||||
format: "org.matrix.custom.html",
|
||||
};
|
||||
if (!isRecursive) {
|
||||
evContent = await replaceRoomIdsWithPills(this, clientMessage, new Set(roomIds), "m.notice");
|
||||
}
|
||||
|
||||
await client.sendMessage(managementRoomId, evContent);
|
||||
}
|
||||
|
||||
levelToFn[level.toString()](module, message);
|
||||
}
|
||||
|
||||
|
||||
public async addProtectedRoom(roomId: string) {
|
||||
this.protectedRooms[roomId] = Permalinks.forRoom(roomId);
|
||||
|
||||
@ -455,7 +493,7 @@ export class Mjolnir {
|
||||
) {
|
||||
validatedSettings[key] = value;
|
||||
} else {
|
||||
await logMessage(
|
||||
await this.logMessage(
|
||||
LogLevel.WARN,
|
||||
"getProtectionSetting",
|
||||
`Tried to read ${protectionName}.${key} and got invalid value ${value}`
|
||||
@ -606,7 +644,7 @@ export class Mjolnir {
|
||||
// Ignore - probably haven't warned about it yet
|
||||
}
|
||||
|
||||
await logMessage(LogLevel.WARN, "Mjolnir", `Not protecting ${roomId} - it is a ban list that this bot did not create. Add the room as protected if it is supposed to be protected. This warning will not appear again.`, roomId);
|
||||
await this.logMessage(LogLevel.WARN, "Mjolnir", `Not protecting ${roomId} - it is a ban list that this bot did not create. Add the room as protected if it is supposed to be protected. This warning will not appear again.`, roomId);
|
||||
await this.client.setAccountData(WARN_UNPROTECTED_ROOM_EVENT_PREFIX + roomId, { warned: true });
|
||||
}
|
||||
|
||||
@ -834,16 +872,16 @@ export class Mjolnir {
|
||||
|
||||
// Run the event handlers - we always run this after protections so that the protections
|
||||
// can flag the event for redaction.
|
||||
await this.unlistedUserRedactionHandler.handleEvent(roomId, event, this.client);
|
||||
await this.unlistedUserRedactionHandler.handleEvent(roomId, event, this);
|
||||
|
||||
if (event['type'] === 'm.room.power_levels' && event['state_key'] === '') {
|
||||
// power levels were updated - recheck permissions
|
||||
ErrorCache.resetError(roomId, ERROR_KIND_PERMISSION);
|
||||
await logMessage(LogLevel.DEBUG, "Mjolnir", `Power levels changed in ${roomId} - checking permissions...`, roomId);
|
||||
await this.logMessage(LogLevel.DEBUG, "Mjolnir", `Power levels changed in ${roomId} - checking permissions...`, roomId);
|
||||
const errors = await this.verifyPermissionsIn(roomId);
|
||||
const hadErrors = await this.printActionResult(errors);
|
||||
if (!hadErrors) {
|
||||
await logMessage(LogLevel.DEBUG, "Mjolnir", `All permissions look OK.`);
|
||||
await this.logMessage(LogLevel.DEBUG, "Mjolnir", `All permissions look OK.`);
|
||||
}
|
||||
return;
|
||||
} else if (event['type'] === "m.room.member") {
|
||||
@ -982,7 +1020,7 @@ export class Mjolnir {
|
||||
* @returns The list of errors encountered, for reporting to the management room.
|
||||
*/
|
||||
public async processRedactionQueue(roomId?: string): Promise<RoomUpdateError[]> {
|
||||
return await this.eventRedactionQueue.process(this.client, roomId);
|
||||
return await this.eventRedactionQueue.process(this, roomId);
|
||||
}
|
||||
|
||||
private async handleReport(roomId: string, reporterId: string, event: any, reason?: string) {
|
||||
|
@ -20,7 +20,6 @@ import { RoomUpdateError } from "../models/RoomUpdateError";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import config from "../config";
|
||||
import { LogLevel, UserID } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import { ERROR_KIND_FATAL, ERROR_KIND_PERMISSION } from "../ErrorCache";
|
||||
|
||||
/**
|
||||
@ -45,7 +44,7 @@ export async function applyServerAcls(lists: BanList[], roomIds: string[], mjoln
|
||||
const finalAcl = acl.safeAclContent();
|
||||
|
||||
if (finalAcl.deny.length !== acl.literalAclContent().deny.length) {
|
||||
logMessage(LogLevel.WARN, "ApplyAcl", `Mjölnir has detected and removed an ACL that would exclude itself. Please check the ACL lists.`);
|
||||
mjolnir.logMessage(LogLevel.WARN, "ApplyAcl", `Mjölnir has detected and removed an ACL that would exclude itself. Please check the ACL lists.`);
|
||||
}
|
||||
|
||||
if (config.verboseLogging) {
|
||||
@ -56,12 +55,12 @@ export async function applyServerAcls(lists: BanList[], roomIds: string[], mjoln
|
||||
const errors: RoomUpdateError[] = [];
|
||||
for (const roomId of roomIds) {
|
||||
try {
|
||||
await logMessage(LogLevel.DEBUG, "ApplyAcl", `Checking ACLs for ${roomId}`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "ApplyAcl", `Checking ACLs for ${roomId}`, roomId);
|
||||
|
||||
try {
|
||||
const currentAcl = await mjolnir.client.getRoomStateEvent(roomId, "m.room.server_acl", "");
|
||||
if (acl.matches(currentAcl)) {
|
||||
await logMessage(LogLevel.DEBUG, "ApplyAcl", `Skipping ACLs for ${roomId} because they are already the right ones`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "ApplyAcl", `Skipping ACLs for ${roomId} because they are already the right ones`, roomId);
|
||||
continue;
|
||||
}
|
||||
} catch (e) {
|
||||
@ -69,12 +68,12 @@ export async function applyServerAcls(lists: BanList[], roomIds: string[], mjoln
|
||||
}
|
||||
|
||||
// We specifically use sendNotice to avoid having to escape HTML
|
||||
await logMessage(LogLevel.DEBUG, "ApplyAcl", `Applying ACL in ${roomId}`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "ApplyAcl", `Applying ACL in ${roomId}`, roomId);
|
||||
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.sendStateEvent(roomId, "m.room.server_acl", "", finalAcl);
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "ApplyAcl", `Tried to apply ACL in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "ApplyAcl", `Tried to apply ACL in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
} catch (e) {
|
||||
const message = e.message || (e.body ? e.body.error : '<no message>');
|
||||
|
@ -18,7 +18,6 @@ import BanList from "../models/BanList";
|
||||
import { RoomUpdateError } from "../models/RoomUpdateError";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import config from "../config";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import { LogLevel } from "matrix-bot-sdk";
|
||||
import { ERROR_KIND_FATAL, ERROR_KIND_PERMISSION } from "../ErrorCache";
|
||||
|
||||
@ -35,7 +34,7 @@ export async function applyUserBans(lists: BanList[], roomIds: string[], mjolnir
|
||||
for (const roomId of roomIds) {
|
||||
try {
|
||||
// We specifically use sendNotice to avoid having to escape HTML
|
||||
await logMessage(LogLevel.DEBUG, "ApplyBan", `Updating member bans in ${roomId}`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "ApplyBan", `Updating member bans in ${roomId}`, roomId);
|
||||
|
||||
let members: { userId: string, membership: string }[];
|
||||
|
||||
@ -63,7 +62,7 @@ export async function applyUserBans(lists: BanList[], roomIds: string[], mjolnir
|
||||
// User needs to be banned
|
||||
|
||||
// We specifically use sendNotice to avoid having to escape HTML
|
||||
await logMessage(LogLevel.INFO, "ApplyBan", `Banning ${member.userId} in ${roomId} for: ${userRule.reason}`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.INFO, "ApplyBan", `Banning ${member.userId} in ${roomId} for: ${userRule.reason}`, roomId);
|
||||
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.banUser(member.userId, roomId, userRule.reason);
|
||||
@ -71,7 +70,7 @@ export async function applyUserBans(lists: BanList[], roomIds: string[], mjolnir
|
||||
mjolnir.queueRedactUserMessagesIn(member.userId, roomId);
|
||||
}
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "ApplyBan", `Tried to ban ${member.userId} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "ApplyBan", `Tried to ban ${member.userId} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
|
||||
banned = true;
|
||||
|
@ -16,7 +16,6 @@ limitations under the License.
|
||||
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { extractRequestError, LogLevel, LogService } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
|
||||
// !mjolnir rooms add <room alias/ID>
|
||||
export async function execAddProtectedRoom(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {
|
||||
@ -33,7 +32,7 @@ export async function execRemoveProtectedRoom(roomId: string, event: any, mjolni
|
||||
await mjolnir.client.leaveRoom(protectedRoomId);
|
||||
} catch (e) {
|
||||
LogService.warn("AddRemoveProtectedRoomsCommand", extractRequestError(e));
|
||||
await logMessage(LogLevel.WARN, "AddRemoveProtectedRoomsCommand", `Failed to leave ${protectedRoomId} - the room is no longer being protected, but the bot could not leave`, protectedRoomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "AddRemoveProtectedRoomsCommand", `Failed to leave ${protectedRoomId} - the room is no longer being protected, but the bot could not leave`, protectedRoomId);
|
||||
}
|
||||
await mjolnir.client.unstableApis.addReactionToEvent(roomId, event['event_id'], '✅');
|
||||
}
|
||||
|
@ -17,7 +17,6 @@ limitations under the License.
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel } from "matrix-bot-sdk";
|
||||
import config from "../config";
|
||||
import { logMessage } from "../LogProxy";
|
||||
|
||||
// !mjolnir kick <user> [room] [reason]
|
||||
export async function execKickCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {
|
||||
@ -39,11 +38,11 @@ export async function execKickCommand(roomId: string, event: any, mjolnir: Mjoln
|
||||
const joinedUsers = await mjolnir.client.getJoinedRoomMembers(targetRoomId);
|
||||
if (!joinedUsers.includes(userId)) continue; // skip
|
||||
|
||||
await logMessage(LogLevel.INFO, "KickCommand", `Kicking ${userId} in ${targetRoomId} for ${reason}`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.INFO, "KickCommand", `Kicking ${userId} in ${targetRoomId} for ${reason}`, targetRoomId);
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.kickUser(userId, targetRoomId, reason);
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "KickCommand", `Tried to kick ${userId} in ${targetRoomId} but the bot is running in no-op mode.`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "KickCommand", `Tried to kick ${userId} in ${targetRoomId} but the bot is running in no-op mode.`, targetRoomId);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -46,7 +46,7 @@ export async function execRedactCommand(roomId: string, event: any, mjolnir: Mjo
|
||||
}
|
||||
|
||||
const targetRoomIds = roomAlias ? [roomAlias] : Object.keys(mjolnir.protectedRooms);
|
||||
await redactUserMessagesIn(mjolnir.client, userId, targetRoomIds, limit);
|
||||
await redactUserMessagesIn(mjolnir, userId, targetRoomIds, limit);
|
||||
|
||||
await mjolnir.client.unstableApis.addReactionToEvent(roomId, event['event_id'], '✅');
|
||||
await mjolnir.client.redactEvent(roomId, processingReactionId, 'done processing');
|
||||
|
@ -16,7 +16,6 @@ limitations under the License.
|
||||
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { extractRequestError, LogLevel, LogService } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
|
||||
// !mjolnir powerlevel <user ID> <level> [room]
|
||||
export async function execSetPowerLevelCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {
|
||||
@ -31,7 +30,7 @@ export async function execSetPowerLevelCommand(roomId: string, event: any, mjoln
|
||||
await mjolnir.client.setUserPowerLevel(victim, targetRoomId, level);
|
||||
} catch (e) {
|
||||
const message = e.message || (e.body ? e.body.error : '<no message>');
|
||||
await logMessage(LogLevel.ERROR, "SetPowerLevelCommand", `Failed to set power level of ${victim} to ${level} in ${targetRoomId}: ${message}`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.ERROR, "SetPowerLevelCommand", `Failed to set power level of ${victim} to ${level} in ${targetRoomId}: ${message}`, targetRoomId);
|
||||
LogService.error("SetPowerLevelCommand", extractRequestError(e));
|
||||
}
|
||||
}
|
||||
|
@ -19,7 +19,6 @@ import BanList, { RULE_ROOM, RULE_SERVER, RULE_USER, USER_RULE_TYPES } from "../
|
||||
import { extractRequestError, LogLevel, LogService, MatrixGlob, RichReply } from "matrix-bot-sdk";
|
||||
import { RECOMMENDATION_BAN, recommendationToStable } from "../models/ListRule";
|
||||
import config from "../config";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import { DEFAULT_LIST_EVENT_TYPE } from "./SetDefaultBanListCommand";
|
||||
|
||||
interface Arguments {
|
||||
@ -144,21 +143,21 @@ export async function execUnbanCommand(roomId: string, event: any, mjolnir: Mjol
|
||||
|
||||
if (USER_RULE_TYPES.includes(bits.ruleType!) && bits.reason === 'true') {
|
||||
const rule = new MatrixGlob(bits.entity);
|
||||
await logMessage(LogLevel.INFO, "UnbanBanCommand", "Unbanning users that match glob: " + bits.entity);
|
||||
await mjolnir.logMessage(LogLevel.INFO, "UnbanBanCommand", "Unbanning users that match glob: " + bits.entity);
|
||||
let unbannedSomeone = false;
|
||||
for (const protectedRoomId of Object.keys(mjolnir.protectedRooms)) {
|
||||
const members = await mjolnir.client.getRoomMembers(protectedRoomId, undefined, ['ban'], undefined);
|
||||
await logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Found ${members.length} banned user(s)`);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Found ${members.length} banned user(s)`);
|
||||
for (const member of members) {
|
||||
const victim = member.membershipFor;
|
||||
if (member.membership !== 'ban') continue;
|
||||
if (rule.test(victim)) {
|
||||
await logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Unbanning ${victim} in ${protectedRoomId}`, protectedRoomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Unbanning ${victim} in ${protectedRoomId}`, protectedRoomId);
|
||||
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.unbanUser(victim, protectedRoomId);
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "UnbanBanCommand", `Attempted to unban ${victim} in ${protectedRoomId} but Mjolnir is running in no-op mode`, protectedRoomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "UnbanBanCommand", `Attempted to unban ${victim} in ${protectedRoomId} but Mjolnir is running in no-op mode`, protectedRoomId);
|
||||
}
|
||||
|
||||
unbannedSomeone = true;
|
||||
@ -167,7 +166,7 @@ export async function execUnbanCommand(roomId: string, event: any, mjolnir: Mjol
|
||||
}
|
||||
|
||||
if (unbannedSomeone) {
|
||||
await logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Syncing lists to ensure no users were accidentally unbanned`);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "UnbanBanCommand", `Syncing lists to ensure no users were accidentally unbanned`);
|
||||
await mjolnir.syncLists(config.verboseLogging);
|
||||
}
|
||||
}
|
||||
|
12
src/index.ts
12
src/index.ts
@ -24,7 +24,6 @@ import {
|
||||
SimpleFsStorageProvider
|
||||
} from "matrix-bot-sdk";
|
||||
import config from "./config";
|
||||
import { logMessage } from "./LogProxy";
|
||||
import { Healthz } from "./health/healthz";
|
||||
import { Mjolnir } from "./Mjolnir";
|
||||
import { patchMatrixClient } from "./utils";
|
||||
@ -42,6 +41,8 @@ if (config.health.healthz.enabled) {
|
||||
}
|
||||
|
||||
(async function () {
|
||||
let bot: Mjolnir | null = null;
|
||||
try {
|
||||
const storagePath = path.isAbsolute(config.dataPath) ? config.dataPath : path.join(__dirname, '../', config.dataPath);
|
||||
const storage = new SimpleFsStorageProvider(path.join(storagePath, "bot.json"));
|
||||
|
||||
@ -55,9 +56,10 @@ if (config.health.healthz.enabled) {
|
||||
patchMatrixClient();
|
||||
config.RUNTIME.client = client;
|
||||
|
||||
let bot = await Mjolnir.setupMjolnirFromConfig(client);
|
||||
bot = await Mjolnir.setupMjolnirFromConfig(client);
|
||||
await bot.start();
|
||||
})().catch(err => {
|
||||
logMessage(LogLevel.ERROR, "index", err);
|
||||
} catch (err) {
|
||||
bot?.logMessage(LogLevel.ERROR, "index", err);
|
||||
process.exit(1);
|
||||
});
|
||||
}
|
||||
})();
|
||||
|
@ -18,7 +18,6 @@ import { Protection } from "./IProtection";
|
||||
import { NumberProtectionSetting } from "./ProtectionSettings";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel, LogService } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import config from "../config";
|
||||
|
||||
// if this is exceeded, we'll ban the user for spam and redact their messages
|
||||
@ -64,11 +63,11 @@ export class BasicFlooding extends Protection {
|
||||
}
|
||||
|
||||
if (messageCount >= this.settings.maxPerMinute.value) {
|
||||
await logMessage(LogLevel.WARN, "BasicFlooding", `Banning ${event['sender']} in ${roomId} for flooding (${messageCount} messages in the last minute)`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "BasicFlooding", `Banning ${event['sender']} in ${roomId} for flooding (${messageCount} messages in the last minute)`, roomId);
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.banUser(event['sender'], roomId, "spam");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "BasicFlooding", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "BasicFlooding", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
|
||||
if (this.recentlyBanned.includes(event['sender'])) return; // already handled (will be redacted)
|
||||
@ -81,7 +80,7 @@ export class BasicFlooding extends Protection {
|
||||
await mjolnir.client.redactEvent(roomId, eventId, "spam");
|
||||
}
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "BasicFlooding", `Tried to redact messages for ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "BasicFlooding", `Tried to redact messages for ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
|
||||
// Free up some memory now that we're ready to handle it elsewhere
|
||||
|
@ -17,7 +17,6 @@ limitations under the License.
|
||||
import { Protection } from "./IProtection";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel, LogService } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import config from "../config";
|
||||
import { isTrueJoinEvent } from "../utils";
|
||||
|
||||
@ -58,11 +57,11 @@ export class FirstMessageIsImage extends Protection {
|
||||
const formattedBody = content['formatted_body'] || '';
|
||||
const isMedia = msgtype === 'm.image' || msgtype === 'm.video' || formattedBody.toLowerCase().includes('<img');
|
||||
if (isMedia && this.justJoined[roomId].includes(event['sender'])) {
|
||||
await logMessage(LogLevel.WARN, "FirstMessageIsImage", `Banning ${event['sender']} for posting an image as the first thing after joining in ${roomId}.`);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "FirstMessageIsImage", `Banning ${event['sender']} for posting an image as the first thing after joining in ${roomId}.`);
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.banUser(event['sender'], roomId, "spam");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "FirstMessageIsImage", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "FirstMessageIsImage", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
|
||||
if (this.recentlyBanned.includes(event['sender'])) return; // already handled (will be redacted)
|
||||
@ -73,7 +72,7 @@ export class FirstMessageIsImage extends Protection {
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.redactEvent(roomId, event['event_id'], "spam");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "FirstMessageIsImage", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "FirstMessageIsImage", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,7 +17,6 @@ limitations under the License.
|
||||
import { Protection } from "./IProtection";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel, Permalinks, UserID } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import config from "../config";
|
||||
|
||||
export class MessageIsMedia extends Protection {
|
||||
@ -42,12 +41,12 @@ export class MessageIsMedia extends Protection {
|
||||
const formattedBody = content['formatted_body'] || '';
|
||||
const isMedia = msgtype === 'm.image' || msgtype === 'm.video' || formattedBody.toLowerCase().includes('<img');
|
||||
if (isMedia) {
|
||||
await logMessage(LogLevel.WARN, "MessageIsMedia", `Redacting event from ${event['sender']} for posting an image/video. ${Permalinks.forEvent(roomId, event['event_id'], [new UserID(await mjolnir.client.getUserId()).domain])}`);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "MessageIsMedia", `Redacting event from ${event['sender']} for posting an image/video. ${Permalinks.forEvent(roomId, event['event_id'], [new UserID(await mjolnir.client.getUserId()).domain])}`);
|
||||
// Redact the event
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.redactEvent(roomId, event['event_id'], "Images/videos are not permitted here");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "MessageIsMedia", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "MessageIsMedia", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,7 +17,6 @@ limitations under the License.
|
||||
import { Protection } from "./IProtection";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel, Permalinks, UserID } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import config from "../config";
|
||||
|
||||
export class MessageIsVoice extends Protection {
|
||||
@ -39,12 +38,12 @@ export class MessageIsVoice extends Protection {
|
||||
if (event['type'] === 'm.room.message' && event['content']) {
|
||||
if (event['content']['msgtype'] !== 'm.audio') return;
|
||||
if (event['content']['org.matrix.msc3245.voice'] === undefined) return;
|
||||
await logMessage(LogLevel.INFO, "MessageIsVoice", `Redacting event from ${event['sender']} for posting a voice message. ${Permalinks.forEvent(roomId, event['event_id'], [new UserID(await mjolnir.client.getUserId()).domain])}`);
|
||||
await mjolnir.logMessage(LogLevel.INFO, "MessageIsVoice", `Redacting event from ${event['sender']} for posting a voice message. ${Permalinks.forEvent(roomId, event['event_id'], [new UserID(await mjolnir.client.getUserId()).domain])}`);
|
||||
// Redact the event
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.redactEvent(roomId, event['event_id'], "Voice messages are not permitted here");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "MessageIsVoice", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "MessageIsVoice", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,7 +17,6 @@ limitations under the License.
|
||||
import { Protection } from "./IProtection";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
import { LogLevel, LogService } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import config from "../config";
|
||||
import { isTrueJoinEvent } from "../utils";
|
||||
|
||||
@ -94,18 +93,18 @@ export class WordList extends Protection {
|
||||
|
||||
// Perform the test
|
||||
if (message && this.badWords.test(message)) {
|
||||
await logMessage(LogLevel.WARN, "WordList", `Banning ${event['sender']} for word list violation in ${roomId}.`);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "WordList", `Banning ${event['sender']} for word list violation in ${roomId}.`);
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.banUser(event['sender'], roomId, "Word list violation");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "WordList", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "WordList", `Tried to ban ${event['sender']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
|
||||
// Redact the event
|
||||
if (!config.noop) {
|
||||
await mjolnir.client.redactEvent(roomId, event['event_id'], "spam");
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "WordList", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "WordList", `Tried to redact ${event['event_id']} in ${roomId} but Mjolnir is running in no-op mode`, roomId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -13,11 +13,11 @@ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
*/
|
||||
import { LogLevel, MatrixClient } from "matrix-bot-sdk"
|
||||
import { LogLevel } from "matrix-bot-sdk"
|
||||
import { ERROR_KIND_FATAL } from "../ErrorCache";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import { RoomUpdateError } from "../models/RoomUpdateError";
|
||||
import { redactUserMessagesIn } from "../utils";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
|
||||
export interface QueuedRedaction {
|
||||
/** The room which the redaction will take place in. */
|
||||
@ -27,7 +27,7 @@ export interface QueuedRedaction {
|
||||
* Called by the EventRedactionQueue.
|
||||
* @param client A MatrixClient to use to carry out the redaction.
|
||||
*/
|
||||
redact(client: MatrixClient): Promise<void>
|
||||
redact(mjolnir: Mjolnir): Promise<void>
|
||||
/**
|
||||
* Used to test whether the redaction is the equivalent to another redaction.
|
||||
* @param redaction Another QueuedRedaction to test if this redaction is an equivalent to.
|
||||
@ -47,9 +47,9 @@ export class RedactUserInRoom implements QueuedRedaction {
|
||||
this.roomId = roomId;
|
||||
}
|
||||
|
||||
public async redact(client: MatrixClient) {
|
||||
await logMessage(LogLevel.DEBUG, "Mjolnir", `Redacting events from ${this.userId} in room ${this.roomId}.`);
|
||||
await redactUserMessagesIn(client, this.userId, [this.roomId]);
|
||||
public async redact(mjolnir: Mjolnir) {
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "Mjolnir", `Redacting events from ${this.userId} in room ${this.roomId}.`);
|
||||
await redactUserMessagesIn(mjolnir, this.userId, [this.roomId]);
|
||||
}
|
||||
|
||||
public redactionEqual(redaction: QueuedRedaction): boolean {
|
||||
@ -107,12 +107,12 @@ export class EventRedactionQueue {
|
||||
* @param limitToRoomId If the roomId is provided, only redactions for that room will be processed.
|
||||
* @returns A description of any errors encountered by each QueuedRedaction that was processed.
|
||||
*/
|
||||
public async process(client: MatrixClient, limitToRoomId?: string): Promise<RoomUpdateError[]> {
|
||||
public async process(mjolnir: Mjolnir, limitToRoomId?: string): Promise<RoomUpdateError[]> {
|
||||
const errors: RoomUpdateError[] = [];
|
||||
const redact = async (currentBatch: QueuedRedaction[]) => {
|
||||
for (const redaction of currentBatch) {
|
||||
try {
|
||||
await redaction.redact(client);
|
||||
await redaction.redact(mjolnir);
|
||||
} catch (e) {
|
||||
let roomError: RoomUpdateError;
|
||||
if (e.roomId && e.errorMessage && e.errorKind) {
|
||||
|
@ -13,9 +13,9 @@ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
*/
|
||||
import { extractRequestError, LogLevel, LogService, MatrixClient, Permalinks } from "matrix-bot-sdk";
|
||||
import { logMessage } from "../LogProxy";
|
||||
import { extractRequestError, LogLevel, LogService, Permalinks } from "matrix-bot-sdk";
|
||||
import config from "../config";
|
||||
import { Mjolnir } from "../Mjolnir";
|
||||
|
||||
/**
|
||||
* A queue of users who have been flagged for redaction typically by the flooding or image protection.
|
||||
@ -38,18 +38,18 @@ export class UnlistedUserRedactionQueue {
|
||||
return this.usersToRedact.has(userId);
|
||||
}
|
||||
|
||||
public async handleEvent(roomId: string, event: any, mjolnirClient: MatrixClient) {
|
||||
public async handleEvent(roomId: string, event: any, mjolnir: Mjolnir) {
|
||||
if (this.isUserQueued(event['sender'])) {
|
||||
const permalink = Permalinks.forEvent(roomId, event['event_id']);
|
||||
try {
|
||||
LogService.info("AutomaticRedactionQueue", `Redacting event because the user is listed as bad: ${permalink}`)
|
||||
if (!config.noop) {
|
||||
await mjolnirClient.redactEvent(roomId, event['event_id']);
|
||||
await mjolnir.client.redactEvent(roomId, event['event_id']);
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "AutomaticRedactionQueue", `Tried to redact ${permalink} but Mjolnir is running in no-op mode`);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "AutomaticRedactionQueue", `Tried to redact ${permalink} but Mjolnir is running in no-op mode`);
|
||||
}
|
||||
} catch (e) {
|
||||
logMessage(LogLevel.WARN, "AutomaticRedactionQueue", `Unable to redact message: ${permalink}`);
|
||||
mjolnir.logMessage(LogLevel.WARN, "AutomaticRedactionQueue", `Unable to redact message: ${permalink}`);
|
||||
LogService.warn("AutomaticRedactionQueue", extractRequestError(e));
|
||||
}
|
||||
}
|
||||
|
22
src/utils.ts
22
src/utils.ts
@ -27,7 +27,7 @@ import {
|
||||
getRequestFn,
|
||||
setRequestFn,
|
||||
} from "matrix-bot-sdk";
|
||||
import { logMessage } from "./LogProxy";
|
||||
import { Mjolnir } from "./Mjolnir";
|
||||
import config from "./config";
|
||||
import { ClientRequest, IncomingMessage } from "http";
|
||||
|
||||
@ -59,17 +59,17 @@ export function isTrueJoinEvent(event: any): boolean {
|
||||
return membership === 'join' && prevMembership !== "join";
|
||||
}
|
||||
|
||||
export async function redactUserMessagesIn(client: MatrixClient, userIdOrGlob: string, targetRoomIds: string[], limit = 1000) {
|
||||
export async function redactUserMessagesIn(mjolnir: Mjolnir, userIdOrGlob: string, targetRoomIds: string[], limit = 1000) {
|
||||
for (const targetRoomId of targetRoomIds) {
|
||||
await logMessage(LogLevel.DEBUG, "utils#redactUserMessagesIn", `Fetching sent messages for ${userIdOrGlob} in ${targetRoomId} to redact...`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "utils#redactUserMessagesIn", `Fetching sent messages for ${userIdOrGlob} in ${targetRoomId} to redact...`, targetRoomId);
|
||||
|
||||
await getMessagesByUserIn(client, userIdOrGlob, targetRoomId, limit, async (eventsToRedact) => {
|
||||
await getMessagesByUserIn(mjolnir.client, userIdOrGlob, targetRoomId, limit, async (eventsToRedact) => {
|
||||
for (const victimEvent of eventsToRedact) {
|
||||
await logMessage(LogLevel.DEBUG, "utils#redactUserMessagesIn", `Redacting ${victimEvent['event_id']} in ${targetRoomId}`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.DEBUG, "utils#redactUserMessagesIn", `Redacting ${victimEvent['event_id']} in ${targetRoomId}`, targetRoomId);
|
||||
if (!config.noop) {
|
||||
await client.redactEvent(targetRoomId, victimEvent['event_id']);
|
||||
await mjolnir.client.redactEvent(targetRoomId, victimEvent['event_id']);
|
||||
} else {
|
||||
await logMessage(LogLevel.WARN, "utils#redactUserMessagesIn", `Tried to redact ${victimEvent['event_id']} in ${targetRoomId} but Mjolnir is running in no-op mode`, targetRoomId);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "utils#redactUserMessagesIn", `Tried to redact ${victimEvent['event_id']} in ${targetRoomId} but Mjolnir is running in no-op mode`, targetRoomId);
|
||||
}
|
||||
}
|
||||
});
|
||||
@ -191,7 +191,7 @@ export async function getMessagesByUserIn(client: MatrixClient, sender: string,
|
||||
* @param msgtype The desired message type of the returned TextualMessageEventContent
|
||||
* @returns A TextualMessageEventContent with replaced room IDs
|
||||
*/
|
||||
export async function replaceRoomIdsWithPills(client: MatrixClient, text: string, roomIds: Set<string>, msgtype: MessageType = "m.text"): Promise<TextualMessageEventContent> {
|
||||
export async function replaceRoomIdsWithPills(mjolnir: Mjolnir, text: string, roomIds: Set<string>, msgtype: MessageType = "m.text"): Promise<TextualMessageEventContent> {
|
||||
const content: TextualMessageEventContent = {
|
||||
body: text,
|
||||
formatted_body: htmlEscape(text),
|
||||
@ -203,14 +203,14 @@ export async function replaceRoomIdsWithPills(client: MatrixClient, text: string
|
||||
return v.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
|
||||
};
|
||||
|
||||
const viaServers = [(new UserID(await client.getUserId())).domain];
|
||||
const viaServers = [(new UserID(await mjolnir.client.getUserId())).domain];
|
||||
for (const roomId of roomIds) {
|
||||
let alias = roomId;
|
||||
try {
|
||||
alias = (await client.getPublishedAlias(roomId)) || roomId;
|
||||
alias = (await mjolnir.client.getPublishedAlias(roomId)) || roomId;
|
||||
} catch (e) {
|
||||
// This is a recursive call, so tell the function not to try and call us
|
||||
await logMessage(LogLevel.WARN, "utils", `Failed to resolve room alias for ${roomId} - see console for details`, null, true);
|
||||
await mjolnir.logMessage(LogLevel.WARN, "utils", `Failed to resolve room alias for ${roomId} - see console for details`, null, true);
|
||||
LogService.warn("utils", extractRequestError(e));
|
||||
}
|
||||
const regexRoomId = new RegExp(escapeRegex(roomId), "g");
|
||||
|
@ -16,7 +16,7 @@ describe("Test: utils", function() {
|
||||
);
|
||||
|
||||
const out = await replaceRoomIdsWithPills(
|
||||
this.mjolnir.client,
|
||||
this.mjolnir,
|
||||
`it's fun here in ${this.mjolnir.managementRoomId}`,
|
||||
new Set([this.mjolnir.managementRoomId])
|
||||
);
|
||||
|
Loading…
Reference in New Issue
Block a user