Skip to content

Commands

shll v0.0.21 · captured 2026-07-16

-h/--help work on every command; -v/--version at the tool root.

shllmeta-CLI for the sahil87 toolkit

shll — meta-CLI for the sahil87 toolkit. shll composes operations that span every per-tool CLI (hop, wt, fab-kit, run-kit, tu, idea) so you have one entry point for cross-toolkit concerns. Subcommands: shll doctor verify every sahil87 tool is installed, runnable, and wired (read-only) shll install brew install every sahil87 tool that isn't already installed shll update brew update + brew upgrade for shll and every installed sahil87 tool shll uninstall brew uninstall sahil87 tools (a clean-slate repair path) shll changelog show release notes for sahil87 tools (what an update would bring) shll shell-init <shell> emit a single eval-safe shell-init blob for all installed tools shll shell-setup [shell] append the shell-init eval line to your rc file (idempotent) shll version print versions of shll and every installed sahil87 tool shll list list the managed sahil87 tools with install status and repo links Per-tool CLIs continue to work standalone — shll wraps them, it does not replace them.

usage
  • shll [command]
flags
flagtypedescriptioncopy
-v, --versionversion for shll
show raw -h output
shll — meta-CLI for the sahil87 toolkit.

shll composes operations that span every per-tool CLI (hop, wt, fab-kit, run-kit, tu, idea)
so you have one entry point for cross-toolkit concerns.

Subcommands:
  shll doctor                 verify every sahil87 tool is installed, runnable, and wired (read-only)
  shll install                brew install every sahil87 tool that isn't already installed
  shll update                 brew update + brew upgrade for shll and every installed sahil87 tool
  shll uninstall              brew uninstall sahil87 tools (a clean-slate repair path)
  shll changelog              show release notes for sahil87 tools (what an update would bring)
  shll shell-init <shell>     emit a single eval-safe shell-init blob for all installed tools
  shll shell-setup [shell]    append the shell-init eval line to your rc file (idempotent)
  shll version                print versions of shll and every installed sahil87 tool
  shll list                   list the managed sahil87 tools with install status and repo links

Per-tool CLIs continue to work standalone — shll wraps them, it does not replace them.

Usage:
  shll [command]

Available Commands:
  changelog   show release notes for sahil87 tools (what an update would bring)
  doctor      verify every sahil87 tool is installed, runnable, and wired
  install     brew install every sahil87 tool that isn't already installed
  list        list the sahil87 tools shll manages, with install status and repo links
  shell-init  emit composed shell-init for all installed sahil87 tools
  shell-setup append the shll shell-init eval line to your rc file
  uninstall   brew uninstall sahil87 tools (a clean-slate repair path)
  update      brew update + per-tool update for shll and every installed sahil87 tool
  version     print versions of shll and every installed sahil87 tool

Flags:
  -h, --help      help for shll
  -v, --version   version for shll

Use "shll [command] --help" for more information about a command.
shll changelogshow release notes for sahil87 tools (what an update would bring)

Show GitHub release notes for sahil87 tools. With no arguments, shll changelog shows the pending releases for every installed tool (its installed version → the latest release) — "what would an update bring?". Name one or more tools to scope it; add an explicit range with `tool@old..new` to show the releases in `(old, new]` regardless of what is installed. shll changelog all installed tools: installed → latest shll changelog tu one tool: installed → latest shll changelog tu@0.6.2..0.6.4 explicit range (releases in (0.6.2, 0.6.4]) shll changelog tu@0.6.2..0.6.4 hop@0.1.16..0.1.18 Valid tool names are the roster names plus shll itself. Versions are accepted with or without a leading v. Release data is fetched from GitHub, unauthenticated; if a fetch fails the entry degrades to a compare URL and the command still exits 0.

usage
  • shll changelog [tool[@old..new]]... [flags]
show raw -h output
Show GitHub release notes for sahil87 tools.

With no arguments, shll changelog shows the pending releases for every installed
tool (its installed version → the latest release) — "what would an update bring?".
Name one or more tools to scope it; add an explicit range with `tool@old..new`
to show the releases in `(old, new]` regardless of what is installed.

  shll changelog                          all installed tools: installed → latest
  shll changelog tu                       one tool: installed → latest
  shll changelog tu@0.6.2..0.6.4          explicit range (releases in (0.6.2, 0.6.4])
  shll changelog tu@0.6.2..0.6.4 hop@0.1.16..0.1.18

