mirror of
https://github.com/garrytan/gstack.git
synced 2026-05-21 12:18:24 +08:00
feat(paths): bin/gstack-paths helper + migrate 8 skills off inline state-root chains
New bin/gstack-paths emits GSTACK_STATE_ROOT, PLAN_ROOT, TMP_ROOT exports for
skill bash blocks to source via eval. Honors GSTACK_HOME → CLAUDE_PLUGIN_DATA →
$HOME/.gstack → .gstack (and parallel chains for plan/tmp roots) so skills work
the same in plugin installs, global installs, and CI containers without HOME.
Eight skills migrate off inline ${CLAUDE_PLUGIN_DATA:-...} or ${GSTACK_HOME:-...}
chains: careful, freeze, guard, unfreeze, investigate, context-save,
context-restore, learn, office-hours, plan-tune, codex. Resolved values are
identical, so existing tests cover correctness; the win is consolidating 11
copy-pasted fallback chains behind one helper.
codex/SKILL.md.tmpl gets a new Step 0.6 Resolve portable roots that sources
gstack-paths once, then replaces hardcoded ~/.claude/plans/*.md and
/tmp/codex-*-XXXXXX.txt with "$PLAN_ROOT"/*.md and "$TMP_ROOT/codex-*-XXXXXX.txt".
Hardening direction credited to the McGluut/gstack fork; this is upstream's
factoring of the per-skill chain the fork inlined.
Tests: test/gstack-paths.test.ts covers all three fallback chains with 8 unit
tests (HOME unset, CLAUDE_PLUGIN_DATA set, GSTACK_HOME wins, etc).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1430,7 +1430,8 @@ After counting signals, append a session entry to the builder profile. This is t
|
||||
source of truth for all closing state (tier, resource dedup, journey tracking).
|
||||
|
||||
```bash
|
||||
mkdir -p "${GSTACK_HOME:-$HOME/.gstack}"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
mkdir -p "$GSTACK_STATE_ROOT"
|
||||
```
|
||||
|
||||
Append one JSON line with these fields (substitute actual values from this session):
|
||||
@@ -1445,7 +1446,8 @@ Append one JSON line with these fields (substitute actual values from this sessi
|
||||
- `topics`: array of 2-3 topic keywords that describe what this session was about
|
||||
|
||||
```bash
|
||||
echo '{"date":"TIMESTAMP","mode":"MODE","project_slug":"SLUG","signal_count":N,"signals":SIGNALS_ARRAY,"design_doc":"DOC_PATH","assignment":"ASSIGNMENT_TEXT","resources_shown":[],"topics":TOPICS_ARRAY}' >> "${GSTACK_HOME:-$HOME/.gstack}/builder-profile.jsonl"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
echo '{"date":"TIMESTAMP","mode":"MODE","project_slug":"SLUG","signal_count":N,"signals":SIGNALS_ARRAY,"design_doc":"DOC_PATH","assignment":"ASSIGNMENT_TEXT","resources_shown":[],"topics":TOPICS_ARRAY}' >> "$GSTACK_STATE_ROOT/builder-profile.jsonl"
|
||||
```
|
||||
|
||||
This entry is append-only. The `resources_shown` field will be updated via a second append
|
||||
@@ -1803,7 +1805,8 @@ This must feel earned, not broadcast. If the evidence doesn't support it, skip e
|
||||
with a narrative arc (not a data table). The arc tells the STORY of their journey in
|
||||
second person, referencing specific things they said across sessions. Then open it:
|
||||
```bash
|
||||
open "${GSTACK_HOME:-$HOME/.gstack}/builder-journey.md"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
open "$GSTACK_STATE_ROOT/builder-journey.md"
|
||||
```
|
||||
|
||||
Then proceed to Founder Resources below.
|
||||
@@ -1905,7 +1908,8 @@ PAUL GRAHAM ESSAYS:
|
||||
1. Log the selected resource URLs to the builder profile (single source of truth).
|
||||
Append a resource-tracking entry:
|
||||
```bash
|
||||
echo '{"date":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","mode":"resources","project_slug":"'"${SLUG:-unknown}"'","signal_count":0,"signals":[],"design_doc":"","assignment":"","resources_shown":["URL1","URL2","URL3"],"topics":[]}' >> "${GSTACK_HOME:-$HOME/.gstack}/builder-profile.jsonl"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
echo '{"date":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","mode":"resources","project_slug":"'"${SLUG:-unknown}"'","signal_count":0,"signals":[],"design_doc":"","assignment":"","resources_shown":["URL1","URL2","URL3"],"topics":[]}' >> "$GSTACK_STATE_ROOT/builder-profile.jsonl"
|
||||
```
|
||||
|
||||
2. Log the selection to analytics:
|
||||
|
||||
@@ -445,7 +445,8 @@ After counting signals, append a session entry to the builder profile. This is t
|
||||
source of truth for all closing state (tier, resource dedup, journey tracking).
|
||||
|
||||
```bash
|
||||
mkdir -p "${GSTACK_HOME:-$HOME/.gstack}"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
mkdir -p "$GSTACK_STATE_ROOT"
|
||||
```
|
||||
|
||||
Append one JSON line with these fields (substitute actual values from this session):
|
||||
@@ -460,7 +461,8 @@ Append one JSON line with these fields (substitute actual values from this sessi
|
||||
- `topics`: array of 2-3 topic keywords that describe what this session was about
|
||||
|
||||
```bash
|
||||
echo '{"date":"TIMESTAMP","mode":"MODE","project_slug":"SLUG","signal_count":N,"signals":SIGNALS_ARRAY,"design_doc":"DOC_PATH","assignment":"ASSIGNMENT_TEXT","resources_shown":[],"topics":TOPICS_ARRAY}' >> "${GSTACK_HOME:-$HOME/.gstack}/builder-profile.jsonl"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
echo '{"date":"TIMESTAMP","mode":"MODE","project_slug":"SLUG","signal_count":N,"signals":SIGNALS_ARRAY,"design_doc":"DOC_PATH","assignment":"ASSIGNMENT_TEXT","resources_shown":[],"topics":TOPICS_ARRAY}' >> "$GSTACK_STATE_ROOT/builder-profile.jsonl"
|
||||
```
|
||||
|
||||
This entry is append-only. The `resources_shown` field will be updated via a second append
|
||||
@@ -758,7 +760,8 @@ This must feel earned, not broadcast. If the evidence doesn't support it, skip e
|
||||
with a narrative arc (not a data table). The arc tells the STORY of their journey in
|
||||
second person, referencing specific things they said across sessions. Then open it:
|
||||
```bash
|
||||
open "${GSTACK_HOME:-$HOME/.gstack}/builder-journey.md"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
open "$GSTACK_STATE_ROOT/builder-journey.md"
|
||||
```
|
||||
|
||||
Then proceed to Founder Resources below.
|
||||
@@ -860,7 +863,8 @@ PAUL GRAHAM ESSAYS:
|
||||
1. Log the selected resource URLs to the builder profile (single source of truth).
|
||||
Append a resource-tracking entry:
|
||||
```bash
|
||||
echo '{"date":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","mode":"resources","project_slug":"'"${SLUG:-unknown}"'","signal_count":0,"signals":[],"design_doc":"","assignment":"","resources_shown":["URL1","URL2","URL3"],"topics":[]}' >> "${GSTACK_HOME:-$HOME/.gstack}/builder-profile.jsonl"
|
||||
eval "$(~/.claude/skills/gstack/bin/gstack-paths)"
|
||||
echo '{"date":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","mode":"resources","project_slug":"'"${SLUG:-unknown}"'","signal_count":0,"signals":[],"design_doc":"","assignment":"","resources_shown":["URL1","URL2","URL3"],"topics":[]}' >> "$GSTACK_STATE_ROOT/builder-profile.jsonl"
|
||||
```
|
||||
|
||||
2. Log the selection to analytics:
|
||||
|
||||
Reference in New Issue
Block a user