Files
2026-04-30 16:32:00 -07:00

74 lines
2.3 KiB
JavaScript

import { ACCESS_TOKEN, SERVER_URL, SOURCE_ROOM_ID, TARGET_ROOM_ID } from "./conf.js";
import {readFileSync, writeFileSync} from "fs";
async function fetchMatrix(url, options = {}) {
options.headers ||= {};
options.headers.Authorization ||= `Bearer ${ACCESS_TOKEN}`;
url = SERVER_URL + url;
while (true) {
console.debug("fetch", url);
try {
var res = await fetch(url, options);
if (res.status == 429) {
var {retry_after_ms} = await res.json();
} else break;
} catch (error) {
console.error(error);
}
await new Promise(r => setTimeout(r, retry_after_ms || 60000));
}
if (!res.ok) throw new Error(`HTTP ${res.status} ${await res.text()}`);
return res;
}
async function getMatrixEvents(room_id, until_event_id) {
var events = [];
do {
var url = `/_matrix/client/v3/rooms/${encodeURIComponent(room_id)}/messages?dir=b&limit=50`;//use 1000 for initial fill
if (end) url += `&from=${end}`;
var {chunk, end} = await fetchMatrix(url).then(res => res.json());
console.log(`got ${chunk.length}`);
for (let event of chunk) {
if (until_event_id && event.event_id == until_event_id) return events;
events.push(event);
}
} while (end)
return events;
}
async function getNewMatrixEvents(room_id) {
var fn = `last_event_id_${room_id.replace(/[^\w]/g,'')}`;
try {
var last_event_id = readFileSync(fn, "utf8");
} catch (error) {
console.log(error.message);
}
var events = await getMatrixEvents(room_id, last_event_id);
for (let event of events) {
event.hasBeenProcessed = () => writeFileSync(fn, event.event_id);
}
return events;
}
var events = await getNewMatrixEvents(SOURCE_ROOM_ID);
for (let event of events.reverse()) {
if (typeof event.content == "object" && ["m.video","m.audio","m.file"].includes(event.content.msgtype)) {
let event_url = `https://matrix.to/#/${encodeURIComponent(event.room_id)}/${encodeURIComponent(event.event_id)}`;
await fetchMatrix(`/_matrix/client/v3/rooms/${encodeURIComponent(TARGET_ROOM_ID)}/send/m.room.message/${Math.random()}`, {
method: "PUT",
headers: {"Content-Type": "application/json"},
body: JSON.stringify({
msgtype: event.content.msgtype,
filename: event.content.filename || event.content.body,
body: event_url,
info: event.content.info,
url: event.content.url
})
});
}
event.hasBeenProcessed();
}