'tarbuckle opinion?' failed at '(eval):1: no matches found' — zsh expands ?, * and [ as globs before the script is reached, and asking him a question is the natural use of the one surface built for questions. Three ways past it, and the wrapper's help now names all three in order of least fuss: drop the ?, quote the phrase, or the noglob alias now in shell/.zshrc. ⚠ The alias is listed LAST and with its limit stated, because it only helps if the calling shell is interactive — .zshrc is not read otherwise — and that is exactly the kind of fix that looks total and silently is not. noglob for one command rather than 'unsetopt nomatch', which would change how every command in the shell behaves to fix one of them. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01J6hZXNYSxEfZseBGTni4sf
216 lines
13 KiB
Bash
216 lines
13 KiB
Bash
# ░░░░▀▀█░█▀▀░█░█░█▀▄░█▀▀
|
|
# ░░░░▄▀░░▀▀█░█▀█░█▀▄░█░░
|
|
# ░▀░░▀▀▀░▀▀▀░▀░▀░▀░▀░▀▀▀
|
|
# Refined shell configuration following durability principles
|
|
# ASCII art: TextKool (https://textkool.com/en) "Font: Pagga"
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# PERFORMANCE & EARLY INITIALIZATION
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Enable Powerlevel10k instant prompt (must be near top)
|
|
if [[ -r "${XDG_CACHE_HOME:-$HOME/.cache}/p10k-instant-prompt-${(%):-%n}.zsh" ]]; then
|
|
source "${XDG_CACHE_HOME:-$HOME/.cache}/p10k-instant-prompt-${(%):-%n}.zsh"
|
|
fi
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# CORE ENVIRONMENT SETUP
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Source modular configuration files
|
|
local config_files=(
|
|
"$HOME/dotfiles/shell/environment.zsh"
|
|
"$HOME/dotfiles/shell/paths.zsh"
|
|
)
|
|
|
|
for config_file in "${config_files[@]}"; do
|
|
[[ -f "$config_file" ]] && source "$config_file"
|
|
done
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# PLUGIN MANAGEMENT
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Antidote plugin manager with graceful fallback
|
|
if [[ -f "/opt/homebrew/share/antidote/antidote.zsh" ]]; then
|
|
source /opt/homebrew/share/antidote/antidote.zsh
|
|
|
|
# Load plugins from manifest
|
|
local plugin_file="$HOME/dotfiles/shell/.zsh-plugins.txt"
|
|
if [[ -f "$plugin_file" ]]; then
|
|
antidote load < "$plugin_file"
|
|
elif [[ -z "${P10K_INSTANT_PROMPT-}" ]]; then
|
|
echo "⚠️ Plugin manifest not found: $plugin_file"
|
|
fi
|
|
elif [[ -z "${P10K_INSTANT_PROMPT-}" ]]; then
|
|
echo "⚠️ Antidote not found. Install with: brew install antidote"
|
|
fi
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# PROMPT CONFIGURATION
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Powerlevel10k configuration
|
|
[[ ! -f ~/.p10k.zsh ]] || source ~/.p10k.zsh
|
|
# Run 'p10k configure' to reconfigure prompt
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# SHELL BEHAVIOR & OPTIONS
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Directory navigation
|
|
setopt auto_cd # Type directory name to cd into it
|
|
setopt auto_pushd # Make cd push old directory onto stack
|
|
setopt pushd_ignore_dups # Don't push duplicates onto stack
|
|
setopt pushd_minus # Make pushd work like cd
|
|
|
|
# Command correction and expansion
|
|
setopt correct # Spelling correction for commands
|
|
setopt correct_all # Spelling correction for arguments
|
|
setopt interactive_comments # Allow comments in interactive shell
|
|
setopt extended_glob # Enable extended globbing
|
|
setopt glob_dots # Don't require leading . in filename to be matched
|
|
|
|
# History configuration (extended)
|
|
setopt extended_history # Record timestamp and duration
|
|
setopt hist_expire_dups_first # Expire duplicates first
|
|
setopt hist_ignore_all_dups # Don't record duplicates
|
|
setopt hist_ignore_space # Don't record commands starting with space
|
|
setopt hist_verify # Show command before executing from history
|
|
setopt inc_append_history # Add commands immediately
|
|
setopt share_history # Share history between sessions
|
|
setopt hist_reduce_blanks # Remove superfluous blanks
|
|
|
|
# Job control
|
|
setopt auto_resume # Single word commands can resume jobs
|
|
setopt long_list_jobs # List jobs in long format
|
|
setopt notify # Report status of background jobs immediately
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# COMPLETION SYSTEM
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Initialize completion system (suppress warnings during instant prompt)
|
|
autoload -Uz compinit
|
|
if [[ -n "${P10K_INSTANT_PROMPT-}" ]]; then
|
|
compinit -d ~/.zcompdump 2>/dev/null
|
|
else
|
|
compinit
|
|
fi
|
|
|
|
# Completion options
|
|
setopt complete_in_word # Complete from both ends of word
|
|
setopt always_to_end # Move cursor to end after completion
|
|
setopt auto_menu # Show completion menu on successive tab
|
|
setopt auto_list # Automatically list choices on ambiguous completion
|
|
setopt auto_param_slash # Add trailing slash for directory completions
|
|
|
|
# Completion styling
|
|
zstyle ':completion:*' menu select
|
|
zstyle ':completion:*' list-colors "${(s.:.)LS_COLORS}"
|
|
zstyle ':completion:*' matcher-list 'm:{a-zA-Z}={A-Za-z}' 'r:|=*' 'l:|=* r:|=*'
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# TOOL INTEGRATIONS
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# (fzf and zoxide removed — not installed)
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# GNU COREUTILS (interactive-only PATH)
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Prevent GMP and other formulae from breaking by keeping gnubin off build PATH.
|
|
# Only activate in interactive shells.
|
|
if [[ $- == *i* ]]; then
|
|
export PATH="/opt/homebrew/opt/coreutils/libexec/gnubin:$PATH"
|
|
fi
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# NODE VERSION MANAGEMENT
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# NVM integration with lazy loading for performance
|
|
[[ -f "$HOME/dotfiles/shell/nvm.zsh" ]] && source "$HOME/dotfiles/shell/nvm.zsh"
|
|
|
|
# Ensure claude-code is accessible (after nvm setup)
|
|
if [[ -d "$HOME/.nvm/versions/node/v22.16.0/bin" ]] && [[ ! -v NVM_LOADED ]]; then
|
|
# Add claude-code's Node bin to PATH as fallback
|
|
# This ensures claude-code works even before nvm is fully loaded
|
|
export PATH="$HOME/.nvm/versions/node/v22.16.0/bin:$PATH"
|
|
fi
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# CUSTOM FUNCTIONS & ALIASES
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Load enhanced functions and aliases
|
|
local shell_files=(
|
|
"$HOME/dotfiles/shell/functions.zsh"
|
|
"$HOME/dotfiles/shell/aliases.zsh"
|
|
)
|
|
|
|
for shell_file in "${shell_files[@]}"; do
|
|
if [[ -f "$shell_file" ]]; then
|
|
source "$shell_file"
|
|
elif [[ -z "${P10K_INSTANT_PROMPT-}" ]]; then
|
|
echo "⚠️ Shell configuration missing: $shell_file"
|
|
fi
|
|
done
|
|
|
|
# Legacy files removed - using dotfiles versions
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# CONTEXT AWARENESS
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Detect and set initial context
|
|
detect_context
|
|
|
|
# Display context-aware welcome message (interactive shells only)
|
|
if [[ $- == *i* ]] && [[ -z "$VSCODE_INJECTION" ]]; then
|
|
case "$CURRENT_CONTEXT" in
|
|
"work") echo "🏢 Work context activated" ;;
|
|
"chamber") echo "🔮 Chamber context activated" ;;
|
|
"vault") echo "📚 Vault context activated" ;;
|
|
"dotfiles") echo "⚙️ Dotfiles context activated" ;;
|
|
esac
|
|
fi
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# PERFORMANCE OPTIMIZATION
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Fast mode for non-interactive shells
|
|
[[ $- != *i* ]] && unsetopt zle && return
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# LOCAL CUSTOMIZATIONS
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Machine-specific configurations
|
|
[[ -f "$HOME/.zshrc.local" ]] && source "$HOME/.zshrc.local"
|
|
|
|
# Development environment configurations
|
|
[[ -f "$HOME/.env.local" ]] && source "$HOME/.env.local"
|
|
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
# LEGACY & MIGRATION SUPPORT
|
|
# ═══════════════════════════════════════════════════════════════════════════════
|
|
|
|
# Temporary: Handle pipx path duplication (remove after migration)
|
|
typeset -U path PATH
|
|
|
|
# Note: This configuration follows the μέτρον principle
|
|
# - Each section has clear purpose and boundaries
|
|
# - Graceful degradation when tools are missing
|
|
# - Performance considerations for different use cases
|
|
# - Modular structure for maintainability
|
|
|
|
# Tarbuckle — call him by name with an actual question.
|
|
# zsh treats `?` (and `*`, `[`) as globs, so `tarbuckle opinion?` dies at
|
|
# "no matches found" before the wrapper is ever reached. noglob suspends filename
|
|
# generation for this command only. Not `unsetopt nomatch`, which would change how
|
|
# every command in the shell behaves to fix one of them.
|
|
alias tarbuckle='noglob tarbuckle'
|