import fs from 'node:fs'; import path from 'node:path'; const LOG_FILE_PATH = process.env.LOG_FILE_PATH || './logs/app.log'; const ENABLE_LOGS = process.env.ENABLE_SERVER_LOGS !== 'false'; export type LogLevel = 'info' | 'warn' | 'error'; export interface LogEntry { timestamp: string; level: LogLevel; message: string; meta?: Record; } function ensureLogDirectory() { const logDir = path.dirname(LOG_FILE_PATH); if (!fs.existsSync(logDir)) { fs.mkdirSync(logDir, { recursive: true }); } } function formatLogEntry(entry: LogEntry): string { const metaStr = entry.meta ? ` | ${JSON.stringify(entry.meta)}` : ''; return `[${entry.timestamp}] [${entry.level.toUpperCase()}] ${entry.message}${metaStr}\n`; } export function writeLog(level: LogLevel, message: string, meta?: Record) { if (!ENABLE_LOGS) return; try { ensureLogDirectory(); const entry: LogEntry = { timestamp: new Date().toISOString(), level, message, meta, }; const logLine = formatLogEntry(entry); fs.appendFileSync(LOG_FILE_PATH, logLine, 'utf8'); if (process.env.NODE_ENV === 'development') { console.log(`[${level.toUpperCase()}]`, message, meta || ''); } } catch (error) { console.error('Failed to write log:', error); console.log(`[${level.toUpperCase()}]`, message, meta || ''); } } export async function logServerAction( level: LogLevel, message: string, meta?: Record ): Promise { return new Promise((resolve) => { writeLog(level, message, meta); resolve(); }); } export const logInfo = (message: string, meta?: Record) => writeLog('info', message, meta); export const logWarn = (message: string, meta?: Record) => writeLog('warn', message, meta); export const logError = (message: string, meta?: Record) => writeLog('error', message, meta);