@expressots/cli
Version:
Expressots CLI - modern, fast, lightweight nodejs web framework (@cli)
238 lines (237 loc) • 8.11 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 (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.runCommand = exports.prodCommand = exports.buildCommand = exports.devCommand = void 0;
const child_process_1 = require("child_process");
const fs_1 = require("fs");
const os_1 = __importDefault(require("os"));
const path_1 = __importStar(require("path"));
const cli_ui_1 = require("../utils/cli-ui");
const compiler_1 = __importDefault(require("../utils/compiler"));
/**
* Helper function to load and extract outDir from tsconfig.build.json
*/
function getOutDir() {
const tsconfigBuildPath = (0, path_1.join)(process.cwd(), "tsconfig.build.json");
if (!(0, fs_1.existsSync)(tsconfigBuildPath)) {
(0, cli_ui_1.printError)("Cannot find tsconfig.build.json. Please create one in the root directory", "tsconfig-build-path");
process.exit(1);
}
const tsconfig = JSON.parse((0, fs_1.readFileSync)(tsconfigBuildPath, "utf-8"));
const outDir = tsconfig.compilerOptions.outDir;
if (!outDir) {
(0, cli_ui_1.printError)("Cannot find outDir in tsconfig.build.json. Please provide an outDir.", "tsconfig-build-path");
process.exit(1);
}
if (!(0, fs_1.existsSync)(outDir)) {
(0, fs_1.mkdirSync)(outDir, { recursive: true });
(0, cli_ui_1.printSuccess)(`Created outDir: ${outDir}`, "outdir-creation");
}
return outDir;
}
/**
* Load the configuration from the compiler
* @param compiler The compiler to load the configuration from
* @returns The configuration
*/
async function opinionatedConfig() {
const { entryPoint } = await compiler_1.default.loadConfig();
const config = [
"--watch",
"-r",
"tsconfig-paths/register",
`./src/${entryPoint}.ts`,
];
return config;
}
/**
* Load the configuration from the compiler
* @param compiler The compiler to load the configuration from
* @returns The configuration
*/
async function nonOpinionatedConfig() {
const { entryPoint } = await compiler_1.default.loadConfig();
const config = ["--watch", `./src/${entryPoint}.ts`];
return config;
}
/**
* Dev command module
* @type {CommandModule<object, object>}
* @returns The command module
*/
exports.devCommand = {
command: "dev",
describe: "Start development server.",
handler: async () => {
await (0, exports.runCommand)({ command: "dev" });
},
};
/**
* Build command module
* @type {CommandModule<object, object>}
* @returns The command module
*/
exports.buildCommand = {
command: "build",
describe: "Build the project.",
handler: async () => {
await (0, exports.runCommand)({ command: "build" });
},
};
/**
* Prod command module
* @type {CommandModule<object, object>}
* @returns The command module
*/
exports.prodCommand = {
command: "prod",
describe: "Run in production mode.",
handler: async () => {
await (0, exports.runCommand)({ command: "prod" });
},
};
/**
* Helper function to execute a command
* @param command The command to execute
* @param args The arguments to pass to the command
* @param cwd The current working directory to execute the command in
* @returns A promise that resolves when the command completes successfully
*/
function execCmd(command, args, cwd = process.cwd()) {
return new Promise((resolve, reject) => {
const proc = (0, child_process_1.spawn)(command, args, {
stdio: "inherit",
shell: true,
cwd,
});
proc.on("close", (code) => {
if (code === 0) {
resolve();
}
else {
reject(new Error(`Command failed with code ${code}`));
}
});
});
}
/**
* Helper function to clean the dist directory
*/
const cleanDist = async (outDir) => {
await fs_1.promises.rm(outDir, { recursive: true, force: true });
(0, cli_ui_1.printSuccess)(`Clean ${outDir} directory`, "clean-dist");
};
/**
* Helper function to compile TypeScript
*/
const compileTypescript = async () => {
await execCmd("npx", ["tsc", "-p", "tsconfig.build.json"]);
(0, cli_ui_1.printSuccess)("Built successfully", "compile-typescript");
};
/**
* Helper function to copy files to the dist directory
*/
const copyFiles = async (outDir) => {
const { opinionated } = await compiler_1.default.loadConfig();
let filesToCopy = [];
if (opinionated) {
filesToCopy = [
"./register-path.js",
"tsconfig.build.json",
"package.json",
];
}
else {
filesToCopy = ["tsconfig.json", "package.json"];
}
filesToCopy.forEach((file) => {
fs_1.promises.copyFile(file, (0, path_1.join)(outDir, path_1.default.basename(file)));
});
};
/**
* Helper function to clear the screen
*/
const clearScreen = () => {
const platform = os_1.default.platform();
const command = platform === "win32" ? "cls" : "clear";
(0, child_process_1.spawn)(command, { stdio: "inherit", shell: true });
};
/**
* Helper function to run a command
* @param command The command to run
*/
const runCommand = async ({ command, }) => {
const { opinionated, entryPoint } = await compiler_1.default.loadConfig();
const outDir = getOutDir();
try {
switch (command) {
case "dev":
execCmd("tsx", opinionated
? await opinionatedConfig()
: await nonOpinionatedConfig());
break;
case "build":
if (!outDir) {
(0, cli_ui_1.printError)("Cannot build project. Please provide an outDir in tsconfig.build.json", "build-command");
process.exit(1);
}
await cleanDist(outDir);
await compileTypescript();
await copyFiles(outDir);
break;
case "prod": {
if (!outDir) {
(0, cli_ui_1.printError)("Cannot run in prod mode. Please provide an outDir in tsconfig.build.json", "prod-command");
process.exit(1);
}
let config = [];
if (opinionated) {
config = [
"-r",
`./${outDir}/register-path.js`,
`./${outDir}/src/${entryPoint}.js`,
];
}
else {
config = [`./${outDir}/${entryPoint}.js`];
}
clearScreen();
execCmd("node", config);
break;
}
default:
(0, cli_ui_1.printError)(`Unknown command: `, command);
break;
}
}
catch (error) {
(0, cli_ui_1.printError)("Error executing command:", error.message);
process.exit(1);
}
};
exports.runCommand = runCommand;