feat: add file_hash column and related index to files table; refactor Telegram API utilities for improved file handling
This commit is contained in:
+1
-1
@@ -2,6 +2,7 @@ import { findFileByPublicId } from '../db/files';
|
||||
import { formatCreatedAt, getErrorMessage } from '../utils/file';
|
||||
import logger from '../utils/logger';
|
||||
import { checkRateLimit } from '../utils/rateLimit';
|
||||
import { getBot } from '../utils/telegram';
|
||||
|
||||
type RequestWithParams = Request & {
|
||||
params?: {
|
||||
@@ -25,7 +26,6 @@ export const handleFileRedirect = async (req: RequestWithParams): Promise<Respon
|
||||
return Response.json({ error: 'File not found' }, { status: 404 });
|
||||
}
|
||||
|
||||
const { getBot } = await import('../utils/telegram');
|
||||
const bot = getBot();
|
||||
const fileInfo = await bot.telegram.getFile(file.telegramFileId);
|
||||
|
||||
|
||||
+3
-10
@@ -14,18 +14,13 @@ import {
|
||||
getFileType,
|
||||
} from '../utils/file';
|
||||
import logger from '../utils/logger';
|
||||
import { forwardToStorage, getBot } from '../utils/telegram';
|
||||
import { forwardToStorage } from '../utils/telegram';
|
||||
|
||||
type UploadedFile = NewFile & {
|
||||
createdAt: Date;
|
||||
updatedAt: Date;
|
||||
};
|
||||
|
||||
type TelegramFileLookup = {
|
||||
mime_type?: string;
|
||||
file_size?: number;
|
||||
};
|
||||
|
||||
interface JsonUploadPayload {
|
||||
file?: unknown;
|
||||
fileName?: string;
|
||||
@@ -57,8 +52,6 @@ const performUpload = async (
|
||||
await Bun.write(tempPath, fileBuffer);
|
||||
const fileStream = createReadStream(tempPath);
|
||||
const result = await forwardToStorage(fileStream, fileName, getFileType(mimeType, fileName));
|
||||
const bot = getBot();
|
||||
const fileInfo = (await bot.telegram.getFile(result.telegramFileId)) as TelegramFileLookup;
|
||||
|
||||
return {
|
||||
publicId: nanoid(),
|
||||
@@ -67,8 +60,8 @@ const performUpload = async (
|
||||
storageChatId: config.storageChatId,
|
||||
storageMessageId: result.storageMessageId,
|
||||
fileName,
|
||||
mimeType: fileInfo.mime_type || mimeType || 'application/octet-stream',
|
||||
sizeBytes: fileInfo.file_size || fileBuffer.byteLength,
|
||||
mimeType: mimeType || 'application/octet-stream',
|
||||
sizeBytes: fileBuffer.byteLength,
|
||||
fileType: getFileType(mimeType, fileName),
|
||||
uploaderId: 0,
|
||||
fileHash: computeHash(fileBuffer),
|
||||
|
||||
+10
-38
@@ -6,7 +6,6 @@ import { enqueueUpload } from './telegramQueue';
|
||||
const botTokens = Array.from(new Set([config.botToken, ...config.additionalBotTokens]));
|
||||
|
||||
const bots = botTokens.map((token) => new Telegraf(token));
|
||||
const TELEGRAM_API_URL = `https://api.telegram.org/bot${config.botToken}/`;
|
||||
|
||||
let currentBotIndex = 0;
|
||||
|
||||
@@ -69,20 +68,6 @@ interface TelegramFileInfo {
|
||||
file_path: string;
|
||||
}
|
||||
|
||||
interface TelegramGetFileResponse {
|
||||
ok: boolean;
|
||||
description?: string;
|
||||
result: {
|
||||
file_id: string;
|
||||
};
|
||||
}
|
||||
|
||||
interface TelegramGetInfoResponse {
|
||||
ok: boolean;
|
||||
description?: string;
|
||||
result: TelegramFileInfo;
|
||||
}
|
||||
|
||||
interface UploadedTelegramFile {
|
||||
file_id?: string;
|
||||
file_unique_id?: string;
|
||||
@@ -256,32 +241,17 @@ export const forwardMediaGroupToStorage = async (
|
||||
|
||||
export const getFileInfo = async (
|
||||
telegramFileId: string,
|
||||
telegramFileUniqueId: string,
|
||||
): Promise<TelegramFileInfo> => {
|
||||
try {
|
||||
const result = await fetch(`${TELEGRAM_API_URL}getFile`);
|
||||
const data = (await result.json()) as TelegramGetFileResponse;
|
||||
|
||||
if (!data.ok) {
|
||||
throw new Error(data.description || 'Telegram API error');
|
||||
}
|
||||
|
||||
const fileId = data.result.file_id === telegramFileId ? telegramFileId : telegramFileUniqueId;
|
||||
const fileResult = await fetch(`${TELEGRAM_API_URL}getInfo`, {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({ file_id: fileId }),
|
||||
});
|
||||
const fileInfo = (await fileResult.json()) as TelegramGetInfoResponse;
|
||||
|
||||
if (!fileInfo.ok) {
|
||||
throw new Error(fileInfo.description || 'Telegram info error');
|
||||
}
|
||||
const result = await executeWithBotRetry((activeBot) =>
|
||||
activeBot.telegram.getFile(telegramFileId),
|
||||
);
|
||||
|
||||
const fileData = result as unknown as TelegramFileInfo;
|
||||
return {
|
||||
file_size: fileInfo.result.file_size,
|
||||
mime_type: fileInfo.result.mime_type,
|
||||
file_path: fileInfo.result.file_path,
|
||||
file_size: fileData.file_size || 0,
|
||||
mime_type: fileData.mime_type || 'application/octet-stream',
|
||||
file_path: fileData.file_path || '',
|
||||
};
|
||||
} catch (error: unknown) {
|
||||
logger.error('Failed to get file info', {
|
||||
@@ -291,4 +261,6 @@ export const getFileInfo = async (
|
||||
}
|
||||
};
|
||||
|
||||
export const getBot = (): Telegraf => bots[0];
|
||||
export const getBot = (): Telegraf => bots[currentBotIndex];
|
||||
|
||||
export const getCurrentBotIndex = (): number => currentBotIndex;
|
||||
|
||||
Reference in New Issue
Block a user