supoort native encryption

This commit is contained in:
H. Shay 2024-09-17 11:26:22 -07:00
parent 9e8546366a
commit 63510e96bd
80 changed files with 436 additions and 109 deletions

View File

@ -9,6 +9,19 @@ rawHomeserverUrl: "https://matrix.org"
# Matrix Access Token to use, Mjolnir will only use this if pantalaimon.use is false.
accessToken: "YOUR_TOKEN_HERE"
# Options related to native encryption
encryption:
# whether to use native encryption in mjolnir, rather than using pantalaimon as a proxy
# note that if encryption is enabled here, pantaliamon must be disabled, and vice versa
use: true
# the username to log in with
username: "mjolnir"
# the password to log in with
password: "password"
# Options related to Pantalaimon (https://github.com/matrix-org/pantalaimon)
pantalaimon:
# Whether or not Mjolnir will use pantalaimon to access the matrix homeserver,

View File

@ -9,6 +9,11 @@ homeserverUrl: "http://localhost:8081"
# Where the homeserver is located (client-server URL). NOT pantalaimon.
rawHomeserverUrl: "http://localhost:8081"
encryption:
use: true
username: test
password: testPassword
# README: We use the Pantalaimon client WITHOUT Pantalaimon itself in tests (and the manual test)
# as an easy way to login with passwords from the config without having
# to resolve a chicken-vs-egg problem in regards to access tokens.
@ -16,7 +21,7 @@ rawHomeserverUrl: "http://localhost:8081"
pantalaimon:
# If true, accessToken above is ignored and the username/password below will be
# used instead. The access token of the bot will be stored in the dataPath.
use: true
use: false
# The username to login with.
username: mjolnir

View File

