Shell Bling Ubuntu

Shell Bling Ubuntu

23 command-line tools, pinned. Tested on 30 distros every commit. fzf, fish, nvim+LazyVim, the whole modern-CLI starter pack — installed silently while you go get a coffee.

recommended install with wget
wget -qO- https://raw.githubusercontent.com/hiAndrewQuinn/shell-bling-ubuntu/main/install.sh | sh
backup install with curl
curl -fsSL https://raw.githubusercontent.com/hiAndrewQuinn/shell-bling-ubuntu/main/install.sh | sh

wget is preferred because it ships in more base images than curl does — fresh Debian 13, for example, has wget but not curl. Either way the script installs curl itself before it needs to fetch anything else, so they're equivalent once it's running.

Try before you install

Drop into a fresh container with the installer already done — kick the tires without touching your real system.

git clone https://github.com/hiAndrewQuinn/shell-bling-ubuntu
cd shell-bling-ubuntu
make dev DISTRO=ubuntu-24.04   # or debian-13, fedora-44, arch, alpine, …

Want it to stick around so you can ssh in from another terminal? make dev-bg DISTRO=… spins it up in the background with sshd on port 2222. Tear down with make dev-down.

Zero configuration files

Shell Bling never drops a dotfile in your home directory. No .vimrc, no .tmux.conf, no opinionated config.fish. The one exception is the optional LazyVim starter, which is its own scaffolded thing you can ignore or replace.

Where possible we ship zero-config tools that just work — fzf, starship, zoxide, bat, eza, lsd, helix, micro. Where there's a real choice to make, we ship multiple variants side-by-side and let you pick: nvim / vim / hx / micro for editors, lsd + eza for modern ls, xclip + wl-clipboard for the X11/Wayland split. You configure your shell on your own time, in your own way.

What you get

The holy trinity — search, search, search

fzf · fuzzy-search anything; Ctrl+R, Alt+C
fd · fast, friendly find
ripgrep · the fastest grep, as rg

Shells & terminals

fish · autocomplete + syntax highlight, out of the box
starship · fast, minimal, customizable prompt
tmux · terminal multiplexer
kitty · GPU terminal w/ FiraCode Nerd Font
xclip + wl-clipboard · clipboard for X11 and Wayland

Editors

neovim + LazyVim · modern Vim with a curated starter config
vim · the classic, for muscle memory
helix · postmodern, zero-config
micro · friendly terminal editor
bat · cat with syntax highlighting

Files & navigation

zoxide · smarter cd that learns
lsd + eza · modern ls with icons
tree · directories as a tree
rsync · smart copy/sync, locally or over ssh

Dev & git

git + delta · version control + pretty diffs
lazygit · git TUI
gh · GitHub CLI
gopass · modern, pass-compatible password manager

JSON

jq · the de-facto JSON query language — filter, reshape, project. Powerful, opinionated, with its own little DSL to learn.
gron · makes JSON greppable. Flattens any blob into one foo.bar[3].baz = "…" line per leaf so you can rg / grep / fzf through it with tools you already know. Round-trips back to JSON with gron -u.

Other data wrangling

qsv · CSV scalpels (select, search, stats, join, frequency, …)
sqlite3 · a real query, ten minutes from now

Cheatsheets & help

tldr · simplified man pages (tealdeer client)
cheat · interactive cheatsheets

System

htop · process viewer
lnav · interactive log viewer

Where it runs

Tier 1 all 23 tools install at pinned version · smoke test PASS without softening

Docker matrix · automated VM matrix · manual VM end-to-end

Ubuntu22.04, 24.04, 26.04 (jammy, noble, resolute)
Debian12, 13 (bookworm, trixie)
Kali Linuxrolling — tracks Debian sid
Tier 2 all 23 tools land cleanly · file issues if anything breaks

Docker matrix · ~ automated VM matrix (in progress) · manual VM

Fedora40, 41, 42, 43, 44 · dnf
Rocky Linux9, 10 · dnf + EPEL
AlmaLinux9, 10 · dnf + EPEL
CentOS Stream9, 10 · dnf + EPEL
Amazon Linux 2023dnf (no EPEL)
Arch Linuxpacman
Manjaropacman
Alpine Linuxapk (musl) · TTY-only
openSUSE Tumbleweedzypper
Void Linuxxbps
macOSIntel + Apple Silicon · Homebrew
WSL2Ubuntu/Debian under Windows · inherits parent
Tier 3 installs with an explicit "known limitations" notice · expect some friction · may need install-script softening if you hit a new wrinkle

Docker matrix · automated VM · manual VM

