import Surreal, { StringRecordId } from "surrealdb"; import { logger } from "../logger"; export type { QueryResult } from "surrealdb"; try { if (document || window) { throw new Error("SurrealDB needs a NodeJS environment to run."); } } catch (err) {} const CONFIG = { url: process.env.SURREAL_URL ?? "", user: process.env.SURREAL_USER ?? "", pass: process.env.SURREAL_PASS ?? "", ns: process.env.SURREAL_NS ?? "", db: process.env.SURREAL_DB ?? "", } as const; const db = new Surreal(); async function connectDB() { try { await db.connect(`http://${CONFIG.url}/rpc`); await db.use({ namespace: CONFIG.ns, database: CONFIG.db }); await authenticateDB(); return true; } catch (error) { logger.error("Error connecting to SurrealDB:", error); return false; } } async function authenticateDB() { try { await db.signin({ username: CONFIG.user, password: CONFIG.pass }); logger.info("🔑 Successfully authenticated with SurrealDB"); return true; } catch (error) { logger.warn("❌ Authentication failed:"); logger.error(error); return false; } } async function ensureAuthenticated() { try { await db.query("RETURN 1"); } catch (error: any) { if (error.status === 401) { logger.warn("⚠️ SurrealDB Auth token expired. Attempting reconnection..."); try { // Full reconnection instead of just re-authentication await db.close(); const success = await connectDB(); if (success) { logger.info("✅ Successfully reconnected to database"); } else { logger.error("❌ Failed to reconnect to database"); } } catch (reconnectError) { logger.error("❌ Reconnection failed:", reconnectError); } } else { logger.error("Unexpected database error:", error); } } } // 1 minute const CHECK_INTERVAL = 60 * 1000; let intervalId: NodeJS.Timeout; async function initializeDB() { const success = await connectDB(); if (success) { // Only start the interval if initial connection was successful intervalId = setInterval(ensureAuthenticated, CHECK_INTERVAL); } else { logger.error("Failed to initialize database connection"); // Optionally implement retry logic here } } export function cleanup() { if (intervalId) { clearInterval(intervalId); } return db.close(); } await initializeDB(); export const surreal = db as Surreal; export function parseToRID(idStr: string) { return new StringRecordId(idStr); } process.on("SIGTERM", cleanup); process.on("SIGINT", cleanup);