"use strict";var __importDefault=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(exports,"__esModule",{value:!0});exports.metadata=void 0;const error_1=require("@b/utils/error"),fs_1=require("fs"),path_1=__importDefault(require("path")),promise_1=require("mysql2/promise"),validation_1=require("@b/utils/validation"),console_1=require("@b/utils/console");exports.metadata={summary:"Restores the database from a backup file",description:"Restores the database from a specified backup file",operationId:"restoreDatabase",tags:["Admin","Database"],requiresAuth:!0,requestBody:{required:!0,content:{"application/json":{schema:{type:"object",properties:{backupFile:{type:"string",description:"Path to the backup file"}},required:["backupFile"]}}}},responses:{200:{description:"Database restored successfully",content:{"application/json":{schema:{type:"object",properties:{message:{type:"string",description:"Success message"}}}}}},500:{description:"Internal server error"}},permission:"access.database",logModule:"ADMIN_SYS",logTitle:"Database restore"};const checkEnvVariables=()=>{["DB_HOST","DB_USER","DB_NAME"].forEach(e=>{if(!process.env[e])throw(0,error_1.createError)({statusCode:500,message:`Environment variable ${e} is not set`})})},getDbConnection=async()=>{const{DB_HOST:e,DB_USER:t,DB_PASSWORD:a,DB_NAME:s}=process.env;if(!e||!t||!s)throw(0,error_1.createError)({statusCode:500,message:"Database configuration is incomplete"});const r=await(0,promise_1.createConnection)({host:e,user:t,password:a||"",database:s,multipleStatements:!0,connectTimeout:1e4});await r.query("SET GLOBAL max_allowed_packet = 67108864");return r},executeSqlStatements=async(e,t)=>{for(const a of t)try{await e.query(a)}catch(t){if("ECONNRESET"!==t.code)throw t;console_1.logger.error("DATABASE","Connection was reset. Retrying...",t);await new Promise(e=>setTimeout(e,5e3));await executeSqlStatements(e,[a])}},splitSqlFile=e=>e.split(/;\s*$/m).map(e=>e.trim()).filter(e=>e.length>0),dropAndRecreateDatabase=async(e,t)=>{await e.query(`DROP DATABASE IF EXISTS \`${t}\``);await e.query(`CREATE DATABASE \`${t}\``);await e.query(`USE \`${t}\``)};exports.default=async e=>{const{ctx:t}=e;try{null==t||t.step("Validating database configuration");checkEnvVariables();const{backupFile:a}=e.body,{DB_NAME:s}=process.env;if(!a)throw(0,error_1.createError)({statusCode:400,message:"Backup file path is required"});null==t||t.step("Validating backup file");const r=(0,validation_1.sanitizePath)(a),o=path_1.default.resolve(process.cwd(),"backup",r);await fs_1.promises.access(o);null==t||t.step("Reading backup file");const i=await fs_1.promises.readFile(o,"utf8"),n=splitSqlFile(i);null==t||t.step("Connecting to database");const c=await getDbConnection();try{null==t||t.step("Dropping and recreating database");await dropAndRecreateDatabase(c,s);null==t||t.step(`Executing ${n.length} SQL statements`);await executeSqlStatements(c,n);null==t||t.success("Database restored successfully");return{message:"Database restored successfully"}}finally{await c.end()}}catch(e){null==t||t.fail(`Database restore failed: ${e.message}`);throw(0,error_1.createError)({statusCode:500,message:`Error restoring database: ${e.message}`})}};