Valid tool names are the roster names plus shll itself. Versions are accepted with
or without a leading v. Release data is fetched from GitHub, unauthenticated; if a
fetch fails the entry degrades to a compare URL and the command still exits 0.

Usage:
  shll changelog [tool[@old..new]]... [flags]

Flags:
  -h, --help   help for changelog
shll doctorverify every sahil87 tool is installed, runnable, and wired

Verify the sahil87 toolkit is correctly installed and wired. For every roster tool, doctor checks that (1) the binary is on PATH, (2) it reports a version (so a half-installed/stale brew link is caught), (3) its Homebrew formula is trusted (so a future 'brew upgrade' won't be refused on Homebrew 6.0+), and (4) — for tools that ship shell integration (wt, tu, hop) — shll's composed shell-init eval block is present in your rc file. Each tool gets one line with an OK / WARN / FAIL marker; non-OK lines carry an actionable suggestion. A missing or non-running binary is FAIL; an installed tool that simply isn't wired into your shell — or whose formula isn't trusted — is WARN (it still works when invoked directly). doctor exits non-zero if ANY tool is FAIL, so it is scriptable in CI. The trust sub-check queries 'brew trust --json=v1' read-only; if your Homebrew is too old to ship 'brew trust' (where trust isn't required anyway), it is skipped silently. doctor is strictly read-only — it never installs, upgrades, trusts, or edits your rc file. Use --json to emit a machine-readable array (one object per tool) instead of the aligned text table; the same checks and the same exit contract apply.

usage
  • shll doctor [flags]
flags
flagtypedescriptioncopy
--jsonemit a machine-readable JSON array instead of the aligned text table
show raw -h output
Verify the sahil87 toolkit is correctly installed and wired. For every roster
tool, doctor checks that (1) the binary is on PATH, (2) it reports a version (so
a half-installed/stale brew link is caught), (3) its Homebrew formula is trusted
(so a future 'brew upgrade' won't be refused on Homebrew 6.0+), and (4) — for
tools that ship shell integration (wt, tu, hop) — shll's composed shell-init eval
block is present in your rc file.

Each tool gets one line with an OK / WARN / FAIL marker; non-OK lines carry an
actionable suggestion. A missing or non-running binary is FAIL; an installed tool
that simply isn't wired into your shell — or whose formula isn't trusted — is
WARN (it still works when invoked directly). doctor exits non-zero if ANY tool is
FAIL, so it is scriptable in CI.

The trust sub-check queries 'brew trust --json=v1' read-only; if your Homebrew is
too old to ship 'brew trust' (where trust isn't required anyway), it is skipped
silently. doctor is strictly read-only — it never installs, upgrades, trusts, or
edits your rc file.

Use --json to emit a machine-readable array (one object per tool) instead of the
aligned text table; the same checks and the same exit contract apply.

Usage:
  shll doctor [flags]

Flags:
  -h, --help   help for doctor
      --json   emit a machine-readable JSON array instead of the aligned text table
shll installbrew install every sahil87 tool that isn't already installed

Install every roster tool that isn't already installed via Homebrew. shll install iterates the roster (`wt`, `idea`, `tu`, `run-kit`, `hop`, `fab-kit`) and runs `brew install sahil87/tap/<formula>` for each one that is missing. Tools that are already installed are skipped silently — the command is idempotent and safe to re-run. Brew's progress output streams directly to your terminal. With no arguments, shll install processes the whole roster as above. Pass one or more tool names to install only that subset (valid targets: wt, idea, tu, run-kit, hop, fab-kit; the legacy alias `rk` still resolves to run-kit) — e.g. `shll install hop wt`. The subset is processed in roster order regardless of the order given; an unknown name is a hard error. Unlike `shll update`, `shll` itself is NOT a valid install target — you cannot brew-install the running orchestrator. By default, shll install records per-formula Homebrew trust before each install — it runs `brew trust --formula sahil87/tap/<formula>` for each tool in the install set first. Homebrew 6.0 makes tap-trust a hard install requirement, and a binary-download formula runs a sandboxed `def install` that requires a real trust record, so this is what lets the install actually proceed. `brew trust` is idempotent, so re-runs stay clean. Pass `--no-trust` to skip the trust step (for users who manage trust themselves). If your Homebrew is too old to ship `brew trust`, the trust step is skipped gracefully and the install proceeds. shll install does NOT upgrade already-installed tools. Use `shll update` for that.

usage
  • shll install [tool...] [flags]
flags
flagtypedescriptioncopy
--dry-runpreview what would run, without making any changes
--no-trustskip recording per-formula Homebrew trust before installing (manage trust yourself)
show raw -h output
Install every roster tool that isn't already installed via Homebrew.

shll install iterates the roster (`wt`, `idea`, `tu`, `run-kit`, `hop`, `fab-kit`)
and runs `brew install sahil87/tap/<formula>` for each one that is missing.
Tools that are already installed are skipped silently — the command is
idempotent and safe to re-run. Brew's progress output streams directly to
your terminal.

With no arguments, shll install processes the whole roster as above. Pass one or
more tool names to install only that subset (valid targets: wt, idea, tu, run-kit,
hop, fab-kit; the legacy alias `rk` still resolves to run-kit) — e.g.
`shll install hop wt`. The subset is processed in roster order
regardless of the order given; an unknown name is a hard error. Unlike
`shll update`, `shll` itself is NOT a valid install target — you cannot
brew-install the running orchestrator.

By default, shll install records per-formula Homebrew trust before each install —
it runs `brew trust --formula sahil87/tap/<formula>` for each tool in the
install set first. Homebrew 6.0 makes tap-trust a hard install requirement, and a
binary-download formula runs a sandboxed `def install` that requires a real
trust record, so this is what lets the install actually proceed. `brew trust` is
idempotent, so re-runs stay clean. Pass `--no-trust` to skip the trust step
(for users who manage trust themselves). If your Homebrew is too old to ship
`brew trust`, the trust step is skipped gracefully and the install proceeds.

shll install does NOT upgrade already-installed tools. Use `shll update`
for that.

Usage:
  shll install [tool...] [flags]

Flags:
      --dry-run    preview what would run, without making any changes
  -h, --help       help for install
      --no-trust   skip recording per-formula Homebrew trust before installing (manage trust yourself)
shll listlist the sahil87 tools shll manages, with install status and repo links

List the sahil87 toolkit roster shll manages — one row per tool with an install-status indicator, a one-line description, and its GitHub repo URL. Install status reuses the same PATH probe as `shll version` (`<tool> --version`, any error means missing) — install-mechanism agnostic, not a Homebrew check. A missing tool is shown as missing, never an error: `shll list` always exits 0. Default output is a column-aligned table (with color when writing to a terminal). Pass --json for a plain JSON array suitable for scripting (`shll list --json | jq`).

usage
  • shll list [flags]
flags
flagtypedescriptioncopy
--jsonemit the roster as a JSON array (no color, for scripting)
show raw -h output
List the sahil87 toolkit roster shll manages — one row per tool with an
install-status indicator, a one-line description, and its GitHub repo URL.

Install status reuses the same PATH probe as `shll version` (`<tool> --version`,
any error means missing) — install-mechanism agnostic, not a Homebrew check. A
missing tool is shown as missing, never an error: `shll list` always exits 0.

Default output is a column-aligned table (with color when writing to a terminal).
Pass --json for a plain JSON array suitable for scripting (`shll list --json | jq`).

Usage:
  shll list [flags]

Flags:
  -h, --help   help for list
      --json   emit the roster as a JSON array (no color, for scripting)
shll shell-initemit composed shell-init for all installed sahil87 tools

Emit a single concatenated shell-init blob for every installed sahil87 tool that exposes shell integration. Today, tu, hop, and wt are the roster tools with shell integration. The output is eval-safe: missing tools produce no output, errors go to stderr, and stdout is shell code only. Use: eval "$(shll shell-init zsh)" # in your ~/.zshrc eval "$(shll shell-init bash)" # in your ~/.bashrc

usage
  • shll shell-init <shell> [flags]
show raw -h output
Emit a single concatenated shell-init blob for every installed sahil87 tool
that exposes shell integration.

Today, tu, hop, and wt are the roster tools with shell integration. The output
is eval-safe: missing tools produce no output, errors go to stderr, and stdout
is shell code only.

Use:  eval "$(shll shell-init zsh)"   # in your ~/.zshrc
      eval "$(shll shell-init bash)"  # in your ~/.bashrc

Usage:
  shll shell-init <shell> [flags]

Flags:
  -h, --help   help for shell-init
shll shell-setupappend the shll shell-init eval line to your rc file

Append a sentinel-wrapped eval block that wires shll shell-init into your shell rc file. Idempotent — re-running is a no-op when the block is already present. Plain O_APPEND so dotfile-manager symlinks are preserved. Also available under the legacy alias `shll shell-install` (unchanged behavior). Modes: shll shell-setup [shell] install the block (default mode) shll shell-setup --print [shell] print the block to stdout, do not modify shll shell-setup --uninstall [shell] remove the block from the rc file shell-setup is pure rc-wiring — it maintains only the `eval "$(shll shell-init <shell>)"` line and touches no Homebrew state. (Tap trust is established by `shll install`, which trusts each formula it installs; see `shll install --help`.) When [shell] is omitted, shll infers it from $SHELL. Supported shells: zsh, bash. By default, the rc file path is derived per shell: zsh → ${ZDOTDIR:-$HOME}/.zshrc bash → $HOME/.bash_profile (macOS) or $HOME/.bashrc (Linux) Use --rc-file <path> to override derivation entirely.

usage
  • shll shell-setup [shell] [flags]
flags
flagtypedescriptioncopy
--printprint the block to stdout, do not modify any file
--rc-filestringoverride the rc file path (escape hatch for non-standard layouts)
--uninstallremove the shll-managed block from the rc file
show raw -h output
Append a sentinel-wrapped eval block that wires shll shell-init into your
shell rc file. Idempotent — re-running is a no-op when the block is already
present. Plain O_APPEND so dotfile-manager symlinks are preserved.

Also available under the legacy alias `shll shell-install` (unchanged behavior).

Modes:
  shll shell-setup [shell]            install the block (default mode)
  shll shell-setup --print [shell]    print the block to stdout, do not modify
  shll shell-setup --uninstall [shell] remove the block from the rc file

shell-setup is pure rc-wiring — it maintains only the
`eval "$(shll shell-init <shell>)"` line and touches no Homebrew state.
(Tap trust is established by `shll install`, which trusts each formula it
installs; see `shll install --help`.)

When [shell] is omitted, shll infers it from $SHELL. Supported shells: zsh, bash.

By default, the rc file path is derived per shell:
  zsh   → ${ZDOTDIR:-$HOME}/.zshrc
  bash  → $HOME/.bash_profile (macOS) or $HOME/.bashrc (Linux)

Use --rc-file <path> to override derivation entirely.

Usage:
  shll shell-setup [shell] [flags]

Aliases:
  shell-setup, shell-install

Flags:
  -h, --help             help for shell-setup
      --print            print the block to stdout, do not modify any file
      --rc-file string   override the rc file path (escape hatch for non-standard layouts)
      --uninstall        remove the shll-managed block from the rc file
shll uninstallbrew uninstall sahil87 tools (a clean-slate repair path)

Uninstall sahil87 toolkit tools via Homebrew — the clean-slate repair path that pairs with `shll install`. With no arguments, shll uninstall removes every INSTALLED roster tool (`wt`, `idea`, `tu`, `run-kit`, `hop`, `fab-kit`) in reverse-roster order (dependents before leaves). Tools that are not installed are skipped silently — uninstall is idempotent and its goal state ("gone") is a success even when a tool was already absent. shll itself is NOT part of the no-args sweep. Pass one or more tool names to uninstall only that subset (valid targets: shll, wt, idea, tu, run-kit, hop, fab-kit; the legacy alias `rk` still resolves to run-kit). `shll uninstall shll` is legal and explicit-only — it removes shll itself (last, after the roster), and only when shll was installed via brew. The running process keeps working; a farewell note points at the reinstall command. By default shll uninstall prints the removal plan and asks for confirmation (`Proceed? [y/N]`). Pass `--yes` (or `-y`) to skip the prompt. On a non-interactive stdin (a pipe / CI) without `--yes`, shll uninstall refuses rather than removing without consent. Pass `--dry-run` to preview the exact brew commands without removing anything. shll uninstall does NOT untap sahil87/tap, revoke trust, purge tool state/config, or stop running processes (it prints hints for the daemon and rc-file cleanup instead).

usage
  • shll uninstall [tool...] [flags]
flags
flagtypedescriptioncopy
--dry-runpreview what would run, without making any changes
-y, --yesskip the confirmation prompt (assume yes — for scripting)
show raw -h output
Uninstall sahil87 toolkit tools via Homebrew — the clean-slate repair path
that pairs with `shll install`.

With no arguments, shll uninstall removes every INSTALLED roster tool
(`wt`, `idea`, `tu`, `run-kit`, `hop`, `fab-kit`) in reverse-roster order
(dependents before leaves). Tools that are not installed are skipped silently —
uninstall is idempotent and its goal state ("gone") is a success even when a tool
was already absent. shll itself is NOT part of the no-args sweep.

Pass one or more tool names to uninstall only that subset (valid targets: shll, wt,
idea, tu, run-kit, hop, fab-kit; the legacy alias `rk` still resolves to
run-kit). `shll uninstall shll` is legal and explicit-only — it removes shll
itself (last, after the roster), and only when shll was installed via brew. The
running process keeps working; a farewell note points at the reinstall command.

By default shll uninstall prints the removal plan and asks for confirmation
(`Proceed? [y/N]`). Pass `--yes` (or `-y`) to skip the prompt.
On a non-interactive stdin (a pipe / CI) without `--yes`, shll uninstall
refuses rather than removing without consent. Pass `--dry-run` to preview the
exact brew commands without removing anything.

shll uninstall does NOT untap sahil87/tap, revoke trust, purge tool state/config, or
stop running processes (it prints hints for the daemon and rc-file cleanup instead).

Usage:
  shll uninstall [tool...] [flags]

Flags:
      --dry-run   preview what would run, without making any changes
  -h, --help      help for uninstall
  -y, --yes       skip the confirmation prompt (assume yes — for scripting)
shll updatebrew update + per-tool update for shll and every installed sahil87 tool

Update shll itself and every installed sahil87 tool via Homebrew. shll update runs `brew update --quiet` once, then `brew upgrade sahil87/tap/shll` (when shll itself was installed via brew), then delegates to each installed roster tool's own `update` subcommand (with `--skip-brew-update` when the tool advertises it) so each tool's post-upgrade side effects (e.g. rk's daemon restart) are preserved. A roster tool that exposes no `update` is upgraded via `brew upgrade sahil87/tap/<formula>` instead. Uninstalled tools (including shll itself, e.g. on a `go install` dev build) are skipped silently. Brew and per-tool progress output streams directly to your terminal. With no arguments, shll update processes the whole roster as above. Pass one or more tool names to update only that subset (valid targets: shll, wt, idea, tu, run-kit, hop, fab-kit; the legacy alias `rk` still resolves to run-kit) — e.g. `shll update shll` to bump only shll itself, or `shll update hop wt` for a pair. The subset is always processed in roster order regardless of the order given. An unknown name, or a named tool that is not installed, is a hard error (a named tool, unlike the whole-roster sweep, is not silently skipped).

usage
  • shll update [tool...] [flags]
flags
flagtypedescriptioncopy
--dry-runpreview what would run, without making any changes
show raw -h output
Update shll itself and every installed sahil87 tool via Homebrew.

shll update runs `brew update --quiet` once, then `brew upgrade sahil87/tap/shll`
(when shll itself was installed via brew), then delegates to each installed roster
tool's own `update` subcommand (with `--skip-brew-update` when the tool
advertises it) so each tool's post-upgrade side effects (e.g. rk's daemon restart)
are preserved. A roster tool that exposes no `update` is upgraded via
`brew upgrade sahil87/tap/<formula>` instead. Uninstalled tools (including shll
itself, e.g. on a `go install` dev build) are skipped silently. Brew and per-tool
progress output streams directly to your terminal.

With no arguments, shll update processes the whole roster as above. Pass one or
more tool names to update only that subset (valid targets: shll, wt, idea, tu,
run-kit, hop, fab-kit; the legacy alias `rk` still resolves to run-kit) — e.g.
`shll update shll` to bump only shll itself, or
`shll update hop wt` for a pair. The subset is always processed in roster order
regardless of the order given. An unknown name, or a named tool that is not
installed, is a hard error (a named tool, unlike the whole-roster sweep, is not
silently skipped).

Usage:
  shll update [tool...] [flags]

Flags:
      --dry-run   preview what would run, without making any changes
  -h, --help      help for update
shll versionprint versions of shll and every installed sahil87 tool

Print a column-aligned plain-text table showing the version of shll itself plus every roster tool. Uninstalled tools show "not installed". Output is plain text — no colors, no JSON — so it pastes cleanly into bug reports.

usage
  • shll version [flags]
show raw -h output
Print a column-aligned plain-text table showing the version of shll itself
plus every roster tool. Uninstalled tools show "not installed". Output is
plain text — no colors, no JSON — so it pastes cleanly into bug reports.

Usage:
  shll version [flags]

Flags:
  -h, --help   help for version