Dynamic and CLI-friendly Bash scripting framework
See the codeBashTab is a Bash scripting framework that makes shell development feel like a modern CLI platform. Command scripts, argument parsing, autocompletion, module loading, and interactive fzf previews — all in pure Bash.

No install needed — the live demo boots Alpine Linux with BashTab pre-installed, running entirely in your browser via v86 (x86 emulation in WebAssembly). Demo source: evagreendev/BashTabDemo.
./setup # one-time: initialise submodules, build Fig specs
source ./activate # load BashTab into your shell
bu # list commands
bu new-module --name myapp # scaffold a module
Add this to your ~/.bashrc to load BashTab automatically:
source /path/to/BashTab/activate
Each clip starts in an activated shell. Expand a topic to watch a focused walkthrough; setup and activation are cut from every recording.
Query TSV directly with --from, complete fields from its header, or pipe bu import-tsv into a query. Use numeric JSON records for grouped averages. CSV and JSONL are supported too (CSV requires jc).

The same records become a table on a terminal or JSONL in a pipe. Complete comma-separated fields, group and filter records, then render double-border or Markdown tables.

Build a where expression interactively, then project a few columns with a readable select name, verb, module list.

Completion uses declared stream formats and required fields. bu validate-pipeline checks known field references without executing the pipeline; bu get-shape runs a producer to inspect its observed field types.

The included devbox host loads gitshelf as a library. Inspect module precedence and Git state, discover commands with their owning modules, and open the library's help. Try it with source ./activate --example devbox in a fresh shell.

An opt-in Alt+T selector previews a registered timeout wrapper and its automatically derived inverse. Unwrapping restores the original command before it runs. See the recording setup for the registration and binding.



Demo coverage and recording guide documents the feature audit, commit history, and regeneration commands.
bu where, bu select, bu sort, bu distinct-object, bu format-table, bu out-default, ...bu query-object — SQL in one command: where, group-by, agg, having, select, distinct, order-by, first in any order--from and import-csv / import-tsv / import-json / import-jsonl, with inferred field completionbu validate-pipeline, and bu get-shapebu get-command | bu select <TAB> suggests the producer's fieldsbu query-object is a fully interactive DSL — it completes clause keywords, field names (from pipeline analysis), binary operators, distinct field values (via tab-execute), and and/or connectors as you type.
BU_MODULE_LIST — semicolon-separated list of name:version:preinit_path entriesbu new-module --name myapp — scaffold a module with activate / module script / preinit callback / commands directorybu get-module — inspect module precedence, version, Git branch, and dirty statebu get-command — attribute commands to modules and inspect shadowed definitionsbu_parse_multiselect — named flags with -h|--help)# _FLAG syntaxbu_parse_positional — positional args with --enum, --hint, --as-if completionbu_scope_push_function / bu_scope_pop_function) ensures cleanups runsource with --__bu-once prevents redundant re-sourcingbu_exit_handler_setup catches unexpected exitsBashTab can use Fig completion specs as a fallback when no native bash completion exists (715+ CLIs).
Setup (handled automatically by ./setup):
git submodule update --init fig_specs
cd fig_specs && pnpm install --ignore-workspace && pnpm build && node ../fig_convert_to_json.mjs
What you get:
bu get-fig-status — see which commands on your PATH are coveredbu get-fig-status --useful — commands on PATH that lack bash completions<TAB> on an unknown command checks the Fig specsbu get-help — list help topics with module provenancebu get-help <topic> — rendered topic pages with SEE ALSO back-references--help on any command is generated from its parser definition (options, enums, examples)v2026.08.15, v2026.08.15.1 for same-day) — never a hand-picked semver./release.sh cuts + pushes the tag and opens a GitHub Releasebu get-version reports the active release (v2026.08.15-3-g1f4ae9c)Every built-in command — bu new-command, bu import-environment, bu get-command — is a Bash script generated from the same template you use. The framework eats its own dogfood.
BashTab is not:
import/load — use source and BU_MODULE_LIST)coproc, mapfile)Shell
99.1%
Dynamic and CLI-friendly Bash scripting framework
See the codeBashTab is a Bash scripting framework that makes shell development feel like a modern CLI platform. Command scripts, argument parsing, autocompletion, module loading, and interactive fzf previews — all in pure Bash.

