Skip to content

munesoft/clix

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

@munesoft/clix

Build a CLI in 5 lines. The fastest way to turn a script into a CLI tool.

import { cli } from "@munesoft/clix";

cli({
  greet: (name) => `Hello ${name}`
});
node app.js greet John
# Hello John

Why clix?

Most CLI frameworks require boilerplate setup, config files, and long tutorials before you can run anything. clix takes a different approach: just map command names to functions and you're done.

Feature clix commander yargs oclif
Lines to first command 3 ~15 ~10 ~30+
Zero config
Auto-generated help
Async commands
TypeScript-first ⚠️
ESM + CJS ⚠️
Subcommands
Setup time <2 min ~10 min ~10 min ~30 min

Installation

npm install @munesoft/clix

Quickstart

Create app.js:

import { cli } from "@munesoft/clix";

cli({
  greet: (name) => `Hello ${name}`,
  add:   (a, b) => Number(a) + Number(b),
});

Run it:

node app.js greet Alice    # Hello Alice
node app.js add 5 10       # 15
node app.js --help         # auto-generated help

That's it. No setup. No config. No program.command().argument().action().


Command Examples

Basic commands

cli({
  // String output
  say: (msg) => msg,

  // Math
  add: (a, b) => Number(a) + Number(b),

  // Object output (pretty-printed as JSON)
  info: () => ({ node: process.version, platform: process.platform }),
});

Flags and options

Flags are passed as the last argument to your function:

cli({
  say: (msg, flags) => flags.loud ? msg.toUpperCase() : msg,
});
node app.js say hello           # hello
node app.js say hello --loud    # HELLO
node app.js serve --port=3000   # flags.port === 3000
node app.js serve --port 8080   # flags.port === 8080
node app.js run --debug         # flags.debug === true

Async commands

cli({
  fetch: async (url) => {
    const res = await fetch(url);
    return res.text();
  },

  delay: async (ms) => {
    await new Promise(r => setTimeout(r, Number(ms)));
    return "done";
  },
});

Subcommands

cli({
  // Space-separated subcommands
  "user create": (name) => `Created user: ${name}`,
  "user delete": (id)   => `Deleted user: ${id}`,

  // Or dot/colon notation
  "db.migrate": () => runMigrations(),
  "db:seed":    () => seedDatabase(),
});
node app.js user create Alice
node app.js db.migrate

Command descriptions (shown in --help)

import { cli, describe } from "@munesoft/clix";

cli({
  greet: describe("Greet a user by name", (name) => `Hello ${name}`),
  add:   describe("Add two numbers",      (a, b) => Number(a) + Number(b)),
});

Aliases

cli(
  { greet: (name) => `Hello ${name}` },
  { aliases: { hi: "greet", hello: "greet" } }
);
node app.js hi Alice      # Hello Alice
node app.js hello Alice   # Hello Alice

Global options

cli(commands, {
  name: "my-tool",
  version: "1.0.0",
  description: "My awesome CLI tool",
});
node app.js --version   # 1.0.0
node app.js --help      # shows name, version, description

Custom output formatter

cli(commands, {
  formatter: (result) => {
    if (typeof result === "object") {
      return `Result: ${JSON.stringify(result)}`;
    }
    return String(result);
  },
});

Auto Help Generator

Running --help (or -h) automatically generates clean help from your commands:

my-tool v1.0.0
My awesome CLI tool

Usage:
  node app.js <command> [args] [--flags]

Available commands:
  greet  <name>     Greet a user by name
  add    <a> <b>    Add two numbers
  fetch  <url>

Global flags:
  --help     Show this help message
  --version  Show version number

No registration needed — clix reads your function parameter names automatically.


Error Handling

Unknown commands produce clean, actionable errors:

❌ Unknown command: xyz

Try: node app.js --help

Errors thrown by your commands are caught and displayed without crashing:

❌ Failed to connect: ECONNREFUSED

Add --verbose (or -v) to get the full stack trace.


TypeScript

clix is written in TypeScript and ships full type definitions:

import { cli, CliOptions, CommandMap } from "@munesoft/clix";

const commands: CommandMap = {
  greet: (name: string) => `Hello ${name}`,
};

const options: CliOptions = {
  name: "greeter",
  version: "1.0.0",
};

cli(commands, options);

API Reference

cli(commands, options?)

Bootstraps the CLI. Reads process.argv, matches the command, and executes it.

Parameter Type Description
commands Record<string, Function> Map of command names to handler functions
options.name string CLI display name
options.version string Version string (enables --version)
options.description string Short description for help output
options.aliases Record<string, string> Alias map { alias: "target" }
options.formatter (result) => string Custom output formatter
options.exit (code) => void Custom exit handler

describe(description, fn)

Attaches a description to a command function for display in --help.

cliSync(commands, options?)

Synchronous wrapper around cli() for environments that cannot use top-level await.

parseArgs(argv)

Low-level argument parser. Returns { command, args, flags, raw }.


Use Cases

Scripts — Turn one-off scripts into proper tools:

cli({ backup: () => runBackup(), restore: (file) => runRestore(file) });

Automation — Build internal automation tools in minutes:

cli({
  deploy: async (env) => deploy(env),
  rollback: async (version) => rollback(version),
  status: async () => getStatus(),
});

Dev tools — Package developer utilities:

cli({
  "db seed":     () => seed(),
  "db migrate":  () => migrate(),
  "db reset":    () => reset(),
  lint:          () => runLint(),
  test:          (pattern) => runTests(pattern),
});

License

MIT © Munesoft

Releases

No releases published

Packages

 
 
 

Contributors