Compare commits
19 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 48814c5d42 | |||
| 0eb605a835 | |||
| c32dbb92ac | |||
| 8c3dcacafc | |||
| c680be4817 | |||
| 13f43c3c5f | |||
| aafdc3a119 | |||
| 4053acbbc0 | |||
| 2906352220 | |||
| 1d2a823750 | |||
| 8400ddf6a8 | |||
| 11bf7ecaa4 | |||
| 3d6f13b2bc | |||
| e2a1e3b784 | |||
| e38a6b3166 | |||
| 467b967ced | |||
| 474fdd028c | |||
| a45f89b187 | |||
| 1b60a9364d |
@@ -0,0 +1,33 @@
|
|||||||
|
# Never track Claude Code per-machine state, secrets, or chat data.
|
||||||
|
#
|
||||||
|
# settings.json IS tracked (portable user prefs + permissions allowlist).
|
||||||
|
# Everything else under ~/.claude/ stays per-host: credentials, session
|
||||||
|
# logs, project memories, file-edit history, telemetry, caches.
|
||||||
|
|
||||||
|
# Auth — must NEVER be tracked
|
||||||
|
.credentials.json
|
||||||
|
|
||||||
|
# Per-machine settings overrides (by Claude Code convention)
|
||||||
|
settings.local.json
|
||||||
|
|
||||||
|
# Chat and session data
|
||||||
|
history.jsonl
|
||||||
|
sessions/
|
||||||
|
projects/
|
||||||
|
file-history/
|
||||||
|
plans/
|
||||||
|
|
||||||
|
# Caches and ephemeral state
|
||||||
|
cache/
|
||||||
|
downloads/
|
||||||
|
paste-cache/
|
||||||
|
shell-snapshots/
|
||||||
|
session-env/
|
||||||
|
backups/
|
||||||
|
telemetry/
|
||||||
|
mcp-needs-auth-cache.json
|
||||||
|
|
||||||
|
# Plugin marketplace state — known_marketplaces.json IS portable, but the
|
||||||
|
# resolved-plugin caches and the local blocklist are per-machine.
|
||||||
|
plugins/blocklist.json
|
||||||
|
plugins/marketplaces/
|
||||||
@@ -0,0 +1,58 @@
|
|||||||
|
{
|
||||||
|
"permissions": {
|
||||||
|
"allow": [
|
||||||
|
"Bash(tmux source-file:*)",
|
||||||
|
"Bash(git:*)",
|
||||||
|
"Bash(curl:*)",
|
||||||
|
"Bash(sudo:*)",
|
||||||
|
"Bash(find:*)",
|
||||||
|
"Bash(ls:*)",
|
||||||
|
"Bash(cat:*)",
|
||||||
|
"Bash(systemctl:*)",
|
||||||
|
"Bash(sysctl:*)",
|
||||||
|
"Bash(crontab:*)",
|
||||||
|
"Bash(dig:*)",
|
||||||
|
"Bash(ulimit:*)",
|
||||||
|
"Bash(python3:*)",
|
||||||
|
"Bash(iptables:*)",
|
||||||
|
"Bash(ip6tables:*)",
|
||||||
|
"Bash(ufw status:*)",
|
||||||
|
"Bash(firewall-cmd:*)",
|
||||||
|
"Bash(apt list:*)",
|
||||||
|
"Bash(apt-get install:*)",
|
||||||
|
"Bash(apt-get upgrade:*)",
|
||||||
|
"Bash(dpkg:*)",
|
||||||
|
"Bash(fail2ban-client status:*)",
|
||||||
|
"Bash(fail2ban-client set:*)",
|
||||||
|
"Bash(aa-status)",
|
||||||
|
"Bash(getenforce)",
|
||||||
|
"Bash(mount)",
|
||||||
|
"Bash(netstat -tuln)",
|
||||||
|
"Bash(netstat -tlnp)",
|
||||||
|
"Bash(openssl x509:*)",
|
||||||
|
"Bash(openssl rand:*)",
|
||||||
|
"Bash(grep -v \"^$\")",
|
||||||
|
"Bash(du -sh /var/log/*)",
|
||||||
|
"Bash(lsmod)",
|
||||||
|
"Bash(xargs ls:*)",
|
||||||
|
"Bash(last:*)",
|
||||||
|
"Bash(nginx:*)",
|
||||||
|
"Bash(redis-cli:*)",
|
||||||
|
"Bash(rkhunter:*)",
|
||||||
|
"Bash(aideinit)",
|
||||||
|
"Bash(npm --version)",
|
||||||
|
"Bash(ruby --version)",
|
||||||
|
"Bash(getent passwd:*)",
|
||||||
|
"Bash(sqlite3:*)",
|
||||||
|
"Read(//home/**)",
|
||||||
|
"Read(//opt/**)",
|
||||||
|
"Read(//etc/nginx/sites-enabled/**)",
|
||||||
|
"Read(//etc/nginx/sites-available/**)"
|
||||||
|
],
|
||||||
|
"defaultMode": "auto"
|
||||||
|
},
|
||||||
|
"theme": "dark-daltonized",
|
||||||
|
"verbose": true,
|
||||||
|
"tui": "fullscreen",
|
||||||
|
"skipAutoPermissionPrompt": true
|
||||||
|
}
|
||||||
+55
-19
@@ -1,33 +1,69 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
#
|
#
|
||||||
# Print the "best" IP for the tmux status bar.
|
# Print the "best" IP for the tmux status bar.
|
||||||
# Preference: DO reserved/floating IP > public egress (ipify) > first local IP.
|
#
|
||||||
|
# Shows a directly-held public/WAN IP when the machine has one on an interface,
|
||||||
|
# otherwise its LAN/private IP. No external "what's my IP" lookup -- a NAT'd box
|
||||||
|
# shows its LAN IP, never the gateway's egress. Works the same everywhere: a box
|
||||||
|
# with a public IP on a NIC (incl. a cloud droplet's eth0) shows that WAN IP; a
|
||||||
|
# NAT'd box shows its LAN IP. The VPN overlay is added separately by tmux-net via
|
||||||
|
# tmux-vpn-ip and is untouched here.
|
||||||
#
|
#
|
||||||
|
|
||||||
set -u
|
set -u
|
||||||
|
|
||||||
META="http://169.254.169.254/metadata/v1"
|
# This machine's own non-loopback IPv4 addresses, one per line. VPN tunnels are
|
||||||
CURL="curl -sf --connect-timeout 1 --max-time 2"
|
# excluded (tmux-net surfaces the VPN address separately as the ⇡ segment).
|
||||||
|
list_ipv4() {
|
||||||
is_digitalocean() {
|
if command -v ip >/dev/null 2>&1; then
|
||||||
[ -r /sys/class/dmi/id/sys_vendor ] \
|
ip -4 -o addr show scope global 2>/dev/null \
|
||||||
&& grep -qi digitalocean /sys/class/dmi/id/sys_vendor
|
| awk '$2 !~ /^(tun|wg|ppp|tap)/ {print $4}' | cut -d/ -f1
|
||||||
|
elif hostname -I >/dev/null 2>&1; then
|
||||||
|
hostname -I 2>/dev/null | tr ' ' '\n'
|
||||||
|
else
|
||||||
|
ifconfig 2>/dev/null | awk '/inet /{print $2}'
|
||||||
|
fi | grep -E '^([0-9]{1,3}\.){3}[0-9]{1,3}$' | grep -v '^127\.'
|
||||||
}
|
}
|
||||||
|
|
||||||
do_anchor_ip() {
|
# RFC1918 / link-local / CGNAT -- not a directly-routable WAN address.
|
||||||
local kind active ip
|
is_private_ipv4() {
|
||||||
for kind in reserved_ip floating_ip; do
|
case "$1" in
|
||||||
active=$($CURL "$META/$kind/ipv4/active" 2>/dev/null) || continue
|
10.*|192.168.*|169.254.*) return 0 ;;
|
||||||
[ "$active" = "true" ] || continue
|
172.1[6-9].*|172.2[0-9].*|172.3[01].*) return 0 ;;
|
||||||
ip=$($CURL "$META/$kind/ipv4/ip_address" 2>/dev/null) || continue
|
100.6[4-9].*|100.[7-9][0-9].*|100.1[01][0-9].*|100.12[0-7].*) return 0 ;;
|
||||||
[ -n "$ip" ] && { printf '%s\n' "$ip"; return 0; }
|
*) return 1 ;;
|
||||||
done
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# First directly-held public/WAN IP, if the machine has one on an interface.
|
||||||
|
public_ip() {
|
||||||
|
local ip
|
||||||
|
while IFS= read -r ip; do
|
||||||
|
[ -n "$ip" ] || continue
|
||||||
|
is_private_ipv4 "$ip" || { printf '%s\n' "$ip"; return 0; }
|
||||||
|
done <<EOF
|
||||||
|
$(list_ipv4)
|
||||||
|
EOF
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
|
|
||||||
if is_digitalocean && do_anchor_ip; then
|
# Fallback: the machine's primary interface IP (covers macOS and odd setups).
|
||||||
exit 0
|
print_local_ip() {
|
||||||
|
local iface ip
|
||||||
|
if command -v ipconfig >/dev/null 2>&1; then
|
||||||
|
for iface in en0 en1 en2; do
|
||||||
|
ip=$(ipconfig getifaddr "$iface" 2>/dev/null) || true
|
||||||
|
[ -n "${ip:-}" ] && { printf '%s\n' "$ip"; return 0; }
|
||||||
|
done
|
||||||
fi
|
fi
|
||||||
|
if hostname -I >/dev/null 2>&1; then
|
||||||
|
hostname -I | awk '{print $1}'
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
ifconfig 2>/dev/null | awk '/inet /{ if ($2 != "127.0.0.1") { print $2; exit } }'
|
||||||
|
}
|
||||||
|
|
||||||
curl -s --connect-timeout 3 https://api.ipify.org 2>/dev/null \
|
# A directly-held public/WAN IP if the box has one, else the LAN IP.
|
||||||
|| hostname -I | awk '{print $1}'
|
ip=$(public_ip || true)
|
||||||
|
[ -z "${ip:-}" ] && ip=$(print_local_ip)
|
||||||
|
printf '%s\n' "${ip:-}"
|
||||||
|
|||||||
Executable
+20
@@ -0,0 +1,20 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# Emit the tmux status-bar network segment.
|
||||||
|
# No VPN: "⌂ <local_ip>"
|
||||||
|
# VPN up: "⌂ <local_ip> / ⇡ <vpn_ip>"
|
||||||
|
# Offline: "✕" (no local IP and no VPN tunnel)
|
||||||
|
#
|
||||||
|
|
||||||
|
set -u
|
||||||
|
|
||||||
|
local_ip=$("$HOME/.local/bin/tmux-ip" 2>/dev/null || true)
|
||||||
|
vpn_ip=$("$HOME/.local/bin/tmux-vpn-ip" 2>/dev/null || true)
|
||||||
|
|
||||||
|
if [ -z "${local_ip:-}" ] && [ -z "${vpn_ip:-}" ]; then
|
||||||
|
printf '\xe2\x9c\x95 \n' # ✕ no active connection (trailing space for padding)
|
||||||
|
elif [ -n "${vpn_ip:-}" ]; then
|
||||||
|
printf '\xe2\x8c\x82 %s / \xe2\x87\xa1 %s\n' "${local_ip:-}" "$vpn_ip"
|
||||||
|
else
|
||||||
|
printf '\xe2\x8c\x82 %s\n' "${local_ip:-}"
|
||||||
|
fi
|
||||||
Executable
+24
@@ -0,0 +1,24 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# Print the IPv4 of the first active VPN tunnel interface, if any.
|
||||||
|
# Empty output when no VPN is up.
|
||||||
|
#
|
||||||
|
# macOS: utun* Linux: tun*, wg*, ppp*
|
||||||
|
|
||||||
|
set -u
|
||||||
|
|
||||||
|
case "$(uname -s)" in
|
||||||
|
Darwin)
|
||||||
|
ifconfig 2>/dev/null | awk '
|
||||||
|
/^utun[0-9]+:/ { iface=$1; sub(":", "", iface); next }
|
||||||
|
/^[a-z]+[0-9]*:/ { iface="" }
|
||||||
|
iface != "" && $1 == "inet" { print $2; exit }
|
||||||
|
'
|
||||||
|
;;
|
||||||
|
Linux)
|
||||||
|
if command -v ip >/dev/null 2>&1; then
|
||||||
|
ip -4 -o addr show 2>/dev/null \
|
||||||
|
| awk '$2 ~ /^(tun|wg|ppp)[0-9]+/ { sub("/.*","",$4); print $4; exit }'
|
||||||
|
fi
|
||||||
|
;;
|
||||||
|
esac
|
||||||
+3
-3
@@ -79,9 +79,9 @@ set -g pane-border-style fg=colour245
|
|||||||
set -g pane-active-border-style fg=colour39
|
set -g pane-active-border-style fg=colour39
|
||||||
set -g message-style fg=colour16,bg=colour221,bold
|
set -g message-style fg=colour16,bg=colour221,bold
|
||||||
set -g status-left '#[fg=colour235,bg=colour252,bold] ❐ #S #[fg=colour252,bg=colour238,nobold]❯#[fg=colour245,bg=colour238,bold] #(whoami) '
|
set -g status-left '#[fg=colour235,bg=colour252,bold] ❐ #S #[fg=colour252,bg=colour238,nobold]❯#[fg=colour245,bg=colour238,bold] #(whoami) '
|
||||||
set -g status-right '#[bold][#[nobold,fg=colour229]#H#[fg=default] / #[fg=colour229]#(~/.local/bin/tmux-ip)#[fg=default,bold]]#[nobold,fg=colour255] %H:%M %d-%b-%Y '
|
set -g status-right '#[bold][#[nobold,fg=colour229]#h#[fg=default] / #[fg=colour229]#(~/.local/bin/tmux-net)#[fg=default,bold]]#[nobold,fg=colour255] %-I:%M%P %d-%b-%Y '
|
||||||
set -g window-status-format '#[fg=colour235,bg=colour252,nobold] #(~/.local/bin/tmux-window-icon #{window_index}) #(pwd="#{pane_current_path}"; echo ${pwd####*/}) #W '
|
set -g window-status-format '#[fg=colour235,bg=colour252,nobold] #{?#{==:#{window_index},1},❶,#{?#{==:#{window_index},2},❷,#{?#{==:#{window_index},3},❸,#{?#{==:#{window_index},4},❹,#{?#{==:#{window_index},5},❺,#{?#{==:#{window_index},6},❻,#{?#{==:#{window_index},7},❼,#{?#{==:#{window_index},8},❽,#{?#{==:#{window_index},9},❾,#{?#{==:#{window_index},10},❿,#{window_index}}}}}}}}}}} #{b:pane_current_path} #W '
|
||||||
set -g window-status-current-format '#[fg=colour234,bg=colour39,bold] [#[fg=colour232,bold]#{?window_zoomed_flag,#[fg=colour228],} #(~/.local/bin/tmux-window-icon #{window_index}) #(pwd="#{pane_current_path}"; echo ${pwd####*/}) #W #[fg=colour234,bold]] '
|
set -g window-status-current-format '#[fg=colour234,bg=colour39,bold] [#[fg=colour232,bold]#{?window_zoomed_flag,#[fg=colour228],} #{?#{==:#{window_index},1},❶,#{?#{==:#{window_index},2},❷,#{?#{==:#{window_index},3},❸,#{?#{==:#{window_index},4},❹,#{?#{==:#{window_index},5},❺,#{?#{==:#{window_index},6},❻,#{?#{==:#{window_index},7},❼,#{?#{==:#{window_index},8},❽,#{?#{==:#{window_index},9},❾,#{?#{==:#{window_index},10},❿,#{window_index}}}}}}}}}}} #{b:pane_current_path} #W #[fg=colour234,bold]] '
|
||||||
set-option -g status-interval 60
|
set-option -g status-interval 60
|
||||||
|
|
||||||
# Patch for OS X pbpaste and pbcopy under tmux.
|
# Patch for OS X pbpaste and pbcopy under tmux.
|
||||||
|
|||||||
@@ -102,6 +102,46 @@ On top of stock YADR:
|
|||||||
- Misc: `.rainbow_config.json` (rainbowstream), `.nanorc`, `.selected_editor`,
|
- Misc: `.rainbow_config.json` (rainbowstream), `.nanorc`, `.selected_editor`,
|
||||||
`.mplayer/config`, `.jigdo-lite`
|
`.mplayer/config`, `.jigdo-lite`
|
||||||
|
|
||||||
|
## Rainbow output (lolcat)
|
||||||
|
|
||||||
|
`zsh/lolcat.zsh` wires [lolcat](https://github.com/busyloop/lolcat) (Debian's
|
||||||
|
`/usr/games/lolcat`, busyloop's Ruby build — 24-bit truecolor) into a few shell
|
||||||
|
helpers. lolcat auto-detects a tty — it colorizes straight to the terminal but
|
||||||
|
passes text through plain when piped onward, so use `-f`/`--force` to colorize
|
||||||
|
mid-pipeline.
|
||||||
|
|
||||||
|
### Opt-in, per command
|
||||||
|
|
||||||
|
Prefix any command to rainbow its output:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
lol fastfetch
|
||||||
|
lol git log --oneline
|
||||||
|
lol ls -C # -C keeps columns: a piped ls otherwise goes single-column
|
||||||
|
lolf git diff | less -R # force color so it survives down a pipeline
|
||||||
|
```
|
||||||
|
|
||||||
|
### Shortcuts
|
||||||
|
|
||||||
|
```sh
|
||||||
|
rcat file.txt # rainbow cat
|
||||||
|
rls -la # rainbow ls, columns preserved
|
||||||
|
some-cmd | rless # rainbow + pager (less -R)
|
||||||
|
```
|
||||||
|
|
||||||
|
### Session toggle
|
||||||
|
|
||||||
|
Rainbow *all* shell stdout until you turn it off:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
rainbow_on # everything is rainbow now
|
||||||
|
...
|
||||||
|
rainbow_off # back to normal
|
||||||
|
```
|
||||||
|
|
||||||
|
Novelty only: it garbles full-screen/interactive programs (vim, less, htop,
|
||||||
|
fzf, ssh) and the prompt, and buffers streaming output. Doesn't touch stderr.
|
||||||
|
|
||||||
## Upstream
|
## Upstream
|
||||||
|
|
||||||
Base is [skwp/dotfiles][yadr] (YADR — Yet Another Dotfiles Repo). All credit
|
Base is [skwp/dotfiles][yadr] (YADR — Yet Another Dotfiles Repo). All credit
|
||||||
|
|||||||
@@ -210,7 +210,7 @@ def install_term_theme
|
|||||||
message = "Which theme would you like to apply to your iTerm2 profile?"
|
message = "Which theme would you like to apply to your iTerm2 profile?"
|
||||||
color_scheme = ask message, iTerm_available_themes
|
color_scheme = ask message, iTerm_available_themes
|
||||||
|
|
||||||
return if color_scheme == 'None'
|
return if color_scheme.nil? || color_scheme == 'None'
|
||||||
|
|
||||||
color_scheme_file = File.join('iTerm2', "#{color_scheme}.itermcolors")
|
color_scheme_file = File.join('iTerm2', "#{color_scheme}.itermcolors")
|
||||||
|
|
||||||
@@ -220,6 +220,8 @@ def install_term_theme
|
|||||||
profiles << 'All'
|
profiles << 'All'
|
||||||
selected = ask message, profiles
|
selected = ask message, profiles
|
||||||
|
|
||||||
|
return if selected.nil?
|
||||||
|
|
||||||
if selected == 'All'
|
if selected == 'All'
|
||||||
(profiles.size-1).times { |idx| apply_theme_to_iterm_profile_idx idx, color_scheme_file }
|
(profiles.size-1).times { |idx| apply_theme_to_iterm_profile_idx idx, color_scheme_file }
|
||||||
else
|
else
|
||||||
@@ -244,7 +246,12 @@ def ask(message, values)
|
|||||||
puts message
|
puts message
|
||||||
while true
|
while true
|
||||||
values.each_with_index { |val, idx| puts " #{idx+1}. #{val}" }
|
values.each_with_index { |val, idx| puts " #{idx+1}. #{val}" }
|
||||||
selection = STDIN.gets.chomp
|
input = STDIN.gets
|
||||||
|
if input.nil?
|
||||||
|
puts "(no input available — skipping prompt)"
|
||||||
|
return nil
|
||||||
|
end
|
||||||
|
selection = input.chomp
|
||||||
if (Float(selection)==nil rescue true) || selection.to_i < 0 || selection.to_i > values.size+1
|
if (Float(selection)==nil rescue true) || selection.to_i < 0 || selection.to_i > values.size+1
|
||||||
puts "ERROR: Invalid selection.\n\n"
|
puts "ERROR: Invalid selection.\n\n"
|
||||||
else
|
else
|
||||||
|
|||||||
+1
-1
@@ -36,7 +36,7 @@ PERSONAL_FILES=(
|
|||||||
# untouched. This deliberately avoids wholesale-replacing $HOME/.local etc.,
|
# untouched. This deliberately avoids wholesale-replacing $HOME/.local etc.,
|
||||||
# which would sweep away unrelated user data (fonts, app state, ...).
|
# which would sweep away unrelated user data (fonts, app state, ...).
|
||||||
PERSONAL_DIRS=(
|
PERSONAL_DIRS=(
|
||||||
.fonts .irssi .nano .themes .local .mplayer
|
.fonts .irssi .nano .themes .local .mplayer .claude
|
||||||
)
|
)
|
||||||
|
|
||||||
have() { command -v "$1" >/dev/null 2>&1; }
|
have() { command -v "$1" >/dev/null 2>&1; }
|
||||||
|
|||||||
@@ -0,0 +1,13 @@
|
|||||||
|
# Eagerly define `diff` as a real function instead of relying on prezto's
|
||||||
|
# autoload stub. The autoload stub emits
|
||||||
|
# "(eval):1: diff: function definition file not found"
|
||||||
|
# in non-interactive eval contexts where $fpath doesn't yet include the
|
||||||
|
# prezto utility module's functions directory. Defining a real function
|
||||||
|
# here bypasses the autoload path entirely.
|
||||||
|
function diff {
|
||||||
|
if (( $+commands[colordiff] )); then
|
||||||
|
command diff --unified "$@" | colordiff --difftype diffu
|
||||||
|
else
|
||||||
|
command diff --unified "$@"
|
||||||
|
fi
|
||||||
|
}
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
# zsh/lolcat.zsh (drunkendotfiles) — auto-sourced via ~/.zshrc: for f in ~/.yadr/zsh/*.zsh
|
||||||
|
# Rainbow-output helpers built on lolcat = Debian's busyloop Ruby build at
|
||||||
|
# /usr/games/lolcat (upstream github.com/busyloop/lolcat; 24-bit truecolor).
|
||||||
|
# It auto-detects a tty, so use -f/--force-color to colorize mid-pipeline.
|
||||||
|
# This lolcat is truecolor and auto-detects a tty: it colorizes when writing
|
||||||
|
# straight to the terminal, but passes text through UNcolored when piped onward,
|
||||||
|
# so use -f/--force to colorize in the middle of a pipeline.
|
||||||
|
|
||||||
|
# Debian ships lolcat in /usr/games; make sure it's reachable in any shell.
|
||||||
|
[[ ":$PATH:" == *":/usr/games:"* ]] || export PATH="$PATH:/usr/games"
|
||||||
|
|
||||||
|
# --- opt-in: prefix ANY command to rainbow its output on the terminal --------
|
||||||
|
# lol ls -C lol fastfetch lol git log --oneline
|
||||||
|
# (The wrapped command sees a pipe, not a tty, so some tools drop their own
|
||||||
|
# colors/columns -- e.g. use `lol ls -C` to keep ls in columns.)
|
||||||
|
lol() { "$@" | lolcat; }
|
||||||
|
|
||||||
|
# Same, but force color so it survives further down a pipeline:
|
||||||
|
# lolf git diff | less -R
|
||||||
|
lolf() { "$@" | lolcat -f; }
|
||||||
|
|
||||||
|
# --- handy rainbow shortcuts for plain-text output ---------------------------
|
||||||
|
rcat() { lolcat "$@"; } # rcat file.txt (or: some-cmd | rcat)
|
||||||
|
rls() { ls -C "$@" | lolcat; } # rainbow ls, columns preserved
|
||||||
|
rless() { lolcat -f | less -R; } # pipe into me: some-cmd | rless
|
||||||
|
|
||||||
|
# --- whole-session "rainbow everything" toggle (NOVELTY) ---------------------
|
||||||
|
# Pipes the shell's stdout through lolcat until turned off. It WILL garble
|
||||||
|
# full-screen/interactive programs (vim, less, htop, fzf, ssh) and your prompt,
|
||||||
|
# and buffers streaming output. Use it for a burst of plain command output,
|
||||||
|
# then rainbow_off. Does not affect stderr.
|
||||||
|
rainbow_on() { [[ -n $RAINBOW_PIPE ]] && return; exec 3>&1; exec > >(lolcat -f); export RAINBOW_PIPE=1; }
|
||||||
|
rainbow_off() { [[ -z $RAINBOW_PIPE ]] && return; exec 1>&3 3>&-; unset RAINBOW_PIPE; }
|
||||||
Reference in New Issue
Block a user