Shell aliases are useful when you remember them.
The problem starts when your collection grows large enough that you no longer remember:
- the exact alias name
- which aliases already exist
- which one solves a specific problem
- what arguments a command expects
- whether a command is safe to run as-is
At that point, aliases stop being a productivity tool and start becoming another thing you need to memorize.
That is the problem I wanted to solve with cmdpeek.
cmdpeek is an open-source searchable command palette for reusable terminal workflows.
Instead of remembering an exact alias such as:
klo
you can search by what you want to do:
cmdpeek kubernetes logs
The command does not need to match the internal name exactly.
cmdpeek searches across:
title
name
description
labels
command contents
This means a workflow can be discovered using different words, old alias names, technical concepts, or even part of the underlying command.
Aliases optimize commands you remember. cmdpeek helps you discover commands you do not.
Why aliases stop scaling
A small number of aliases is easy to manage:
alias k='kubectl'
alias kgp='kubectl get pods'
alias klo='kubectl logs -f'
But over time, collections often grow into dozens or hundreds of entries covering Kubernetes, Flux, Git, GitHub Actions, AWS, Terraform, local development, troubleshooting, media conversion, and deployment workflows.
The commands may still be useful, but remembering their names becomes difficult.
You may know that you created something to download GitHub Actions logs, force a Flux HelmRelease reconciliation, switch Kubernetes context, inspect Elasticsearch shards, or convert a GIF into MP4.
But you may not remember whether the alias was called:
ghlogs
download-run
gha-debug
flux-force
hr-reconcile
gif2mp4
cmdpeek removes that dependency on exact names.
A command can include rich searchable metadata:
- name: force-reconcile-flux-helmrelease
title: Force Flux HelmRelease reconciliation
description: Select a namespace and HelmRelease, then force Flux to reconcile it with its source.
labels:
- flux
- fluxcd
- helm
- helmrelease
- reconcile
- force
- kubernetes
- gitops
- troubleshooting
That same command can be found with searches such as:
flux force
helm reconcile
gitops troubleshooting
helmrelease
Historical alias names can also remain as labels, so an existing mental shortcut still works without defining a separate shell alias.
Search by intent
The main idea behind cmdpeek is simple:
Search by intent
โ
Select a workflow
โ
Resolve its variables
โ
Review the rendered command
โ
Confirm and execute
The catalog is defined in YAML, making workflows easy to review, version, share, and extend.
A command can include:
- a stable internal name
- a human-readable title
- a detailed description
- searchable labels
- a shell script
- interactive variables
- dynamic selectors generated by commands
For example:
- name: pod-logs
title: Follow Kubernetes pod logs
description: Select a namespace and stream logs from one of its pods
labels:
- kubernetes
- pods
- logs
- troubleshooting
- stream
- klo
run: kubectl logs -f "" -n ""
This workflow can be found through:
pod logs
kubernetes troubleshooting
stream
klo
The exact command name is no longer the only entry point.
Demo: search a large catalog
The interactive catalog supports:
/ Search
โ / โ Navigate
โ / โ Change page
e Open details
Enter Select
q Quit
Searches are ranked across the command metadata.
Multiple terms can be combined:
github logs
production deploy
elasticsearch size
kubernetes context
A result can therefore match because of its title, description, labels, internal name, or script contents.
This is especially useful for commands that are important but not used frequently enough to memorize.
Start with a search directly from the command line
You can also pass search terms directly after cmdpeek:
cmdpeek kubernetes context
cmdpeek github logs
cmdpeek elasticsearch shards
The arguments are joined into an initial search query.
The behavior depends on the number of results:
exact command name โ open that workflow directly
one search result โ open that workflow directly
multiple results โ show the interactive catalog already filtered
no results โ show the catalog with no matching commands
This lets cmdpeek behave like a discoverable alias system.
When you know roughly what you want, you can start with:
cmdpeek elastic
instead of opening the full catalog and typing the filter manually.
Demo: direct search and automatic selection
When a search returns several workflows, cmdpeek opens the filtered list.
When the search returns only one workflow, it skips the list and enters that command directly.
For example:
cmdpeek gif
may directly open a GIF-to-MP4 conversion workflow when it is the only matching command.
This keeps the tool fast when you already know the intent, while preserving discovery when the query is broad.
Interactive variables instead of fragile aliases
Aliases become difficult to maintain when commands need parameters.
A shell alias may work for a fixed command:
alias klo='kubectl logs -f'
But real workflows usually need values such as namespace, pod, environment, branch, file path, HelmRelease, GitHub Actions URL, or commit message.
cmdpeek supports four variable sources:
| Source | Purpose |
|---|---|
input |
Free-form user input |
options |
Static selectable values |
environment |
Initial value loaded from an environment variable |
command |
Options generated by a shell command |
A Kubernetes workflow can generate namespaces dynamically:
variables:
- name: namespace
prompt: Select Kubernetes namespace
source:
type: command
command: >-
kubectl get namespaces
-o jsonpath='{range .items[*]}{.metadata.name}{"\n"}{end}'
A second variable can depend on the first:
- name: pod
prompt: Select pod
source:
type: command
command: >-
kubectl get pods -n ""
-o jsonpath='{range .items[*]}{.metadata.name}{"\n"}{end}'
This turns a command into a guided workflow rather than a string you need to remember and edit manually.
Dynamic selectors
Command-generated variables are especially useful for DevOps workflows.
They can list Kubernetes namespaces, pods, contexts, Flux HelmReleases, Git branches, AWS profiles, files, releases, or environments.
For example, a Flux reconciliation workflow can first list namespaces and then list only the HelmReleases inside the selected namespace:
variables:
- name: namespace
prompt: Select Kubernetes namespace
source:
type: command
command: kubectl get namespaces -o name
- name: helmrelease
prompt: Select Flux HelmRelease
source:
type: command
command: >-
flux get helmreleases
--namespace ""
--no-header
| awk '{print $1}'
The user does not need to remember or type resource names manually.
Preview before execution
Variable values are inserted into the command preview as they are selected.
Long commands and scripts remain scrollable, allowing the final result to be reviewed before execution.
After all variables are resolved, cmdpeek displays the fully rendered command and requires explicit confirmation:
Execute this command?
โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ
โ flux reconcile helmrelease svc-time โ
โ -n devbox-phoenix-2 โ
โ --with-source โ
โ --force โ
โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ
y execute n cancel enter cancel
This is particularly useful for commands involving production environments, deployments, deletes, forced reconciliations, pushes, migrations, or infrastructure changes.
The command remains visible before execution instead of being hidden behind an alias.
Non-interactive mode
Interactive discovery is useful when you do not remember the exact workflow.
But sometimes you already know the command name and want to reuse it from a shell function, a script, CI, documentation, or another tool.
For those cases, cmdpeek also supports non-interactive execution:
cmdpeek \
--no-interactive \
--name gcommit \
--set "message=Add non-interactive execution demo"
Values can be supplied with repeatable --set flags:
cmdpeek \
--no-interactive \
--name deploy \
--set environment=staging \
--set version=1.4.2
The same YAML catalog can therefore support both interactive discovery and scriptable execution.
Demo: reuse a workflow non-interactively
This mode still renders the command and asks for confirmation unless --yes is provided.
A dry run is also available:
cmdpeek \
--no-interactive \
--name gcommit \
--set "message=Preview this commit" \
--dry-run
This prints the final command without executing it.
Local and shared catalogs
By default, cmdpeek looks for:
.cmdpeek.yaml
A local path can be configured through:
export CMDPEEK_CONFIG_FILE="$HOME/.config/cmdpeek/commands.yaml"
Catalogs can also be loaded from GitHub:
export CMDPEEK_CONFIG_GITHUB="company/platform-config:cmdpeek/commands.yaml@main"
For private repositories, authentication can be supplied through:
export CMDPEEK_GITHUB_TOKEN="github_pat_..."
Remote configurations are cached locally and refreshed using GitHub ETags.
This makes it possible to maintain a personal workflow catalog, a repository-specific catalog, a shared team catalog, or a versioned platform engineering catalog.
The YAML file becomes executable documentation for workflows that would otherwise be scattered across aliases, shell history, snippets, and README files.
Example workflows
The same catalog can describe very different tasks.
Analyze GitHub Actions logs
cmdpeek github logs
The workflow can request a GitHub Actions run or job URL, download the logs, extract them, and prepare them for analysis.
Force a Flux HelmRelease reconciliation
cmdpeek flux force
The workflow can interactively select a namespace and HelmRelease before running:
flux reconcile helmrelease <name> \
--namespace <namespace> \
--with-source \
--force
Switch Kubernetes context
cmdpeek kubernetes context
Available contexts can be generated dynamically from the current kubeconfig.
Convert GIF to MP4
cmdpeek gif mp4
The workflow can request input and output paths and execute a consistent ffmpeg conversion.
Run a Git commit workflow
cmdpeek \
--no-interactive \
--name gcommit \
--set "message=Document cmdpeek workflows"
Installation
Homebrew
Linux and macOS:
brew install --cask pierinho13/tools/cmdpeek
Upgrade:
brew update
brew upgrade --cask cmdpeek
GitHub Releases
Precompiled binaries are available through GitHub Releases.
Build from source
git clone https://github.com/pierinho13/cmdpeek.git
cd cmdpeek
go build -o cmdpeek ./cmd/cmdpeek
sudo mv cmdpeek /usr/local/bin/
Quick start
Create .cmdpeek.yaml:
version: 1
shell: bash
commands:
- name: greet
title: Greet a person
description: Print a personalized greeting
labels:
- example
- greeting
- hello
run: |
name=""
echo "Hello, ${name}!"
variables:
- name: name
prompt: Person name
default: world
source:
type: input
Then run:
cmdpeek
Or search directly:
cmdpeek greeting
Why not just use aliases, fzf, or a task runner?
cmdpeek is not intended to replace every shell alias, fuzzy finder, or task runner.
Aliases are still ideal for very short commands you use constantly and remember easily.
Task runners are excellent for repository-defined build and automation tasks.
fzf is excellent for filtering arbitrary streams of text.
The focus of cmdpeek is different:
structured command discovery by intent
+
guided variable resolution
+
live preview
+
safe execution
The searchable metadata belongs to the command model itself.
A workflow is not just a command string. It has a title, description, labels, variables, and execution behavior.
That makes it easier to discover months later, share with other people, and evolve without creating more aliases.
Final thoughts
The main goal of cmdpeek is not simply to execute commands.
The goal is to make useful terminal workflows discoverable.
A command you cannot remember effectively does not exist when you need it.
By searching names, titles, descriptions, labels, and command contents, cmdpeek makes it possible to find workflows using the words you remember at that moment.
That is what makes it different from a large alias file.
Instead of asking:
What did I call that alias?
You can ask:
What do I want to do?
The project is open source:
https://github.com/pierinho13/cmdpeek
Contributions, feedback, workflow examples, documentation improvements, tests, packaging support, and TUI ideas are very welcome.
If youโre interested in this kind of platform engineering work, you can learn more about my experience or get in touch.
Comments