openSUSE Leap 15.6all tools land — nothing degraded (glibc 2.38)
Debian 11 bullseye21/23 · helix + neovim (glibc 2.31)
Ubuntu 20.04 focal21/23 · same shape as Debian 11
Rocky 8, AlmaLinux 821/23 · EPEL 8 nvim 0.8.0 fallback
Amazon Linux 221/23 · glibc 2.26 (yum-era)
CentOS 721/23 · glibc 2.17 · vault.centos.org mirror

For legacy-glibc distros, five Rust binaries (bat, fd, eza, lsd, starship) auto-route to their musl variants. You get the same version as on a modern distro, just statically linked.

How we test, in detail

"Tested on 30 distros every commit" is a real claim. Every push to main kicks off a three-layer test pipeline before anything lands. Here's what each layer catches.

Layer 1 — Container matrix (short-cycle gate)

Every commit rebuilds 30 minimal container images — one per supported distro release — and runs the installer end-to-end inside each. Each image starts from the distro's official base, adds only an unprivileged tester user with sudo/wheel/doas, and installs just enough of wget + ca-certificates for the installer to bootstrap itself. Nothing more — we want each container to look like a fresh box, not a curated one.

The container then runs the same wget -qO- … | sh one-liner a real user would, in SHELL_BLING_NONINTERACTIVE=1 mode. A smoke script execs every binary the registry installed (fzf --version, rg --version, nvim --version, fish --version, …) and asserts it returns 0 and prints a sane version. Any non-zero kills the lane.

The Tier 1 / Tier 2 / Tier 3 split above is exactly this matrix's grading rubric — a Tier 1 distro is one where everything passes without softening; a Tier 3 distro is one where the installer detects an ancient glibc and auto-routes a handful of Rust binaries to their musl variants.

Layer 2 — Automated VM matrix (high-fidelity confirmation)

Containers are great for catching "does this command exist?" regressions but they don't have systemd, a real init, a desktop session, or the chsh / usermod / cloud-init interactions a fresh install actually hits. So if the container matrix is green, the pipeline fans out to a second matrix against real cloud-init-provisioned VMs.

Each VM lane boots an upstream cloud image (Debian generic-cloud, Ubuntu cloud-img) seeded with a minimal cloud-init drive that adds the tester user and an SSH key, waits for cloud-init to converge, then runs the same wget one-liner + smoke pass over SSH. Result JSON and the full run log get collected back to the build agent — guests stay credential-free, with no in-guest secrets and no in-guest upload step.

Today the VM matrix covers Debian 12/13 and Ubuntu 22.04/24.04/26.04 on amd64 and arm64. Expanding it to the Tier 2 distros is an in-progress work item.

Layer 3 — Manual VM walkthrough (the human-eyeball pass)

For Tier 1 specifically, every functional change to install.sh also gets a manual run-through on a local libvirt VM with a real desktop session (GNOME on Debian/Ubuntu, the Kali default on Kali). The flow: boot a golden-clean snapshot, paste the wget one-liner, sit through the install, log out, log back in, open a terminal, confirm the new $SHELL, the prompt, the editor picker, and the keybinds all behave. Snapshot back to golden-clean and move on.

This layer is what catches the things automation will never catch — a confusing prompt phrasing, a final message that says the wrong thing, an x-terminal-emulator alternative that didn't take, a desktop session that didn't re-source $SHELL the way the docs claimed it would.

What's not tested

Tier 2 and Tier 3 distros get only the container layer right now. Tier 2 expansion into the VM matrix is a tracked work item. Tier 3 (legacy-glibc) will likely stay container-only — the value there is "the installer doesn't explode on a 2015-era box," not "the modern editor works perfectly under systemd 219."

What the script does

1.
Detect platform. /etc/os-release, glibc version, architecture, virt status, init system. Probes sudo / doas / root with a usability test, not a "is it on PATH" test — so non-sudoers get a real error message instead of a wasted password prompt.
2.
Sudo password once. A background keepalive refreshes the timestamp every 50s so you're never prompted again mid-install.
3.
Install everything silently. Native packages where they exist; upstream-pinned tarballs (verified by sha256) for the rest. Parallel fetch with a progress ticker. Per-platform softening for ancient glibcs.
4.
One fzf picker. Just for your default editor (nvim / vim / hx / micro). Fish becomes your login shell automatically. Skip the picker with SHELL_BLING_NONINTERACTIVE=1.
5.
Friendly recap, then exit. Log out of your desktop session and back in (or reboot) for $SHELL and the new x-terminal-emulator default to take effect. Just reopening a terminal isn't enough on most desktops.