#!/usr/bin/env node import { Command } from "commander"; // NOTE: this changed in node 18 to be node:url for...stupid import { fileURLToPath } from "url"; import { glob } from "../lib/tooling.js"; import path from "path"; import assert from "assert"; import fs from "fs"; // BUG: this will load the commands but most of them assume the root const __filename = fileURLToPath(import.meta.url); const { dir } = path.parse(__filename); let __dirname = path.resolve(dir); // now even exec commands will know where the project root is process.env['PROJECT_ROOT'] = path.resolve(path.join(__dirname, "..")); const program = new Command(); // remember that glob doesn't like windows \ const command_dir = path.resolve(path.join(__dirname, "..", "commands")); if(!fs.existsSync(command_dir)) { console.error("ERROR: there is no command directory at", command_dir); process.exit(1); } program .name("bando") .description("Command runner for the bando project.") .version("0.1.0"); // only load the commands modules if any options are given if(process.argv.length === 2) { console.log("COMMANDS:\n"); const commands = glob(`${command_dir}/*.js`).map(cmd => { console.log(path.parse(cmd).name); }); if(process.platform === "win32") { console.log("\nUse './bando help' for full help."); } else { console.log("\nUse './bando.js help' for full help."); } } else { try { const name = process.argv[2]; const command = path.join(command_dir, `${name}.js`); if(fs.existsSync(command)) { const mod = await import(`file://${command}`); assert(mod.description, `export const description missing in ${command}`); assert(mod.main, `export const main missing in ${command}`); const build = program.command(name) .description(mod.description) .action(mod.main); if(mod.options) { mod.options.forEach(opt => build.option(...opt)); } if(mod.required) { mod.required.forEach(opt => build.requiredOption(...opt)); } if(mod.argument) { build.argument(...mod.argument); } } } catch(error) { console.log(error, `Loading file ${process.argv[2]}`); } } try { program.parse(); } catch(error) { console.log("------------- ERROR, here's the stack trace."); console.error(error.stack); process.exit(1); }