48 lines
1.6 KiB
TypeScript
48 lines
1.6 KiB
TypeScript
import { detectMime } from "../media/mime.js";
|
|
import { type SavedMedia, saveMediaBuffer } from "../media/store.js";
|
|
|
|
export type TelegramFileInfo = {
|
|
file_id: string;
|
|
file_unique_id?: string;
|
|
file_size?: number;
|
|
file_path?: string;
|
|
};
|
|
|
|
export async function getTelegramFile(token: string, fileId: string): Promise<TelegramFileInfo> {
|
|
const res = await fetch(
|
|
`https://api.telegram.org/bot${token}/getFile?file_id=${encodeURIComponent(fileId)}`,
|
|
);
|
|
if (!res.ok) {
|
|
throw new Error(`getFile failed: ${res.status} ${res.statusText}`);
|
|
}
|
|
const json = (await res.json()) as { ok: boolean; result?: TelegramFileInfo };
|
|
if (!json.ok || !json.result?.file_path) {
|
|
throw new Error("getFile returned no file_path");
|
|
}
|
|
return json.result;
|
|
}
|
|
|
|
export async function downloadTelegramFile(
|
|
token: string,
|
|
info: TelegramFileInfo,
|
|
maxBytes?: number,
|
|
): Promise<SavedMedia> {
|
|
if (!info.file_path) throw new Error("file_path missing");
|
|
const url = `https://api.telegram.org/file/bot${token}/${info.file_path}`;
|
|
const res = await fetch(url);
|
|
if (!res.ok || !res.body) {
|
|
throw new Error(`Failed to download telegram file: HTTP ${res.status}`);
|
|
}
|
|
const array = Buffer.from(await res.arrayBuffer());
|
|
const mime = await detectMime({
|
|
buffer: array,
|
|
headerMime: res.headers.get("content-type"),
|
|
filePath: info.file_path,
|
|
});
|
|
// save with inbound subdir
|
|
const saved = await saveMediaBuffer(array, mime, "inbound", maxBytes);
|
|
// Ensure extension matches mime if possible
|
|
if (!saved.contentType && mime) saved.contentType = mime;
|
|
return saved;
|
|
}
|