No install needed — the live demo boots Alpine Linux with BashTab pre-installed, running entirely in your browser via v86 (x86 emulation in WebAssembly). Demo source: evagreendev/BashTabDemo.
./setup # one-time: initialise submodules, build Fig specs
source ./activate # load BashTab into your shell
bu # list commands
bu new-module --name myapp # scaffold a module
Add this to your ~/.bashrc to load BashTab automatically:
source /path/to/BashTab/activate
Each clip starts in an activated shell. Expand a topic to watch a focused walkthrough; setup and activation are cut from every recording.
Query TSV directly with --from, complete fields from its header, or pipe bu import-tsv into a query. Use numeric JSON records for grouped averages. CSV and JSONL are supported too (CSV requires jc).

The same records become a table on a terminal or JSONL in a pipe. Complete comma-separated fields, group and filter records, then render double-border or Markdown tables.

Build a where expression interactively, then project a few columns with a readable select name, verb, module list.

Completion uses declared stream formats and required fields. bu validate-pipeline checks known field references without executing the pipeline; bu get-shape runs a producer to inspect its observed field types.

The included devbox host loads gitshelf as a library. Inspect module precedence and Git state, discover commands with their owning modules, and open the library's help. Try it with source ./activate --example devbox in a fresh shell.

An opt-in Alt+T selector previews a registered timeout wrapper and its automatically derived inverse. Unwrapping restores the original command before it runs. See the recording setup for the registration and binding.



Demo coverage and recording guide documents the feature audit, commit history, and regeneration commands.
bu where, bu select, bu sort, bu distinct-object, bu format-table, bu out-default, ...bu query-object — SQL in one command: where, group-by, agg, having, select, distinct, order-by, first in any order--from and import-csv / import-tsv / import-json / import-jsonl, with inferred field completionbu validate-pipeline, and bu get-shapebu get-command | bu select <TAB> suggests the producer's fieldsbu query-object is a fully interactive DSL — it completes clause keywords, field names (from pipeline analysis), binary operators, distinct field values (via tab-execute), and and/or connectors as you type.
BU_MODULE_LIST — semicolon-separated list of name:version:preinit_path entriesbu new-module --name myapp — scaffold a module with activate / module script / preinit callback / commands directorybu get-module — inspect module precedence, version, Git branch, and dirty statebu get-command — attribute commands to modules and inspect shadowed definitionsbu_parse_multiselect — named flags with -h|--help)# _FLAG syntaxbu_parse_positional — positional args with --enum, --hint, --as-if completionbu_scope_push_function / bu_scope_pop_function) ensures cleanups runsource with --__bu-once prevents redundant re-sourcingbu_exit_handler_setup catches unexpected exitsBashTab can use Fig completion specs as a fallback when no native bash completion exists (715+ CLIs).
Setup (handled automatically by ./setup):
git submodule update --init fig_specs
cd fig_specs && pnpm install --ignore-workspace && pnpm build && node ../fig_convert_to_json.mjs
What you get:
bu get-fig-status — see which commands on your PATH are coveredbu get-fig-status --useful — commands on PATH that lack bash completions<TAB> on an unknown command checks the Fig specsbu get-help — list help topics with module provenancebu get-help <topic> — rendered topic pages with SEE ALSO back-references--help on any command is generated from its parser definition (options, enums, examples)v2026.08.15, v2026.08.15.1 for same-day) — never a hand-picked semver./release.sh cuts + pushes the tag and opens a GitHub Releasebu get-version reports the active release (v2026.08.15-3-g1f4ae9c)Every built-in command — bu new-command, bu import-environment, bu get-command — is a Bash script generated from the same template you use. The framework eats its own dogfood.
BashTab is not:
import/load — use source and BU_MODULE_LIST)coproc, mapfile)Shell
99.1%