fix: replace compinit re-run with autoload+compdef for site-functions completions#359
Conversation
… completions The fpath-diff approach from #355/#356 had a blind spot: when the user added site-functions to fpath after their own compinit but before sparkdock, neither the duplicate guard (init.zsh) nor the fpath-change detection (sparkdock.zshrc) would trigger compinit, leaving completions like ajust, ljust unloaded. Re-running compinit is also problematic because it wipes bash-style completions (aws, gcloud) registered earlier via bashcompinit. Replace the entire fpath-snapshot + conditional-compinit mechanism with direct autoload + compdef registration of completion files in site-functions. autoload is lazy (no file I/O) and compdef writes to a hash table — both are effectively free. This works regardless of fpath/compinit ordering and never interferes with bashcompinit.
PR Reviewer Guide 🔍Here are some key observations to aid the review process:
|
PR Code Suggestions ✨Explore these optional code suggestions:
|
There was a problem hiding this comment.
Pull request overview
This PR replaces the fragile fpath-snapshot + conditional compinit re-run mechanism (introduced in #355/#356) with direct autoload -Uz + compdef registration of completion files from ~/.local/share/zsh/site-functions. The fix addresses a remaining blind spot where completions weren't discovered when a user's .zshrc added site-functions to fpath after calling compinit but before sourcing sparkdock.
Changes:
- Removed the fpath-before/after snapshot comparison and the
unset _sparkdock_fpath_beforecleanup. - Replaced conditional
compinitre-run with awhence -w compdefguard that only initializes the completion system if it has never been set up. - Added a loop that iterates over all
_*files in~/.local/share/zsh/site-functionsand registers each viaautoload -Uz+compdef, independent of fpath/compinit ordering.
You can also share your feedback on Copilot code review. Take the survey.
| # Register site-functions completions directly via autoload + compdef. | ||
| # This avoids re-running compinit (which wipes bashcompinit registrations | ||
| # like aws, gcloud) and works regardless of whether the user added | ||
| # site-functions to fpath before or after their own compinit call. | ||
| _sparkdock_site_dir="${HOME}/.local/share/zsh/site-functions" | ||
| if [[ -d "${_sparkdock_site_dir}" ]]; then | ||
| for _f in "${_sparkdock_site_dir}"/_*(N); do | ||
| autoload -Uz "${_f:t}" | ||
| compdef "${_f:t}" "${${_f:t}#_}" 2>/dev/null | ||
| done | ||
| unset _f | ||
| fi | ||
| unset _sparkdock_site_dir |
There was a problem hiding this comment.
This PR has no CHANGELOG entry documenting the approach change (replacing the fpath-snapshot + conditional compinit mechanism with direct autoload+compdef registration). Per codebase conventions (see CHANGELOG.md), all code changes must be documented with a one-line entry in CHANGELOG.md. The existing entry at line 41 describes the problem fixed in #355, but this PR introduces a new fix strategy that supersedes that approach and should be recorded as a fix entry.
User description
Summary
compinitmechanism (fix: zsh completions not discovered when compinit runs before sparkdock #355, fix: avoid duplicate fpath entry for site-functions #356) with directautoload -Uz+compdefregistration of completion files in~/.local/share/zsh/site-functionsfpathafter their owncompinitbut before sparkdock is sourcedcompinitentirely, which previously wipedbashcompinitregistrations (aws, gcloud)Problem
Commits #355 and #356 together created a blind spot:
The third case happens when
.zshrcadds site-functions tofpathaftercompinit(e.g. oh-my-zsh) but before sourcing sparkdock.Solution
Instead of trying to detect when
compinitneeds re-running (which is inherently fragile and conflicts withbashcompinit), register completions directly:This is generic (no tool-specific knowledge), idempotent, and never interferes with
bashcompinit.Testing
Tested locally —
ajust <TAB>,aws <TAB>, andgcloud <TAB>all work correctly regardless of fpath/compinit ordering in.zshrc.PR Type
Bug fix, Enhancement
Description
Replace fragile fpath-snapshot + conditional
compinitwith directautoload+compdefregistrationFix completions not discovered when user's
compinitruns before sparkdock is sourcedAvoid re-running
compinit, which previously wipedbashcompinitregistrations (aws, gcloud)Only initialize completion system if
compdefis not already availableDiagram Walkthrough
File Walkthrough
sparkdock.zshrc
Replace fpath-diff compinit with direct autoload+compdef registrationconfig/shell/sparkdock.zshrc
_sparkdock_fpath_before) andfpath-diff conditional around
compinitcompinitifcompdefis not already defined(i.e., completion system never initialized)
~/.local/share/zsh/site-functions/_*files to registercompletions directly via
autoload -Uzandcompdef, bypassing need tore-run
compinitbashcompinitregistrations (aws, gcloud) caused byre-running
compinit