diff --git a/scripts/backfill.js b/scripts/backfill.js index 27600f0..c0c440e 100644 --- a/scripts/backfill.js +++ b/scripts/backfill.js @@ -38,12 +38,8 @@ passthrough.select = orm.select /** @type {import("../src/d2m/event-dispatcher")}*/ const eventDispatcher = sync.require("../src/d2m/event-dispatcher") - -const roomID = passthrough.select("channel_room", "room_id", {channel_id: channelID}).pluck().get() -if (!roomID) { - console.error("Please choose a channel that's already bridged.") - process.exit(1) -} +/** @type {import("../src/d2m/actions/create-room")} */ +const createRoom = sync.require("../src/d2m/actions/create-room") ;(async () => { await discord.cloud.connect() @@ -60,6 +56,18 @@ async function event(event) { if (!channel) return const guild_id = event.d.id + let roomID = passthrough.select("channel_room", "room_id", {channel_id: channelID}).pluck().get() + if (!roomID) { + console.log(`Channel #${channel.name} is not bridged yet. Attempting to auto-create...`) + try { + roomID = await createRoom.syncRoom(channelID) + console.log(`Successfully bridged to new room: ${roomID}`) + } catch (e) { + console.error(`Failed to auto-create room: ${e.message}`) + process.exit(1) + } + } + let last = backfill.prepare("SELECT cast(max(message_id) as TEXT) FROM backfill WHERE channel_id = ?").pluck().get(channelID) || "0" console.log(`OK, processing messages for #${channel.name}, continuing from ${last}`) diff --git a/src/d2m/converters/message-to-event.js b/src/d2m/converters/message-to-event.js index 7f77b81..4ec28c2 100644 --- a/src/d2m/converters/message-to-event.js +++ b/src/d2m/converters/message-to-event.js @@ -769,7 +769,21 @@ async function messageToEvent(message, guild, options = {}, di) { // Then scheduled events if (message.content && di?.snow) { for (const match of [...message.content.matchAll(/discord\.gg\/([A-Za-z0-9]+)\?event=([0-9]{18,})/g)]) { // snowflake has minimum 18 because the events feature is at least that old - const invite = await di.snow.invite.getInvite(match[1], {guild_scheduled_event_id: match[2]}) + let invite + try { + invite = await di.snow.invite.getInvite(match[1], {guild_scheduled_event_id: match[2]}) + } catch (e) { + // Skip expired events and invites + if (e.code === 10006 || e.httpStatus === 404) { + console.warn(`[Backfill] Skipped expired scheduled event: ${match[0]}`) + const fallbackBody = `[Expired Scheduled Event: ${match[0]}]` + const fallbackHtml = `
Expired Scheduled Event: ${match[0]}
` + await addTextEvent(fallbackBody, fallbackHtml, "m.notice") + continue + } + throw e + } + const event = invite.guild_scheduled_event if (!event) continue // the event ID provided was not valid diff --git a/src/d2m/converters/message-to-event.test.js b/src/d2m/converters/message-to-event.test.js index 1a73aea..166c3d7 100644 --- a/src/d2m/converters/message-to-event.test.js +++ b/src/d2m/converters/message-to-event.test.js @@ -1538,6 +1538,38 @@ test("message2event: vc invite event renders embed with room link", async t => { ]) }) +test("message2event: expired event invite renders fallback notice", async t => { + const events = await messageToEvent({content: "https://discord.gg/placeholder?event=1381190945646710824"}, {}, {}, { + snow: { + invite: { + getInvite: async () => { + const error = new Error("Unknown Invite") + error.code = 10006 + throw error + } + } + } + }) + t.deepEqual(events, [ + { + $type: "m.room.message", + body: "https://discord.gg/placeholder?event=1381190945646710824", + format: "org.matrix.custom.html", + formatted_body: "https://discord.gg/placeholder?event=1381190945646710824", + "m.mentions": {}, + msgtype: "m.text", + }, + { + $type: "m.room.message", + msgtype: "m.notice", + body: "[Expired Scheduled Event: discord.gg/placeholder?event=1381190945646710824]", + format: "org.matrix.custom.html", + formatted_body: "
Expired Scheduled Event: discord.gg/placeholder?event=1381190945646710824
", + "m.mentions": {} + } + ]) +}) + test("message2event: channel links are converted even inside lists (parser post-processer descends into list items)", async t => { let called = 0 const events = await messageToEvent({ diff --git a/test/test.js b/test/test.js index e05b687..ee8c333 100644 --- a/test/test.js +++ b/test/test.js @@ -13,7 +13,10 @@ const {green} = require("ansi-colors") const passthrough = require("../src/passthrough") const db = new sqlite(":memory:") -const {reg} = require("../src/matrix/read-registration") +const readReg = require("../src/matrix/read-registration") +readReg.reg = readReg.getTemplateRegistration("cadence.moe") +const {reg} = readReg +reg.url = "http://localhost:6693" reg.ooye.discord_token = "Njg0MjgwMTkyNTUzODQ0NzQ3.Xl3zlw.baby" reg.ooye.server_origin = "https://matrix.cadence.moe" // so that tests will pass even when hard-coded reg.ooye.server_name = "cadence.moe"