@ -63,7 +63,8 @@
"prom-client": "^14.1.0",
"shell-quote": "^1.7.3",
"ulidx": "^0.3.0",
"yaml": "^2.2.2"
"yaml": "^2.2.2",
"@vector-im/matrix-bot-sdk": "^0.7.1-element.0"
},
"engines": {
"node": ">=18.0.0"

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import * as Sentry from "@sentry/node";
import { extractRequestError, LogLevel, LogService, MessageType, Permalinks, TextualMessageEventContent, UserID } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService, MessageType, Permalinks, TextualMessageEventContent, UserID } from "@vector-im/matrix-bot-sdk";
import { IConfig } from "./config";
import { MatrixSendClient } from "./MatrixEmitter";
import { htmlEscape } from "./utils";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import EventEmitter from "events";
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
/**
* This is an interface created in order to keep the event listener

View File

@ -19,7 +19,8 @@ import {
LogLevel,
LogService,
MembershipEvent,
} from "matrix-bot-sdk";
MatrixClient
} from "@vector-im/matrix-bot-sdk";
import { ALL_RULE_TYPES as ALL_BAN_LIST_RULE_TYPES } from "./models/ListRule";
import { COMMAND_PREFIX, handleCommand } from "./commands/CommandHandler";
@ -136,10 +137,10 @@ export class Mjolnir {
/**
* Create a new Mjolnir instance from a client and the options in the configuration file, ready to be started.
* @param {MatrixSendClient} client The client for Mjolnir to use.
* @param {MatrixClient} client The client for Mjolnir to use.
* @returns A new Mjolnir instance that can be started without further setup.
*/
static async setupMjolnirFromConfig(client: MatrixSendClient, matrixEmitter: MatrixEmitter, config: IConfig): Promise<Mjolnir> {
static async setupMjolnirFromConfig(client: MatrixClient, matrixEmitter: MatrixEmitter, config: IConfig): Promise<Mjolnir> {
if (!config.autojoinOnlyIfManager && config.acceptInvitesFromSpace === getDefaultConfig().acceptInvitesFromSpace) {
throw new TypeError("`autojoinOnlyIfManager` has been disabled but you have not set `acceptInvitesFromSpace`. Please make it empty to accept invites from everywhere or give it a namespace alias or room id.");
}

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import AwaitLock from 'await-lock';
import { extractRequestError, LogService, Permalinks } from "matrix-bot-sdk";
import { extractRequestError, LogService, Permalinks } from "@vector-im/matrix-bot-sdk";
import { IConfig } from "./config";
import { MatrixSendClient } from './MatrixEmitter';
const PROTECTED_ROOMS_EVENT_TYPE = "org.matrix.mjolnir.protected_rooms";

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { LogLevel, LogService, MatrixGlob, Permalinks, UserID } from "matrix-bot-sdk";
import { LogLevel, LogService, MatrixGlob, Permalinks, UserID } from "@vector-im/matrix-bot-sdk";
import { IConfig } from "./config";
import ErrorCache, { ERROR_KIND_FATAL, ERROR_KIND_PERMISSION } from "./ErrorCache";
import ManagementRoomOutput from "./ManagementRoomOutput";

View File

@ -17,7 +17,7 @@ limitations under the License.
import { Bridge } from "matrix-appservice-bridge";
import AccessControlUnit, { EntityAccess } from "../models/AccessControlUnit";
import PolicyList from "../models/PolicyList";
import { Permalinks } from "matrix-bot-sdk";
import { Permalinks } from "@vector-im/matrix-bot-sdk";
/**
* Utility to manage which users have access to the application service,
@ -47,6 +47,7 @@ export class AccessControl {
const accessControlList = new PolicyList(
accessControlListId,
Permalinks.forRoom(accessControlListId),
// @ts-ignore
bridge.getBot().getClient()
);
const accessControlUnit = new AccessControlUnit([accessControlList]);

View File

@ -3,7 +3,7 @@ import { Request, WeakEvent, BridgeContext, Bridge, Intent, Logger } from "matri
import { getProvisionedMjolnirConfig } from "../config";
import { IConfig as IAppserviceConfig } from "./config/config";
import PolicyList from "../models/PolicyList";
import { Permalinks, MatrixClient } from "matrix-bot-sdk";
import { Permalinks, MatrixClient } from "@vector-im/matrix-bot-sdk";
import { DataStore } from "./datastore";
import { AccessControl } from "./AccessControl";
import { Access } from "../models/AccessControlUnit";
@ -140,7 +140,7 @@ export class MjolnirManager {
invite: [requestingUserId],
name: `${requestingUserId}'s mjolnir`
});
// @ts-ignore
const mjolnir = await this.makeInstance(requestingUserId, managementRoomId, mjIntent.matrixClient);
await mjolnir.createFirstList(requestingUserId, "list");
@ -183,6 +183,7 @@ export class MjolnirManager {
await this.makeInstance(
mjolnirRecord.owner,
mjolnirRecord.management_room,
// @ts-ignore
mjIntent.matrixClient,
).catch((e: any) => {
log.error(`Could not start mjolnir ${mjolnirRecord.local_part} for ${mjolnirRecord.owner}:`, e);

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { extractRequestError, LogLevel, LogService } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService } from "@vector-im/matrix-bot-sdk";
// !mjolnir rooms add <room alias/ID>
export async function execAddProtectedRoom(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
async function addRemoveFromDirectory(inRoomId: string, event: any, mjolnir: Mjolnir, roomRef: string, visibility: "public" | "private") {
const isAdmin = await mjolnir.isSynapseAdmin();

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
import { htmlEscape } from "../utils";
// !mjolnir move <alias> <new room ID>

View File

@ -18,7 +18,7 @@ import { Mjolnir } from "../Mjolnir";
import { execStatusCommand } from "./StatusCommand";
import { execBanCommand, execUnbanCommand } from "./UnbanBanCommand";
import { execDumpRulesCommand, execRulesMatchingCommand } from "./DumpRulesCommand";
import { extractRequestError, LogService, RichReply } from "matrix-bot-sdk";
import { extractRequestError, LogService, RichReply } from "@vector-im/matrix-bot-sdk";
import { htmlEscape } from "../utils";
import { execSyncCommand } from "./SyncCommand";
import { execPermissionCheckCommand } from "./PermissionCheckCommand";

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Mjolnir } from "../Mjolnir";
import PolicyList from "../models/PolicyList";
import { Permalinks, RichReply } from "matrix-bot-sdk";
import { Permalinks, RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir list create <shortcode> <alias localpart>
export async function execCreateListCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir deactivate <user ID>
export async function execDeactivateCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
import { Mjolnir } from "../Mjolnir";
import { EntityType } from "../models/ListRule";
import { htmlEscape } from "../utils";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
import { EntityType } from "../models/ListRule";
import PolicyList from "../models/PolicyList";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { LogLevel, MatrixGlob, RichReply } from "matrix-bot-sdk";
import { LogLevel, MatrixGlob, RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir kick <user|filter> [room] [reason]
export async function execKickCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { Permalinks, RichReply } from "matrix-bot-sdk";
import { Permalinks, RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir rooms
export async function execListProtectedRooms(roomId: string, event: any, mjolnir: Mjolnir) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir make admin <room> [<user ID>]
export async function execMakeRoomAdminCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -16,7 +16,7 @@ limitations under the License.
import { htmlEscape } from "../utils";
import { Mjolnir } from "../Mjolnir";
import { extractRequestError, LogService, RichReply } from "matrix-bot-sdk";
import { extractRequestError, LogService, RichReply } from "@vector-im/matrix-bot-sdk";
import { isListSetting } from "../protections/ProtectionSettings";
// !mjolnir enable <protection>

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Mjolnir } from "../Mjolnir";
import { redactUserMessagesIn } from "../utils";
import { Permalinks } from "matrix-bot-sdk";
import { Permalinks } from "@vector-im/matrix-bot-sdk";
// !mjolnir redact <user ID> [room alias] [limit]
export async function execRedactCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
export const DEFAULT_LIST_EVENT_TYPE = "org.matrix.mjolnir.default_list";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { extractRequestError, LogLevel, LogService } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService } from "@vector-im/matrix-bot-sdk";
// !mjolnir powerlevel <user ID> <level> [room]
export async function execSetPowerLevelCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -1,5 +1,5 @@
import { Mjolnir } from "../Mjolnir";
import { LogLevel } from "matrix-bot-sdk";
import { LogLevel } from "@vector-im/matrix-bot-sdk";
const EVENT_MODERATED_BY = "org.matrix.msc3215.room.moderation.moderated_by";
const EVENT_MODERATOR_OF = "org.matrix.msc3215.room.moderation.moderator_of";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir shutdown room <room> [<message>]
export async function execShutdownRoomCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { LogLevel, LogService, RichReply } from "matrix-bot-sdk";
import { LogLevel, LogService, RichReply } from "@vector-im/matrix-bot-sdk";
import { htmlEscape, parseDuration } from "../utils";
import { ParseEntry } from "shell-quote";
import { HumanizeDurationLanguage, HumanizeDuration } from "humanize-duration-ts";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir, STATE_CHECKING_PERMISSIONS, STATE_NOT_STARTED, STATE_RUNNING, STATE_SYNCING } from "../Mjolnir";
import { RichReply } from "matrix-bot-sdk";
import { RichReply } from "@vector-im/matrix-bot-sdk";
import { htmlEscape, parseDuration } from "../utils";
import { HumanizeDurationLanguage, HumanizeDuration } from "humanize-duration-ts";
import PolicyList from "../models/PolicyList";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import {Mjolnir} from "../Mjolnir";
import {RichReply} from "matrix-bot-sdk";
import {RichReply} from "@vector-im/matrix-bot-sdk";
export async function execSuspendCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {
const target = parts[2];

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Mjolnir } from "../Mjolnir";
import PolicyList from "../models/PolicyList";
import { extractRequestError, LogLevel, LogService, MatrixGlob, RichReply } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService, MatrixGlob, RichReply } from "@vector-im/matrix-bot-sdk";
import { RULE_ROOM, RULE_SERVER, RULE_USER, USER_RULE_TYPES } from "../models/ListRule";
import { DEFAULT_LIST_EVENT_TYPE } from "./SetDefaultBanListCommand";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import {Mjolnir} from "../Mjolnir";
import {RichReply} from "matrix-bot-sdk";
import {RichReply} from "@vector-im/matrix-bot-sdk";
export async function execUnsuspendCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {
const target = parts[2];

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { Mjolnir } from "../Mjolnir";
import { Permalinks, RichReply } from "matrix-bot-sdk";
import { Permalinks, RichReply } from "@vector-im/matrix-bot-sdk";
// !mjolnir watch <room alias or ID>
export async function execWatchCommand(roomId: string, event: any, mjolnir: Mjolnir, parts: string[]) {

View File

@ -16,7 +16,7 @@ limitations under the License.
import * as fs from "fs";
import { load } from "js-yaml";
import { MatrixClient, LogService } from "matrix-bot-sdk";
import { MatrixClient, LogService } from "@vector-im/matrix-bot-sdk";
import Config from "config";
export interface IHealthConfig {
@ -70,6 +70,11 @@ export interface IConfig {
homeserverUrl: string;
rawHomeserverUrl: string;
accessToken: string;
encryption: {
use: boolean;
username: string;
password: string;
}
pantalaimon: {
use: boolean;
username: string;
@ -189,6 +194,11 @@ const defaultConfig: IConfig = {
homeserverUrl: "http://localhost:8008",
rawHomeserverUrl: "http://localhost:8008",
accessToken: "NONE_PROVIDED",
encryption: {
use: true,
username: "",
password: "",
},
pantalaimon: {
use: false,
username: "",

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import * as http from "http";
import { LogService } from "matrix-bot-sdk";
import { LogService } from "@vector-im/matrix-bot-sdk";
import { IConfig } from "../config";
// allowed to use the global configuration since this is only intended to be used by `src/index.ts`.

View File

@ -24,8 +24,12 @@ import {
MatrixClient,
PantalaimonClient,
RichConsoleLogger,
SimpleFsStorageProvider
} from "matrix-bot-sdk";
SimpleFsStorageProvider,
RustSdkCryptoStorageProvider,
MatrixAuth
} from "@vector-im/matrix-bot-sdk"
import { read as configRead } from "./config";
import { Mjolnir } from "./Mjolnir";
@ -59,13 +63,35 @@ import { initializeSentry, initializeGlobalPerformanceMetrics, patchMatrixClient
try {
const storagePath = path.isAbsolute(config.dataPath) ? config.dataPath : path.join(__dirname, '../', config.dataPath);
const storage = new SimpleFsStorageProvider(path.join(storagePath, "bot.json"));
const cryptoStorage = new RustSdkCryptoStorageProvider(storagePath, 0)
if (config.encryption.use && config.pantalaimon.use) {
throw Error('Cannot enable both pantalaimon and encryption at the same time. Remove one from the config.');
}
let client: MatrixClient;
if (config.pantalaimon.use) {
const pantalaimon = new PantalaimonClient(config.homeserverUrl, storage);
client = await pantalaimon.createClientWithCredentials(config.pantalaimon.username, config.pantalaimon.password);
} else {
client = new MatrixClient(config.homeserverUrl, config.accessToken, storage);
const accessToken = await Promise.resolve(storage.readValue("access_token"));
if (accessToken) {
client = new MatrixClient(config.homeserverUrl, accessToken, storage, cryptoStorage);
}
else {
const auth = new MatrixAuth(config.homeserverUrl)
const tempClient = await auth.passwordLogin(config.encryption.username, config.encryption.password)
client = new MatrixClient(config.homeserverUrl, tempClient.accessToken, storage, cryptoStorage);
}
try {
LogService.info("index", "Preparing encrypted client...")
await client.crypto.prepare();
} catch (e) {
LogService.error("Index", `Error preparing encrypted client ${e}`)
throw e
}
}
patchMatrixClient();
config.RUNTIME.client = client;

View File

@ -16,7 +16,7 @@ limitations under the License.
import PolicyList, { ChangeType, ListRuleChange } from "./PolicyList";
import { EntityType, ListRule, Recommendation, RULE_SERVER, RULE_USER } from "./ListRule";
import { LogService, UserID } from "matrix-bot-sdk";
import { LogService, UserID } from "@vector-im/matrix-bot-sdk";
import { ServerAcl } from "./ServerAcl";
/**

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { MatrixGlob } from "matrix-bot-sdk";
import { MatrixGlob } from "@vector-im/matrix-bot-sdk";
export enum EntityType {
/// `entity` is to be parsed as a glob of users IDs

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { extractRequestError, LogLevel, LogService, Permalinks, RoomCreateOptions, UserID } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService, Permalinks, RoomCreateOptions, UserID } from "@vector-im/matrix-bot-sdk";
import { EventEmitter } from "events";
import { ALL_RULE_TYPES, EntityType, ListRule, Recommendation, ROOM_RULE_TYPES, RULE_ROOM, RULE_SERVER, RULE_USER, SERVER_RULE_TYPES, USER_RULE_TYPES } from "./ListRule";
import { MatrixSendClient } from "../MatrixEmitter";

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import BanList, { ChangeType, ListRuleChange } from "./PolicyList"
import * as crypto from "crypto";
import { LogService } from "matrix-bot-sdk";
import { LogService } from "@vector-im/matrix-bot-sdk";
import { EntityType, ListRule } from "./ListRule";
import PolicyList from "./PolicyList";

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { MatrixGlob } from "matrix-bot-sdk";
import { MatrixGlob } from "@vector-im/matrix-bot-sdk";
import { setToArray } from "../utils";
export interface ServerAclContent {

View File

@ -17,7 +17,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { NumberProtectionSetting } from "./ProtectionSettings";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, LogService } from "matrix-bot-sdk";
import { LogLevel, LogService } from "@vector-im/matrix-bot-sdk";
// if this is exceeded, we'll ban the user for spam and redact their messages
export const DEFAULT_MAX_PER_MINUTE = 10;

View File

@ -17,7 +17,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { DurationMSProtectionSetting, NumberProtectionSetting, StringSetProtectionSetting } from "./ProtectionSettings";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, UserID } from "matrix-bot-sdk";
import { LogLevel, UserID } from "@vector-im/matrix-bot-sdk";
const DEFAULT_BUCKET_DURATION_MS = 10_000;
const DEFAULT_BUCKET_NUMBER = 6;

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, LogService } from "matrix-bot-sdk";
import { LogLevel, LogService } from "@vector-im/matrix-bot-sdk";
import { isTrueJoinEvent } from "../utils";
export class FirstMessageIsImage extends Protection {

View File

@ -17,7 +17,7 @@ limitations under the License.
import {Protection} from "./IProtection";
import {Mjolnir} from "../Mjolnir";
import {NumberProtectionSetting} from "./ProtectionSettings";
import {LogLevel} from "matrix-bot-sdk";
import {LogLevel} from "@vector-im/matrix-bot-sdk";
const DEFAULT_MAX_PER_TIMESCALE = 50;
const DEFAULT_TIMESCALE_MINUTES = 60;

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { LogLevel } from "matrix-bot-sdk";
import { LogLevel } from "@vector-im/matrix-bot-sdk";
import { Mjolnir } from "../Mjolnir";
import { Protection } from "./IProtection";

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, Permalinks, UserID } from "matrix-bot-sdk";
import { LogLevel, Permalinks, UserID } from "@vector-im/matrix-bot-sdk";
export class MessageIsMedia extends Protection {

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, Permalinks, UserID } from "matrix-bot-sdk";
import { LogLevel, Permalinks, UserID } from "@vector-im/matrix-bot-sdk";
export class MessageIsVoice extends Protection {

View File

@ -17,7 +17,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { Mjolnir } from "../Mjolnir";
import * as nsfw from 'nsfwjs';
import {LogLevel} from "matrix-bot-sdk";
import {LogLevel} from "@vector-im/matrix-bot-sdk";
import { node } from '@tensorflow/tfjs-node';

View File

@ -24,7 +24,7 @@ import { MessageIsMedia } from "./MessageIsMedia";
import { TrustedReporters } from "./TrustedReporters";
import { JoinWaveShortCircuit } from "./JoinWaveShortCircuit";
import { Mjolnir } from "../Mjolnir";
import { extractRequestError, LogLevel, LogService, Permalinks } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService, Permalinks } from "@vector-im/matrix-bot-sdk";
import { ProtectionSettingValidationError } from "./ProtectionSettings";
import { Consequence } from "./consequence";
import { htmlEscape } from "../utils";

View File

@ -17,7 +17,7 @@ limitations under the License.
import { Protection } from "./IProtection";
import { ConsequenceBan, ConsequenceRedact } from "./consequence";
import { Mjolnir } from "../Mjolnir";
import { LogLevel, LogService } from "matrix-bot-sdk";
import { LogLevel, LogService } from "@vector-im/matrix-bot-sdk";
import { isTrueJoinEvent } from "../utils";
export class WordList extends Protection {

View File

@ -13,7 +13,7 @@ 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, MatrixClient } from "@vector-im/matrix-bot-sdk"
import { ERROR_KIND_FATAL } from "../ErrorCache";
import { RoomUpdateError } from "../models/RoomUpdateError";
import { redactUserMessagesIn } from "../utils";

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
import { extractRequestError, LogLevel } from "matrix-bot-sdk";
import { extractRequestError, LogLevel } from "@vector-im/matrix-bot-sdk";
import { Mjolnir } from "../Mjolnir";
export type Task<T> = (queue: ThrottlingQueue) => Promise<T>;

View File

@ -13,7 +13,7 @@ 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, Permalinks } from "matrix-bot-sdk";
import { extractRequestError, LogLevel, LogService, Permalinks } from "@vector-im/matrix-bot-sdk";
import { Mjolnir } from "../Mjolnir";
/**

View File

@ -15,7 +15,7 @@ limitations under the License.
*/
import { PowerLevelAction } from "matrix-bot-sdk/lib/models/PowerLevelAction";
import { LogService, UserID } from "matrix-bot-sdk";
import { LogService, UserID } from "@vector-im/matrix-bot-sdk";
import { htmlToText } from "html-to-text";
import { htmlEscape } from "../utils";
import { JSDOM } from 'jsdom';

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Mjolnir, REPORT_POLL_EVENT_TYPE } from "../Mjolnir";
import { ReportManager } from './ReportManager';
import { LogLevel } from "matrix-bot-sdk";
import { LogLevel } from "@vector-im/matrix-bot-sdk";
class InvalidStateError extends Error { }

View File

@ -20,7 +20,7 @@ import {
MatrixGlob,
getRequestFn,
setRequestFn,
} from "matrix-bot-sdk";
} from "@vector-im/matrix-bot-sdk";
import { ClientRequest, IncomingMessage } from "http";
import { default as parseDuration } from "parse-duration";
import * as Sentry from '@sentry/node';

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Server } from "http";
import express from "express";
import { LogService } from "matrix-bot-sdk";
import { LogService } from "@vector-im/matrix-bot-sdk";
import { IHealthConfig } from "../config";
import { collectDefaultMetrics, register } from "prom-client";

