fix(update): disambiguate local vs global install when CWD is HOME

When running /gsd:update from $HOME, the local path ./.claude/ resolves
to the same directory as $HOME/.claude/. The local branch always wins,
triggering --local reinstall that corrupts all paths in a global install.
This is self-reinforcing — once corrupted, every subsequent update
perpetuates the corruption.

Compare canonical paths (via cd + pwd) and only report LOCAL when the
resolved directories differ. When they're the same, fall through to
GLOBAL detection.

Closes #721

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Tibsfox
2026-03-03 03:08:38 -08:00
committed by Lex Christopherson
parent 07f44cc1c3
commit 1c6f4fe11f

View File

@@ -14,24 +14,34 @@ Detect whether GSD is installed locally or globally by checking both locations a
```bash
# Check local first (takes priority only if valid)
# Detect runtime config directory (supports Claude, OpenCode, Gemini)
LOCAL_VERSION_FILE="" LOCAL_MARKER_FILE=""
LOCAL_VERSION_FILE="" LOCAL_MARKER_FILE="" LOCAL_DIR=""
for dir in .claude .config/opencode .opencode .gemini; do
if [ -f "./$dir/get-shit-done/VERSION" ]; then
LOCAL_VERSION_FILE="./$dir/get-shit-done/VERSION"
LOCAL_MARKER_FILE="./$dir/get-shit-done/workflows/update.md"
LOCAL_DIR="$(cd "./$dir" 2>/dev/null && pwd)"
break
fi
done
GLOBAL_VERSION_FILE="" GLOBAL_MARKER_FILE=""
GLOBAL_VERSION_FILE="" GLOBAL_MARKER_FILE="" GLOBAL_DIR=""
for dir in .claude .config/opencode .opencode .gemini; do
if [ -f "$HOME/$dir/get-shit-done/VERSION" ]; then
GLOBAL_VERSION_FILE="$HOME/$dir/get-shit-done/VERSION"
GLOBAL_MARKER_FILE="$HOME/$dir/get-shit-done/workflows/update.md"
GLOBAL_DIR="$(cd "$HOME/$dir" 2>/dev/null && pwd)"
break
fi
done
# Only treat as LOCAL if the resolved paths differ (prevents misdetection when CWD=$HOME)
IS_LOCAL=false
if [ -n "$LOCAL_VERSION_FILE" ] && [ -f "$LOCAL_VERSION_FILE" ] && [ -f "$LOCAL_MARKER_FILE" ] && grep -Eq '^[0-9]+\.[0-9]+\.[0-9]+' "$LOCAL_VERSION_FILE"; then
if [ -z "$GLOBAL_DIR" ] || [ "$LOCAL_DIR" != "$GLOBAL_DIR" ]; then
IS_LOCAL=true
fi
fi
if [ "$IS_LOCAL" = true ]; then
cat "$LOCAL_VERSION_FILE"
echo "LOCAL"
elif [ -n "$GLOBAL_VERSION_FILE" ] && [ -f "$GLOBAL_VERSION_FILE" ] && [ -f "$GLOBAL_MARKER_FILE" ] && grep -Eq '^[0-9]+\.[0-9]+\.[0-9]+' "$GLOBAL_VERSION_FILE"; then