axiodb
Version:
The Pure JavaScript Alternative to SQLite. Embedded NoSQL database for Node.js with MongoDB-style queries, zero native dependencies, built-in InMemoryCache, and web GUI. Perfect for desktop apps, CLI tools, and embedded systems. No compilation, no platfor
276 lines • 13.1 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
/* eslint-disable @typescript-eslint/no-explicit-any */
const outers_1 = require("outers");
const responseBuilder_helper_1 = __importDefault(require("../../helper/responseBuilder.helper"));
const ZipUnzip_utils_1 = require("../../../utility/ZipUnzip.utils");
const fs_1 = __importDefault(require("fs"));
const path_1 = __importDefault(require("path"));
/**
* Controller class for managing databases in AxioDB.
*
* This class provides methods for retrieving database information,
* creating new databases, and other database management operations.
* It acts as an interface between the API routes and the AxioDB instance.
*/
class DatabaseController {
constructor(AxioDBInstance) {
this.AxioDBInstance = AxioDBInstance;
}
/**
* Retrieves a list of databases from the AxioDB instance.
*
* @returns {Promise<ResponseBuilder>} A Promise that resolves to a ResponseBuilder object
* containing the list of databases with an OK status code and a success message.
*
* @example
* const response = await databaseController.getDatabases();
* // Returns a ResponseBuilder with status 200 and database list
*/
getDatabases() {
return __awaiter(this, void 0, void 0, function* () {
const databases = yield this.AxioDBInstance.getInstanceInfo();
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.OK, "List of Databases", databases === null || databases === void 0 ? void 0 : databases.data);
});
}
/**
* Creates a new database with the specified name.
*
* @param request - The Fastify request object containing the database name in the body
* @returns A ResponseBuilder object containing the status and message of the operation
*
* @throws Will return a conflict response if database already exists
* @throws Will return a bad request response if name is missing, not a string, or empty
* @throws Will return an internal server error response if database creation fails
*/
createDatabase(request) {
return __awaiter(this, void 0, void 0, function* () {
const { name } = request.body;
try {
// check if the database already exists
const exists = yield this.AxioDBInstance.isDatabaseExists(name);
if (exists) {
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.CONFLICT, "Database already exists");
}
// create the database
if (!name) {
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.BAD_REQUEST, "Database name is required");
}
if (typeof name !== "string" || name.trim() === "") {
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.BAD_REQUEST, "Invalid database name");
}
yield this.AxioDBInstance.createDB(name);
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.CREATED, "Database Created", {
Database_Name: name,
});
}
catch (error) {
console.error("Error creating database:", error);
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.INTERNAL_SERVER_ERROR, "Error creating database");
}
});
}
/**
* Deletes a database with the specified name.
*
* @param request - The Fastify request object containing the database name in the body
* @returns A ResponseBuilder object with appropriate status code and message
* - 200 OK if the database is successfully deleted
* - 404 NOT_FOUND if the database does not exist
* - 500 INTERNAL_SERVER_ERROR if an error occurs during deletion
*
* @example
* // Example request body
* {
* "name": "myDatabase"
* }
*/
deleteDatabase(request) {
return __awaiter(this, void 0, void 0, function* () {
const { dbName } = request.query;
try {
// check if the database exists
const exists = yield this.AxioDBInstance.isDatabaseExists(dbName);
if (!exists) {
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.NOT_FOUND, "Database not found");
}
// delete the database
yield this.AxioDBInstance.deleteDatabase(dbName);
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.OK, "Database Deleted", {
Database_Name: dbName,
});
}
catch (error) {
console.error("Error deleting database:", error);
return (0, responseBuilder_helper_1.default)(outers_1.StatusCodes.INTERNAL_SERVER_ERROR, "Error deleting database");
}
});
}
/**
* Exports a database as a compressed tar.gz file and sends it as a downloadable attachment.
*
* @param request - The Fastify request object containing the query parameter 'dbName'
* @param reply - The Fastify reply object used to send the response
* @returns A stream of the compressed database file or an error response
*
* @throws Will return an error response if the export process fails
*
* @remarks
* The method creates a temporary tar.gz file of the specified database directory,
* streams it to the client as a downloadable file, and then deletes the temporary
* file once the stream is closed.
*/
exportDatabase(request, reply) {
return __awaiter(this, void 0, void 0, function* () {
const { dbName } = request.query;
try {
// check if name is provided
if (!dbName) {
return reply.status(400).send({
success: false,
message: "Database name is required",
});
}
// check if the database exists
const exists = yield this.AxioDBInstance.isDatabaseExists(dbName);
if (!exists) {
return reply.status(404).send({
success: false,
message: "Database not found",
});
}
// Get the current database path
const currDatabasePathData = `${this.AxioDBInstance.GetPath}/${dbName}`;
const responseZipTar = yield (0, ZipUnzip_utils_1.tarGzFolder)(currDatabasePathData, `./${dbName}.tar.gz`);
// Check if file was created and get its size
const fs = yield Promise.resolve().then(() => __importStar(require("fs")));
const stats = yield fs.promises.stat(responseZipTar);
if (stats.size === 0) {
yield fs.promises.unlink(responseZipTar);
return reply.status(500).send({
success: false,
message: "Generated export file is empty",
});
}
// Set headers
reply.header("Content-Type", "application/gzip");
reply.header("Content-Disposition", `attachment; filename="${dbName}.tar.gz"`);
reply.header("Content-Length", stats.size.toString());
const stream = fs.createReadStream(responseZipTar);
// Handle stream errors
stream.on("error", (error) => __awaiter(this, void 0, void 0, function* () {
console.error("Stream error:", error);
try {
yield fs.promises.unlink(responseZipTar);
}
catch (unlinkError) {
console.error("Error cleaning up temp file:", unlinkError);
}
}));
// Clean up after stream ends
stream.on("end", () => __awaiter(this, void 0, void 0, function* () {
try {
yield fs.promises.unlink(responseZipTar);
}
catch (unlinkError) {
console.error("Error cleaning up temp file:", unlinkError);
}
}));
return reply.send(stream);
}
catch (error) {
console.error("Error exporting database:", error);
return reply.status(500).send({
success: false,
message: "Error exporting database",
error: error instanceof Error ? error.message : String(error),
});
}
});
}
/**
* Imports a database from an uploaded zip file.
*
* This method handles the upload of a database file, saves it temporarily,
* unzips it to the AxioDB instance path, and cleans up temporary files.
*
* @param request - The Fastify request object containing the uploaded file
* @param reply - The Fastify reply object for sending responses
* @returns A response object indicating success or failure of the import operation
* @throws Will handle errors related to file operations and return appropriate HTTP responses
*/
importDatabase(request, reply) {
return __awaiter(this, void 0, void 0, function* () {
const data = yield request.file(); // single file
if (!data) {
return reply.status(400).send({
success: false,
message: "No file uploaded",
});
}
// Create a Temporary Directory for Uploads
const tempDir = path_1.default.join(__dirname, "uploads");
yield fs_1.default.promises.mkdir(tempDir, { recursive: true });
const savePath = path_1.default.join(tempDir, data.filename);
yield fs_1.default.promises.writeFile(savePath, yield data.toBuffer());
const unzipped = yield (0, ZipUnzip_utils_1.unzipFile)(savePath, this.AxioDBInstance.GetPath);
// Check if unzipping was successful
if (!unzipped) {
return reply.status(500).send({
success: false,
message: "Error unzipping file",
});
}
// Remove the temporary directory
yield fs_1.default.promises.rmdir(tempDir, { recursive: true });
return { message: "File uploaded successfully", file: data.filename };
});
}
}
exports.default = DatabaseController;
//# sourceMappingURL=Databse.controller.js.map