View File

@ -16,7 +16,7 @@ limitations under the License.
import { Server } from "http";
import express from "express";
import { LogService, MatrixClient } from "matrix-bot-sdk";
import { LogService, MatrixClient } from "@vector-im/matrix-bot-sdk";
import RuleServer from "../models/RuleServer";
import { ReportManager } from "../report/ReportManager";
import { IConfig } from "../config";

View File

@ -1,7 +1,7 @@
import { isPolicyRoom, readTestConfig, setupHarness } from "../utils/harness";
import { newTestUser } from "../../integration/clientHelper";
import { getFirstReply } from "../../integration/commands/commandUtils";
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
import { MjolnirAppService } from "../../../src/appservice/AppService";
import dns from 'node:dns';

View File

@ -2,7 +2,7 @@ import { MjolnirAppService } from "../../../src/appservice/AppService";
import { newTestUser } from "../../integration/clientHelper";
import { isPolicyRoom, readTestConfig, setupHarness } from "../utils/harness";
import { CreateMjolnirResponse, MjolnirWebAPIClient } from "../utils/webAPIClient";
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
import { getFirstReply } from "../../integration/commands/commandUtils";
import expect from "expect";
import dns from 'node:dns';

View File

@ -4,7 +4,7 @@ import { ensureAliasedRoomExists } from "../../integration/mjolnirSetupUtils";
import { read as configRead, IConfig } from "../../../src/appservice/config/config";
import { newTestUser } from "../../integration/clientHelper";
import PolicyList from "../../../src/models/PolicyList";
import { CreateEvent, MatrixClient } from "matrix-bot-sdk";
import { CreateEvent, MatrixClient } from "@vector-im/matrix-bot-sdk";
export function readTestConfig(): IConfig {
return configRead(path.join(__dirname, "../../../src/appservice/config/config.harness.yaml"));

View File

@ -1,5 +1,5 @@
import * as request from "request";
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
interface OpenIDTokenInfo {
access_token: string,

View File

@ -1,4 +1,4 @@
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
import { Mjolnir } from "../../src/Mjolnir"
import { newTestUser } from "./clientHelper";

View File

@ -1,6 +1,6 @@
import { strict as assert } from "assert";
import { newTestUser } from "./clientHelper";
import { LogService, MatrixClient, Permalinks, UserID } from "matrix-bot-sdk";
import { LogService, MatrixClient, Permalinks, UserID } from "@vector-im/matrix-bot-sdk";
import PolicyList, { ChangeType } from "../../src/models/PolicyList";
import { ServerAcl } from "../../src/models/ServerAcl";
import { getFirstReaction } from "./commands/commandUtils";

View File

@ -1,8 +1,17 @@
import { HmacSHA1 } from "crypto-js";
import { getRequestFn, LogService, MatrixClient, MemoryStorageProvider, PantalaimonClient } from "matrix-bot-sdk";
import {
getRequestFn,
LogService,
MatrixClient,
MemoryStorageProvider,
PantalaimonClient,
RustSdkCryptoStorageProvider
} from "@vector-im/matrix-bot-sdk";
import { promises as fs } from "fs";
const REGISTRATION_ATTEMPTS = 10;
const REGISTRATION_RETRY_BASE_DELAY_MS = 100;
let CryptoStorePaths: string[] = [];
/**
* Register a user using the synapse admin api that requires the use of a registration secret rather than an admin user.
@ -15,7 +24,7 @@ const REGISTRATION_RETRY_BASE_DELAY_MS = 100;
* @param admin True to make the user an admin, false otherwise.
* @returns The response from synapse.
*/
export async function registerUser(homeserver: string, username: string, displayname: string, password: string, admin: boolean): Promise<void> {
export async function registerUser(homeserver: string, username: string, displayname: string, password: string, admin: boolean): Promise<any> {
let registerUrl = `${homeserver}/_synapse/admin/v1/register`
const data: {nonce: string} = await new Promise((resolve, reject) => {
getRequestFn()({uri: registerUrl, method: "GET", timeout: 60000}, (error: any, response: any, resBody: any) => {
@ -25,8 +34,7 @@ export async function registerUser(homeserver: string, username: string, display
const nonce = data.nonce!;
let mac = HmacSHA1(`${nonce}\0${username}\0${password}\0${admin ? 'admin' : 'notadmin'}`, 'REGISTRATION_SHARED_SECRET');
for (let i = 1; i <= REGISTRATION_ATTEMPTS; ++i) {
try {
const params = {
const params = {
uri: registerUrl,
method: "POST",
headers: {"Content-Type": "application/json"},
@ -40,16 +48,56 @@ export async function registerUser(homeserver: string, username: string, display
}),
timeout: 60000
}
try {
return await new Promise((resolve, reject) => {
getRequestFn()(params, (error: any) => error ? reject(error) : resolve());
getRequestFn()(params, (error: any, response: any, respBody: any) => {
if (error) {
reject(error)
}
if (response.statusCode != 200) {
reject(JSON.parse(response.body))
}
resolve(JSON.parse(respBody));
});
});
} catch (ex) {
let err;
if (ex instanceof Error) {
err = ex.body.errcode
} else {
err = ex.errcode
}
// In case of timeout or throttling, backoff and retry.
if (ex?.code === 'ESOCKETTIMEDOUT' || ex?.code === 'ETIMEDOUT'
|| ex?.body?.errcode === 'M_LIMIT_EXCEEDED') {
if (err === 'ESOCKETTIMEDOUT' || err === 'ETIMEDOUT'
|| err === 'M_LIMIT_EXCEEDED') {
await new Promise(resolve => setTimeout(resolve, REGISTRATION_RETRY_BASE_DELAY_MS * i * i));
continue;
}
if (err === 'M_USER_IN_USE') {
console.log("logging in")
const loginUrl = `${homeserver}/_matrix/client/r0/login`
const params = {
uri: loginUrl,
method: "POST",
headers: {"Content-Type": "application/json"},
body: JSON.stringify({
"type": "m.login.password",
"identifier": {
"type": "m.id.user",
"user": username
},
"password": password
}),
timeout: 60000
}
return await new Promise((resolve, reject) => {
getRequestFn()(params, (error: any, result: any, respBody: any) => {
let resp = JSON.parse(respBody)
console.log(resp)
error ? reject(error) : resolve(resp.access_token)
});
});
}
throw ex;
}
}
@ -180,3 +228,14 @@ export function noticeListener(targetRoomdId: string, cb: (event: any) => void)
cb(event);
}
}
export async function teardownCryptoStores () {
await Promise.all(CryptoStorePaths.map(p => fs.rm(p, { force: true, recursive: true})));
CryptoStorePaths = [];
}
export async function getTempCryptoStore() {
const cryptoDir = await fs.mkdtemp('mjolnir-integration-test');
CryptoStorePaths.push(cryptoDir);
return new RustSdkCryptoStorageProvider(cryptoDir, 0);
}

View File

@ -1,4 +1,4 @@
import { MatrixClient } from "matrix-bot-sdk";
import { MatrixClient } from "@vector-im/matrix-bot-sdk";
import { strict as assert } from "assert";
import * as crypto from "crypto";
import { MatrixEmitter } from "../../../src/MatrixEmitter";

View File

@ -2,7 +2,7 @@
import { newTestUser } from "../clientHelper";
import { PowerLevelAction } from "matrix-bot-sdk/lib/models/PowerLevelAction";
import { LogService } from "matrix-bot-sdk";
import { LogService } from "@vector-im/matrix-bot-sdk";
import { getFirstReaction } from "./commandUtils";
describe("Test: The make admin command", function () {

View File

@ -2,7 +2,7 @@ import { strict as assert } from "assert";
import { newTestUser } from "../clientHelper";
import { getMessagesByUserIn } from "../../../src/utils";
import { LogService } from "matrix-bot-sdk";
import { LogService } from "@vector-im/matrix-bot-sdk";
import { getFirstReaction } from "./commandUtils";
describe("Test: The redaction command", function () {

View File

@ -16,7 +16,7 @@ limitations under the License.
import {newTestUser} from "../clientHelper";
import {strict as assert} from "assert";
import { MatrixClient, RoomCreateOptions } from "matrix-bot-sdk";
import { MatrixClient, RoomCreateOptions } from "@vector-im/matrix-bot-sdk";
import { read as configRead } from "../../../src/config";
describe("Test: suspend/unsuspend command", function () {

View File

@ -1,6 +1,6 @@
import { strict as assert } from "assert";
import { UserID } from "matrix-bot-sdk";
import { UserID } from "@vector-im/matrix-bot-sdk";
import { Suite } from "mocha";
import { Mjolnir } from "../../src/Mjolnir";
import { DetectFederationLag, LAG_STATE_EVENT } from "../../src/protections/DetectFederationLag";

View File

@ -1,6 +1,7 @@
import { read as configRead } from "../../src/config";
import { makeMjolnir, teardownManagementRoom } from "./mjolnirSetupUtils";
import dns from 'node:dns';
import { teardownCryptoStores } from "./clientHelper";
// Necessary for CI: Node 17+ defaults to using ipv6 first, but Github Actions does not support ipv6
dns.setDefaultResultOrder('ipv4first');
@ -39,6 +40,7 @@ export const mochaHooks = {
]);
// remove alias from management room and leave it.
await teardownManagementRoom(this.mjolnir.client, this.mjolnir.managementRoomId, this.managementRoomAlias);
await teardownCryptoStores();
console.error("---- completed test", JSON.stringify(this.currentTest.title), "\n\n"); // Makes MatrixClient error logs a bit easier to parse.
}
]

View File

@ -15,18 +15,18 @@ limitations under the License.
*/
import {
MatrixClient,
PantalaimonClient,
MemoryStorageProvider,
LogService,
LogLevel,
RichConsoleLogger
} from "matrix-bot-sdk";
} from "@vector-im/matrix-bot-sdk";
import { Mjolnir} from '../../src/Mjolnir';
import { overrideRatelimitForUser, registerUser } from "./clientHelper";
import { overrideRatelimitForUser, registerUser, getTempCryptoStore } from "./clientHelper";
import { initializeGlobalPerformanceMetrics, initializeSentry, patchMatrixClient } from "../../src/utils";
import { IConfig } from "../../src/config";
/**
* Ensures that a room exists with the alias, if it does not exist we create it.
* @param client The MatrixClient to use to resolve or create the aliased room.
@ -49,18 +49,16 @@ export async function ensureAliasedRoomExists(client: MatrixClient, alias: strin
}
}
async function configureMjolnir(config: IConfig) {
async function configureMjolnir(config: IConfig): Promise<string> {
// Initialize error monitoring as early as possible.
initializeSentry(config);
initializeGlobalPerformanceMetrics(config);
try {
await registerUser(config.homeserverUrl, config.pantalaimon.username, config.pantalaimon.username, config.pantalaimon.password, true)
const accessToken = await registerUser(config.homeserverUrl, config.encryption.username, "testMjolnir", config.encryption.password, true)
return accessToken
} catch (e) {
if (e?.body?.errcode === 'M_USER_IN_USE') {
console.log(`${config.pantalaimon.username} already registered, skipping`);
return;
}
console.log(`Error registering user ${e}`)
throw e;
};
}
@ -82,8 +80,16 @@ export async function makeMjolnir(config: IConfig): Promise<Mjolnir> {
LogService.setLogger(new RichConsoleLogger());
LogService.setLevel(LogLevel.fromString(config.logLevel, LogLevel.DEBUG));
LogService.info("test/mjolnirSetupUtils", "Starting bot...");
const pantalaimon = new PantalaimonClient(config.homeserverUrl, new MemoryStorageProvider());
const client = await pantalaimon.createClientWithCredentials(config.pantalaimon.username, config.pantalaimon.password);
let accessToken = await configureMjolnir(config)
let cryptoStore = await getTempCryptoStore()
let client = new MatrixClient(config.homeserverUrl, accessToken, new MemoryStorageProvider(), cryptoStore);
try {
LogService.info("index", "Preparing encrypted client...")
await client.crypto.prepare();
} catch (e) {
LogService.error("Index", `Error preparing encrypted client ${e}`)
throw e
}
await overrideRatelimitForUser(config.homeserverUrl, await client.getUserId());
patchMatrixClient();
await ensureAliasedRoomExists(client, config.managementRoom);

View File

@ -1,6 +1,6 @@
import {newTestUser} from "./clientHelper";
import {MatrixClient} from "matrix-bot-sdk";
import {MatrixClient} from "@vector-im/matrix-bot-sdk";
import {getFirstReaction} from "./commands/commandUtils";
import {strict as assert} from "assert";
import { readFileSync } from 'fs';

View File

@ -1,5 +1,5 @@
import { strict as assert } from "assert";
import { getRequestFn } from "matrix-bot-sdk";
import { getRequestFn } from "@vector-im/matrix-bot-sdk";
import { IConfig } from "../../src/config";

View File

@ -3,7 +3,7 @@ import { strict as assert } from "assert";
import { newTestUser } from "./clientHelper";
import { Mjolnir } from "../../src/Mjolnir";
import { read as configRead } from "../../src/config";
import { getRequestFn, LogService } from "matrix-bot-sdk";
import { getRequestFn, LogService } from "@vector-im/matrix-bot-sdk";
import { createBanList, getFirstReaction } from "./commands/commandUtils";
/**

View File

@ -1,6 +1,6 @@
import { strict as assert } from "assert";
import { MatrixClient, Permalinks, UserID } from "matrix-bot-sdk";
import { MatrixClient, Permalinks, UserID } from "@vector-im/matrix-bot-sdk";
import { MatrixSendClient } from "../../src/MatrixEmitter";
import { Mjolnir } from "../../src/Mjolnir";
import PolicyList from "../../src/models/PolicyList";

View File

@ -1,6 +1,6 @@
import { strict as assert } from "assert";
import { UserID } from "matrix-bot-sdk";
import { UserID } from "@vector-im/matrix-bot-sdk";
import { ThrottlingQueue } from "../../src/queues/ThrottlingQueue";
describe("Test: ThrottlingQueue", function() {

View File

@ -1,5 +1,5 @@
import { strict as assert } from "assert";
import { LogLevel } from "matrix-bot-sdk";
import { LogLevel } from "@vector-im/matrix-bot-sdk";
import ManagementRoomOutput from "../../src/ManagementRoomOutput";
describe("Test: utils", function() {

224
yarn.lock
View File

@ -104,6 +104,14 @@
semver "^7.3.5"
tar "^6.1.11"
"@matrix-org/matrix-sdk-crypto-nodejs@0.2.0-beta.1":
version "0.2.0-beta.1"
resolved "https://registry.yarnpkg.com/@matrix-org/matrix-sdk-crypto-nodejs/-/matrix-sdk-crypto-nodejs-0.2.0-beta.1.tgz#b696707ccfa944cfed3c96cf7e54799b0f1e3329"
integrity sha512-CgbOKORfD6dvYgQTPhfN73H1RbQknrFkMnRRwCIJMt15iL2AF1gEowgbrlGhkbG6gNng4CgPnKs1iHKCRrhvmA==
dependencies:
https-proxy-agent "^5.0.1"
node-downloader-helper "^2.1.5"
"@matrix-org/matrix-sdk-crypto-nodejs@^0.1.0-beta.1":
version "0.1.0-beta.1"
resolved "https://registry.npmjs.org/@matrix-org/matrix-sdk-crypto-nodejs/-/matrix-sdk-crypto-nodejs-0.1.0-beta.1.tgz"
@ -111,6 +119,14 @@
dependencies:
node-downloader-helper "^2.1.1"
"@selderee/plugin-htmlparser2@^0.11.0":
version "0.11.0"
resolved "https://registry.yarnpkg.com/@selderee/plugin-htmlparser2/-/plugin-htmlparser2-0.11.0.tgz#d5b5e29a7ba6d3958a1972c7be16f4b2c188c517"
integrity sha512-P33hHGdldxGabLFjPPpaTxVolMrzrcegejx+0GxjrIb9Zv48D8yAIA/QTDR2dFl7Uz7urX8aX6+5bCZslr+gWQ==
dependencies:
domhandler "^5.0.3"
selderee "^0.11.0"
"@selderee/plugin-htmlparser2@^0.6.0":
version "0.6.0"
resolved "https://registry.npmjs.org/@selderee/plugin-htmlparser2/-/plugin-htmlparser2-0.6.0.tgz"
@ -289,6 +305,16 @@
"@types/qs" "*"
"@types/range-parser" "*"
"@types/express-serve-static-core@^4.17.33":
version "4.19.5"
resolved "https://registry.yarnpkg.com/@types/express-serve-static-core/-/express-serve-static-core-4.19.5.tgz#218064e321126fcf9048d1ca25dd2465da55d9c6"
integrity sha512-y6W03tvrACO72aijJ5uF02FRq5cgDR9lUxddQ8vyF+GvmjJQqbzDcJngEjURc+ZsG31VI3hODNZJ2URj86pzmg==
dependencies:
"@types/node" "*"
"@types/qs" "*"
"@types/range-parser" "*"
"@types/send" "*"
"@types/express@^4.17.13", "@types/express@^4.17.8":
version "4.17.13"
resolved "https://registry.npmjs.org/@types/express/-/express-4.17.13.tgz"
@ -299,6 +325,16 @@
"@types/qs" "*"
"@types/serve-static" "*"
"@types/express@^4.17.21":
version "4.17.21"
resolved "https://registry.yarnpkg.com/@types/express/-/express-4.17.21.tgz#c26d4a151e60efe0084b23dc3369ebc631ed192d"
integrity sha512-ejlPM315qwLpaQlQDTjPdsUFSc6ZsP4AN6AlWnogPjQ7CVi7PYF3YVz+CY3jE2pwYf7E/7HlDAN0rV2GxTG0HQ==
dependencies:
"@types/body-parser" "*"
"@types/express-serve-static-core" "^4.17.33"
"@types/qs" "*"
"@types/serve-static" "*"
"@types/html-to-text@^8.0.1":
version "8.0.1"
resolved "https://registry.npmjs.org/@types/html-to-text/-/html-to-text-8.0.1.tgz"
@ -445,6 +481,14 @@
resolved "https://registry.yarnpkg.com/@types/seedrandom/-/seedrandom-2.4.34.tgz#c725cd0fc0442e2d3d0e5913af005686ffb7eb99"
integrity sha512-ytDiArvrn/3Xk6/vtylys5tlY6eo7Ane0hvcx++TKo6RxQXuVfW0AF/oeWqAj9dN29SyhtawuXstgmPlwNcv/A==
"@types/send@*":
version "0.17.4"
resolved "https://registry.yarnpkg.com/@types/send/-/send-0.17.4.tgz#6619cd24e7270793702e4e6a4b958a9010cfc57a"
integrity sha512-x2EM6TJOybec7c52BX0ZspPodMsQUd5L6PRwOunVyVUhXiBSKf3AezDL8Dgvgt5o0UfKNfuA0eMLr2wLT4AiBA==
dependencies:
"@types/mime" "^1"
"@types/node" "*"
"@types/serve-static@*":
version "1.13.10"
resolved "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.13.10.tgz"
@ -485,6 +529,30 @@
resolved "https://registry.npmjs.org/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz"
integrity sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q==
"@vector-im/matrix-bot-sdk@^0.7.1-element.0":
version "0.7.1-element.4"
resolved "https://registry.yarnpkg.com/@vector-im/matrix-bot-sdk/-/matrix-bot-sdk-0.7.1-element.4.tgz#fa83785986643d544b8e0cc05811ca3c0eb7e1d1"
integrity sha512-v2o6rG9a3845XvwRbt0vJaqPAtRMPThcnBFsNncq/LXHBKtZHFJAfSbgWKcj7PF+fvwjfR5YsokDNjOXyHZV9g==
dependencies:
"@matrix-org/matrix-sdk-crypto-nodejs" "0.2.0-beta.1"
"@types/express" "^4.17.21"
another-json "^0.2.0"
async-lock "^1.4.0"
chalk "4"
express "^4.18.2"
glob-to-regexp "^0.4.1"
hash.js "^1.1.7"
html-to-text "^9.0.5"
htmlencode "^0.0.4"
lowdb "1"
lru-cache "^10.0.1"
mkdirp "^3.0.1"
morgan "^1.10.0"
postgres "^3.4.1"
request "^2.88.2"
request-promise "^4.2.6"
sanitize-html "^2.11.0"
"@webgpu/types@0.1.38":
version "0.1.38"
resolved "https://registry.yarnpkg.com/@webgpu/types/-/types-0.1.38.tgz#6fda4b410edc753d3213c648320ebcf319669020"
@ -674,6 +742,11 @@ async-lock@^1.3.2:
resolved "https://registry.npmjs.org/async-lock/-/async-lock-1.3.2.tgz"
integrity sha512-phnXdS3RP7PPcmP6NWWzWMU0sLTeyvtZCxBPpZdkYE3seGLKSQZs9FrmVO/qwypq98FUtWWUEYxziLkdGk5nnA==
async-lock@^1.4.0:
version "1.4.1"
resolved "https://registry.yarnpkg.com/async-lock/-/async-lock-1.4.1.tgz#56b8718915a9b68b10fce2f2a9a3dddf765ef53f"
integrity sha512-Az2ZTpuytrtqENulXwO3GGv1Bztugx6TT37NIo7imr/Qo0gsYiGtSdBa2B6fsXhTpVZDNfu1Qn3pk531e3q+nQ==
async@0.2.10:
version "0.2.10"
resolved "https://registry.npmjs.org/async/-/async-0.2.10.tgz"
@ -850,6 +923,14 @@ caseless@~0.12.0:
resolved "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz"
integrity sha512-4tYFyifaFfGacoiObjJegolkwSU4xQNGbVgUiNYVUxbQ2x2lUsFvY4hVgVzGiIe6WLOPqycWXA40l+PWsxthUw==
chalk@4, chalk@^4, chalk@^4.0.0, chalk@^4.1.0:
version "4.1.2"
resolved "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz"
integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==
dependencies:
ansi-styles "^4.1.0"
supports-color "^7.1.0"
chalk@^2.0.0, chalk@^2.3.0:
version "2.4.2"
resolved "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz"
@ -859,14 +940,6 @@ chalk@^2.0.0, chalk@^2.3.0:
escape-string-regexp "^1.0.5"
supports-color "^5.3.0"
chalk@^4, chalk@^4.0.0, chalk@^4.1.0:
version "4.1.2"
resolved "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz"
integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==
dependencies:
ansi-styles "^4.1.0"
supports-color "^7.1.0"
chokidar@3.5.3:
version "3.5.3"
resolved "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz"
@ -1108,6 +1181,11 @@ deepmerge@^4.2.2:
resolved "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz"
integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==
deepmerge@^4.3.1:
version "4.3.1"
resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.3.1.tgz#44b5f2147cd3b00d4b56137685966f26fd25dd4a"
integrity sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==
define-data-property@^1.1.4:
version "1.1.4"
resolved "https://registry.yarnpkg.com/define-data-property/-/define-data-property-1.1.4.tgz#894dc141bb7d3060ae4366f6a0107e68fbe48c5e"
@ -1535,6 +1613,43 @@ express@^4.17.1, express@^4.18.1, express@^4.20:
utils-merge "1.0.1"
vary "~1.1.2"
express@^4.18.2:
version "4.21.0"
resolved "https://registry.yarnpkg.com/express/-/express-4.21.0.tgz#d57cb706d49623d4ac27833f1cbc466b668eb915"
integrity sha512-VqcNGcj/Id5ZT1LZ/cfihi3ttTn+NJmkli2eZADigjq29qTlWi/hAQ43t/VLPq8+UX06FCEx3ByOYet6ZFblng==
dependencies:
accepts "~1.3.8"
array-flatten "1.1.1"
body-parser "1.20.3"
content-disposition "0.5.4"
content-type "~1.0.4"
cookie "0.6.0"
cookie-signature "1.0.6"
debug "2.6.9"
depd "2.0.0"
encodeurl "~2.0.0"
escape-html "~1.0.3"
etag "~1.8.1"
finalhandler "1.3.1"
fresh "0.5.2"
http-errors "2.0.0"
merge-descriptors "1.0.3"
methods "~1.1.2"
on-finished "2.4.1"
parseurl "~1.3.3"
path-to-regexp "0.1.10"
proxy-addr "~2.0.7"
qs "6.13.0"
range-parser "~1.2.1"
safe-buffer "5.2.1"
send "0.19.0"
serve-static "1.16.2"
setprototypeof "1.2.0"
statuses "2.0.1"
type-is "~1.6.18"
utils-merge "1.0.1"
vary "~1.1.2"
extend@^3.0.2, extend@~3.0.2:
version "3.0.2"
resolved "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz"
@ -1599,6 +1714,19 @@ finalhandler@1.2.0:
statuses "2.0.1"
unpipe "~1.0.0"
finalhandler@1.3.1:
version "1.3.1"
resolved "https://registry.yarnpkg.com/finalhandler/-/finalhandler-1.3.1.tgz#0c575f1d1d324ddd1da35ad7ece3df7d19088019"
integrity sha512-6BN9trH7bp3qvnrRyzsBz+g3lZxTNZTbVO2EV1CS0WIcDbawYVdYvGflME/9QP0h0pYlCDBCTjYa9nZzMDpyxQ==
dependencies:
debug "2.6.9"
encodeurl "~2.0.0"
escape-html "~1.0.3"
on-finished "2.4.1"
parseurl "~1.3.3"
statuses "2.0.1"
unpipe "~1.0.0"
find-up@5.0.0:
version "5.0.0"
resolved "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz"
@ -1923,6 +2051,17 @@ html-to-text@^8.0.0, html-to-text@^8.2.0:
minimist "^1.2.6"
selderee "^0.6.0"
html-to-text@^9.0.5:
version "9.0.5"
resolved "https://registry.yarnpkg.com/html-to-text/-/html-to-text-9.0.5.tgz#6149a0f618ae7a0db8085dca9bbf96d32bb8368d"
integrity sha512-qY60FjREgVZL03vJU6IfMV4GDjGBIoOyvuFdpBDIX9yTlDw0TjxVBQp+P8NvpdIXNJvfWBTNul7fsAQJq2FNpg==
dependencies:
"@selderee/plugin-htmlparser2" "^0.11.0"
deepmerge "^4.3.1"
dom-serializer "^2.0.0"
htmlparser2 "^8.0.2"
selderee "^0.11.0"
htmlencode@^0.0.4:
version "0.0.4"
resolved "https://registry.npmjs.org/htmlencode/-/htmlencode-0.0.4.tgz"
@ -1938,7 +2077,7 @@ htmlparser2@^6.1.0:
domutils "^2.5.2"
entities "^2.0.0"
htmlparser2@^8.0.0:
htmlparser2@^8.0.0, htmlparser2@^8.0.2:
version "8.0.2"
resolved "https://registry.yarnpkg.com/htmlparser2/-/htmlparser2-8.0.2.tgz#f002151705b383e62433b5cf466f5b716edaec21"
integrity sha512-GYdjWKDkbRLkZ5geuHs5NY1puJ+PXwP7+fHPRz06Eirsb9ugf6d8kkXav6ADhcODhFFPMIXyxkxSuMf3D6NCFA==
@ -1993,6 +2132,14 @@ https-proxy-agent@^5.0.0:
agent-base "6"
debug "4"
https-proxy-agent@^5.0.1:
version "5.0.1"
resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6"
integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==
dependencies:
agent-base "6"
debug "4"
humanize-duration-ts@^2.1.1:
version "2.1.1"
resolved "https://registry.npmjs.org/humanize-duration-ts/-/humanize-duration-ts-2.1.1.tgz"
@ -2344,6 +2491,11 @@ layerr@^0.1.2:
resolved "https://registry.npmjs.org/layerr/-/layerr-0.1.2.tgz"
integrity sha512-ob5kTd9H3S4GOG2nVXyQhOu9O8nBgP555XxWPkJI0tR0JeRilfyTp8WtPdIJHLXBmHMSdEq5+KMxiYABeScsIQ==
leac@^0.6.0:
version "0.6.0"
resolved "https://registry.yarnpkg.com/leac/-/leac-0.6.0.tgz#dcf136e382e666bd2475f44a1096061b70dc0912"
integrity sha512-y+SqErxb8h7nE/fiEX07jsbuhrpO9lL8eca7/Y1nuWV2moNlXhyd59iDGcRf6moVyDMbmTNzL40SUyrFU/yDpg==
levn@^0.4.1:
version "0.4.1"
resolved "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz"
@ -2425,7 +2577,7 @@ long@4.0.0:
resolved "https://registry.yarnpkg.com/long/-/long-4.0.0.tgz#9a7b71cfb7d361a194ea555241c92f7468d5bf28"
integrity sha512-XsP+KhQif4bjX1kbuSiySJFNAehNxgLb6hPRGJ9QsUr8ajHkuXGdrHmFUTUUXhDwVX2R5bY4JNZEwbUiMhV+MA==
lowdb@^1:
lowdb@1, lowdb@^1:
version "1.0.0"
resolved "https://registry.npmjs.org/lowdb/-/lowdb-1.0.0.tgz"
integrity sha512-2+x8esE/Wb9SQ1F9IHaYWfsC9FIecLOPrK4g17FGEayjUWH172H6nwicRovGvSE2CPZouc2MCIqCI7h9d+GftQ==
@ -2436,6 +2588,11 @@ lowdb@^1:
pify "^3.0.0"
steno "^0.4.1"
lru-cache@^10.0.1:
version "10.4.3"
resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-10.4.3.tgz#410fc8a17b70e598013df257c2446b7f3383f119"
integrity sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==
lru-cache@^4.1.5:
version "4.1.5"
resolved "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz"
@ -2630,6 +2787,11 @@ mkdirp@^1.0.3, mkdirp@^1.0.4:
resolved "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz"
integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==
mkdirp@^3.0.1:
version "3.0.1"
resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-3.0.1.tgz#e44e4c5607fb279c168241713cc6e0fea9adcb50"
integrity sha512-+NsyUUAZDmo6YVHzL/stxSu3t9YS1iljliy3BSDrXJ/dkn1KYdmtZODGGjLcc9XLgVVpH4KshHB8XmZgMhaBXg==
mkdirp@~0.5.1:
version "0.5.6"
resolved "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz"
@ -2749,6 +2911,11 @@ node-downloader-helper@^2.1.1:
resolved "https://registry.npmjs.org/node-downloader-helper/-/node-downloader-helper-2.1.1.tgz"
integrity sha512-ouk8MGmJj1gYymbJwi1L8Mr6PdyheJLwfsmyx0KtsvyJ+7Fpf0kBBzM8Gmx8Mt/JBfRWP1PQm6dAGV6x7eNedw==
node-downloader-helper@^2.1.5:
version "2.1.9"
resolved "https://registry.yarnpkg.com/node-downloader-helper/-/node-downloader-helper-2.1.9.tgz#a59ee7276b2bf708bbac2cc5872ad28fc7cd1b0e"
integrity sha512-FSvAol2Z8UP191sZtsUZwHIN0eGoGue3uEXGdWIH5228e9KH1YHXT7fN8Oa33UGf+FbqGTQg3sJfrRGzmVCaJA==
node-fetch@^2.6.7:
version "2.7.0"
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.7.0.tgz#d0f0fa6e3e2dc1d27efcd8ad99d550bda94d187d"
@ -2938,6 +3105,14 @@ parse5@6.0.1:
resolved "https://registry.npmjs.org/parse5/-/parse5-6.0.1.tgz"
integrity sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==
parseley@^0.12.0:
version "0.12.1"
resolved "https://registry.yarnpkg.com/parseley/-/parseley-0.12.1.tgz#4afd561d50215ebe259e3e7a853e62f600683aef"
integrity sha512-e6qHKe3a9HWr0oMRVDTRhKce+bRO8VGQR3NyVwcjwrbhMmFCX9KszEV35+rn4AdilFAq9VPxP/Fe1wC9Qjd2lw==
dependencies:
leac "^0.6.0"
peberminta "^0.9.0"
parseley@^0.7.0:
version "0.7.0"
resolved "https://registry.npmjs.org/parseley/-/parseley-0.7.0.tgz"
@ -2976,6 +3151,11 @@ path-to-regexp@0.1.10:
resolved "https://registry.yarnpkg.com/path-to-regexp/-/path-to-regexp-0.1.10.tgz#67e9108c5c0551b9e5326064387de4763c4d5f8b"
integrity sha512-7lf7qcQidTku0Gu3YDPc8DJ1q7OOucfa/BSsIwjuh56VU7katFvuM8hULfkwB3Fns/rsVF7PwPKVw1sl5KQS9w==
peberminta@^0.9.0:
version "0.9.0"
resolved "https://registry.yarnpkg.com/peberminta/-/peberminta-0.9.0.tgz#8ec9bc0eb84b7d368126e71ce9033501dca2a352"
integrity sha512-XIxfHpEuSJbITd1H3EeQwpcZbTLHc+VVr8ANI9t5sit565tsI4/xK3KWTUFE2e6QiangUkh3B0jihzmGnNrRsQ==
performance-now@^2.1.0:
version "2.1.0"
resolved "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz"
@ -3093,6 +3273,11 @@ postgres@^3.3.1:
resolved "https://registry.npmjs.org/postgres/-/postgres-3.3.2.tgz"
integrity sha512-NaPqFpUC6C7aCQkJXLvuO/3RKNKL4en8opY53YrcXK3//xXra6CZ2qX6290lxuQ1dW1LbRGYCmsawRlCxSBonQ==
postgres@^3.4.1:
version "3.4.4"
resolved "https://registry.yarnpkg.com/postgres/-/postgres-3.4.4.tgz#adbe08dc1fff0dea3559aa4f83ded70a289a6cb8"
integrity sha512-IbyN+9KslkqcXa8AO9fxpk97PA4pzewvpi2B3Dwy9u4zpV32QicaEdgmF3eSQUzdRk7ttDHQejNgAEr4XoeH4A==
prelude-ls@^1.2.1:
version "1.2.1"
resolved "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz"
@ -3338,7 +3523,7 @@ safe-stable-stringify@^2.3.1:
resolved "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz"
integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==
sanitize-html@^2.7.0:
sanitize-html@^2.11.0, sanitize-html@^2.7.0:
version "2.13.0"
resolved "https://registry.yarnpkg.com/sanitize-html/-/sanitize-html-2.13.0.tgz#71aedcdb777897985a4ea1877bf4f895a1170dae"
integrity sha512-Xff91Z+4Mz5QiNSLdLWwjgBDm5b1RU6xBT0+12rapjiaR7SwfRdjw8f+6Rir2MXKLrDicRFHdb51hGOAxmsUIA==
@ -3362,6 +3547,13 @@ seedrandom@^3.0.5:
resolved "https://registry.yarnpkg.com/seedrandom/-/seedrandom-3.0.5.tgz#54edc85c95222525b0c7a6f6b3543d8e0b3aa0a7"
integrity sha512-8OwmbklUNzwezjGInmZ+2clQmExQPvomqjL7LFqOYqtmuxRgQYqOD3mHaU+MvZn5FLUeVxVfQjwLZW/n/JFuqg==
selderee@^0.11.0:
version "0.11.0"
resolved "https://registry.yarnpkg.com/selderee/-/selderee-0.11.0.tgz#6af0c7983e073ad3e35787ffe20cefd9daf0ec8a"
integrity sha512-5TF+l7p4+OsnP8BCCvSyZiSPc4x4//p5uPwK8TCnVPJYRmU2aYKMpOXvw8zM5a5JvuuCGN1jmsMwuU2W02ukfA==
dependencies:
parseley "^0.12.0"
selderee@^0.6.0:
version "0.6.0"
resolved "https://registry.npmjs.org/selderee/-/selderee-0.6.0.tgz"
@ -3446,6 +3638,16 @@ serve-static@1.16.0:
parseurl "~1.3.3"
send "0.18.0"
serve-static@1.16.2:
version "1.16.2"
resolved "https://registry.yarnpkg.com/serve-static/-/serve-static-1.16.2.tgz#b6a5343da47f6bdd2673848bf45754941e803296"
integrity sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==
dependencies:
encodeurl "~2.0.0"
escape-html "~1.0.3"
parseurl "~1.3.3"
send "0.19.0"
set-blocking@^2.0.0:
version "2.0.0"
resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7"