mirror of
https://github.com/garrytan/gstack.git
synced 2026-05-01 19:25:10 +02:00
feat: inline /office-hours — no more "another window" (v0.11.3.1) (#352)
* feat: inline /office-hours invocation — no more "another window" BENEFITS_FROM now uses read-and-follow pattern (same as /autoplan) to run /office-hours inline. Removes handoff note save infrastructure from plan-ceo-review template. Keeps handoff note check for backward compat. * chore: bump version and changelog (v0.11.3.1) Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -1,5 +1,12 @@
|
||||
# Changelog
|
||||
|
||||
## [0.11.5.1] - 2026-03-23 — Inline Office Hours
|
||||
|
||||
### Changed
|
||||
|
||||
- **No more "open another window" for /office-hours.** When `/plan-ceo-review` or `/plan-eng-review` offer to run `/office-hours` first, it now runs inline in the same conversation. The review picks up right where it left off after the design doc is ready. Same for mid-session detection when you're still figuring out what to build.
|
||||
- **Handoff note infrastructure removed.** The handoff notes that bridged the old "go to another window" flow are no longer written. Existing notes from prior sessions are still read for backward compatibility.
|
||||
|
||||
## [0.11.5.0] - 2026-03-23 — Bash Compatibility Fix
|
||||
|
||||
### Fixed
|
||||
|
||||
+33
-1
@@ -331,12 +331,44 @@ Say to the user via AskUserQuestion:
|
||||
> not per-product — it captures the thinking behind this specific change."
|
||||
|
||||
Options:
|
||||
- A) Run /office-hours first (in another window, then come back)
|
||||
- A) Run /office-hours now (we'll pick up the review right after)
|
||||
- B) Skip — proceed with standard review
|
||||
|
||||
If they skip: "No worries — standard review. If you ever want sharper input, try
|
||||
/office-hours first next time." Then proceed normally. Do not re-offer later in the session.
|
||||
|
||||
If they choose A:
|
||||
|
||||
Say: "Running /office-hours inline. Once the design doc is ready, I'll pick up
|
||||
the review right where we left off."
|
||||
|
||||
Read the office-hours skill file from disk using the Read tool:
|
||||
`~/.claude/skills/gstack/office-hours/SKILL.md`
|
||||
|
||||
Follow it inline, **skipping these sections** (already handled by the parent skill):
|
||||
- Preamble (run first)
|
||||
- AskUserQuestion Format
|
||||
- Completeness Principle — Boil the Lake
|
||||
- Search Before Building
|
||||
- Contributor Mode
|
||||
- Completion Status Protocol
|
||||
- Telemetry (run last)
|
||||
|
||||
If the Read fails (file not found), say:
|
||||
"Could not load /office-hours — proceeding with standard review."
|
||||
|
||||
After /office-hours completes, re-run the design doc check:
|
||||
```bash
|
||||
SLUG=$(~/.claude/skills/gstack/browse/bin/remote-slug 2>/dev/null || basename "$(git rev-parse --show-toplevel 2>/dev/null || pwd)")
|
||||
BRANCH=$(git rev-parse --abbrev-ref HEAD 2>/dev/null | tr '/' '-' || echo 'no-branch')
|
||||
DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-$BRANCH-design-*.md 2>/dev/null | head -1)
|
||||
[ -z "$DESIGN" ] && DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-design-*.md 2>/dev/null | head -1)
|
||||
[ -n "$DESIGN" ] && echo "Design doc found: $DESIGN" || echo "No design doc found"
|
||||
```
|
||||
|
||||
If a design doc is now found, read it and continue the review.
|
||||
If none was produced (user may have cancelled), proceed with standard review.
|
||||
|
||||
# /autoplan — Auto-Review Pipeline
|
||||
|
||||
One command. Rough plan in, fully reviewed plan out.
|
||||
|
||||
+40
-41
@@ -432,65 +432,64 @@ Say to the user via AskUserQuestion:
|
||||
> not per-product — it captures the thinking behind this specific change."
|
||||
|
||||
Options:
|
||||
- A) Run /office-hours first (in another window, then come back)
|
||||
- A) Run /office-hours now (we'll pick up the review right after)
|
||||
- B) Skip — proceed with standard review
|
||||
|
||||
If they skip: "No worries — standard review. If you ever want sharper input, try
|
||||
/office-hours first next time." Then proceed normally. Do not re-offer later in the session.
|
||||
|
||||
**Handoff note save (BENEFITS_FROM):** If the user chose A (run /office-hours first),
|
||||
save a handoff context note before they leave. Reuse $SLUG and $BRANCH from the
|
||||
design doc check block above (they use the same `remote-slug || basename` fallback
|
||||
that handles repos without an origin remote). Then run:
|
||||
If they choose A:
|
||||
|
||||
Say: "Running /office-hours inline. Once the design doc is ready, I'll pick up
|
||||
the review right where we left off."
|
||||
|
||||
Read the office-hours skill file from disk using the Read tool:
|
||||
`~/.claude/skills/gstack/office-hours/SKILL.md`
|
||||
|
||||
Follow it inline, **skipping these sections** (already handled by the parent skill):
|
||||
- Preamble (run first)
|
||||
- AskUserQuestion Format
|
||||
- Completeness Principle — Boil the Lake
|
||||
- Search Before Building
|
||||
- Contributor Mode
|
||||
- Completion Status Protocol
|
||||
- Telemetry (run last)
|
||||
|
||||
If the Read fails (file not found), say:
|
||||
"Could not load /office-hours — proceeding with standard review."
|
||||
|
||||
After /office-hours completes, re-run the design doc check:
|
||||
```bash
|
||||
mkdir -p ~/.gstack/projects/$SLUG
|
||||
USER=$(whoami)
|
||||
DATETIME=$(date +%Y%m%d-%H%M%S)
|
||||
```
|
||||
Write to `~/.gstack/projects/$SLUG/$USER-$BRANCH-ceo-handoff-$DATETIME.md`:
|
||||
```markdown
|
||||
# CEO Review Handoff Note
|
||||
|
||||
Generated by /plan-ceo-review on {date}
|
||||
Branch: {branch}
|
||||
Repo: {owner/repo}
|
||||
|
||||
## Why I paused
|
||||
User chose to run /office-hours first (no design doc found).
|
||||
|
||||
## System Audit Summary
|
||||
{Summarize what the system audit found — recent git history, diff scope,
|
||||
CLAUDE.md key points, TODOS.md relevant items, known pain points}
|
||||
|
||||
## Discussion So Far
|
||||
{Empty — handoff happened before Step 0. Frontend/UI scope detection has not
|
||||
run yet — it will be assessed when the review resumes.}
|
||||
SLUG=$(~/.claude/skills/gstack/browse/bin/remote-slug 2>/dev/null || basename "$(git rev-parse --show-toplevel 2>/dev/null || pwd)")
|
||||
BRANCH=$(git rev-parse --abbrev-ref HEAD 2>/dev/null | tr '/' '-' || echo 'no-branch')
|
||||
DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-$BRANCH-design-*.md 2>/dev/null | head -1)
|
||||
[ -z "$DESIGN" ] && DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-design-*.md 2>/dev/null | head -1)
|
||||
[ -n "$DESIGN" ] && echo "Design doc found: $DESIGN" || echo "No design doc found"
|
||||
```
|
||||
|
||||
Tell the user: "Context saved. Run /office-hours in another window. When you come back
|
||||
and invoke /plan-ceo-review, I'll pick up the context automatically — including the
|
||||
design doc /office-hours produces."
|
||||
If a design doc is now found, read it and continue the review.
|
||||
If none was produced (user may have cancelled), proceed with standard review.
|
||||
|
||||
**Mid-session detection:** During Step 0A (Premise Challenge), if the user can't
|
||||
articulate the problem, keeps changing the problem statement, answers with "I'm not
|
||||
sure," or is clearly exploring rather than reviewing — offer `/office-hours`:
|
||||
|
||||
> "It sounds like you're still figuring out what to build — that's totally fine, but
|
||||
> that's what /office-hours is designed for. Want to pause this review and run
|
||||
> /office-hours first? It'll help you nail down the problem and approach, then come
|
||||
> back here for the strategic review."
|
||||
> that's what /office-hours is designed for. Want to run /office-hours right now?
|
||||
> We'll pick up right where we left off."
|
||||
|
||||
Options: A) Yes, run /office-hours first. B) No, keep going.
|
||||
Options: A) Yes, run /office-hours now. B) No, keep going.
|
||||
If they keep going, proceed normally — no guilt, no re-asking.
|
||||
|
||||
**Handoff note save (mid-session):** If the user chose A (run /office-hours first from
|
||||
mid-session detection), save a handoff context note with the same format above, but
|
||||
include any Step 0A progress in the "Discussion So Far" section — premises discussed,
|
||||
problem framing attempts, user answers so far. Use the same bash block to generate the
|
||||
file path.
|
||||
If they choose A: Read the office-hours skill file from disk:
|
||||
`~/.claude/skills/gstack/office-hours/SKILL.md`
|
||||
|
||||
Tell the user: "Context saved with your discussion so far. Run /office-hours, then
|
||||
come back to /plan-ceo-review."
|
||||
Follow it inline, skipping these sections (already handled by parent skill):
|
||||
Preamble, AskUserQuestion Format, Completeness Principle, Search Before Building,
|
||||
Contributor Mode, Completion Status Protocol, Telemetry.
|
||||
|
||||
Note current Step 0A progress so you don't re-ask questions already answered.
|
||||
After completion, re-run the design doc check and resume the review.
|
||||
|
||||
When reading TODOS.md, specifically:
|
||||
* Note any TODOs this plan touches, blocks, or unlocks
|
||||
|
||||
@@ -129,59 +129,26 @@ context to pick up where we left off."
|
||||
|
||||
{{BENEFITS_FROM}}
|
||||
|
||||
**Handoff note save (BENEFITS_FROM):** If the user chose A (run /office-hours first),
|
||||
save a handoff context note before they leave. Reuse $SLUG and $BRANCH from the
|
||||
design doc check block above (they use the same `remote-slug || basename` fallback
|
||||
that handles repos without an origin remote). Then run:
|
||||
```bash
|
||||
mkdir -p ~/.gstack/projects/$SLUG
|
||||
USER=$(whoami)
|
||||
DATETIME=$(date +%Y%m%d-%H%M%S)
|
||||
```
|
||||
Write to `~/.gstack/projects/$SLUG/$USER-$BRANCH-ceo-handoff-$DATETIME.md`:
|
||||
```markdown
|
||||
# CEO Review Handoff Note
|
||||
|
||||
Generated by /plan-ceo-review on {date}
|
||||
Branch: {branch}
|
||||
Repo: {owner/repo}
|
||||
|
||||
## Why I paused
|
||||
User chose to run /office-hours first (no design doc found).
|
||||
|
||||
## System Audit Summary
|
||||
{Summarize what the system audit found — recent git history, diff scope,
|
||||
CLAUDE.md key points, TODOS.md relevant items, known pain points}
|
||||
|
||||
## Discussion So Far
|
||||
{Empty — handoff happened before Step 0. Frontend/UI scope detection has not
|
||||
run yet — it will be assessed when the review resumes.}
|
||||
```
|
||||
|
||||
Tell the user: "Context saved. Run /office-hours in another window. When you come back
|
||||
and invoke /plan-ceo-review, I'll pick up the context automatically — including the
|
||||
design doc /office-hours produces."
|
||||
|
||||
**Mid-session detection:** During Step 0A (Premise Challenge), if the user can't
|
||||
articulate the problem, keeps changing the problem statement, answers with "I'm not
|
||||
sure," or is clearly exploring rather than reviewing — offer `/office-hours`:
|
||||
|
||||
> "It sounds like you're still figuring out what to build — that's totally fine, but
|
||||
> that's what /office-hours is designed for. Want to pause this review and run
|
||||
> /office-hours first? It'll help you nail down the problem and approach, then come
|
||||
> back here for the strategic review."
|
||||
> that's what /office-hours is designed for. Want to run /office-hours right now?
|
||||
> We'll pick up right where we left off."
|
||||
|
||||
Options: A) Yes, run /office-hours first. B) No, keep going.
|
||||
Options: A) Yes, run /office-hours now. B) No, keep going.
|
||||
If they keep going, proceed normally — no guilt, no re-asking.
|
||||
|
||||
**Handoff note save (mid-session):** If the user chose A (run /office-hours first from
|
||||
mid-session detection), save a handoff context note with the same format above, but
|
||||
include any Step 0A progress in the "Discussion So Far" section — premises discussed,
|
||||
problem framing attempts, user answers so far. Use the same bash block to generate the
|
||||
file path.
|
||||
If they choose A: Read the office-hours skill file from disk:
|
||||
`~/.claude/skills/gstack/office-hours/SKILL.md`
|
||||
|
||||
Tell the user: "Context saved with your discussion so far. Run /office-hours, then
|
||||
come back to /plan-ceo-review."
|
||||
Follow it inline, skipping these sections (already handled by parent skill):
|
||||
Preamble, AskUserQuestion Format, Completeness Principle, Search Before Building,
|
||||
Contributor Mode, Completion Status Protocol, Telemetry.
|
||||
|
||||
Note current Step 0A progress so you don't re-ask questions already answered.
|
||||
After completion, re-run the design doc check and resume the review.
|
||||
|
||||
When reading TODOS.md, specifically:
|
||||
* Note any TODOs this plan touches, blocks, or unlocks
|
||||
|
||||
@@ -363,12 +363,44 @@ Say to the user via AskUserQuestion:
|
||||
> not per-product — it captures the thinking behind this specific change."
|
||||
|
||||
Options:
|
||||
- A) Run /office-hours first (in another window, then come back)
|
||||
- A) Run /office-hours now (we'll pick up the review right after)
|
||||
- B) Skip — proceed with standard review
|
||||
|
||||
If they skip: "No worries — standard review. If you ever want sharper input, try
|
||||
/office-hours first next time." Then proceed normally. Do not re-offer later in the session.
|
||||
|
||||
If they choose A:
|
||||
|
||||
Say: "Running /office-hours inline. Once the design doc is ready, I'll pick up
|
||||
the review right where we left off."
|
||||
|
||||
Read the office-hours skill file from disk using the Read tool:
|
||||
`~/.claude/skills/gstack/office-hours/SKILL.md`
|
||||
|
||||
Follow it inline, **skipping these sections** (already handled by the parent skill):
|
||||
- Preamble (run first)
|
||||
- AskUserQuestion Format
|
||||
- Completeness Principle — Boil the Lake
|
||||
- Search Before Building
|
||||
- Contributor Mode
|
||||
- Completion Status Protocol
|
||||
- Telemetry (run last)
|
||||
|
||||
If the Read fails (file not found), say:
|
||||
"Could not load /office-hours — proceeding with standard review."
|
||||
|
||||
After /office-hours completes, re-run the design doc check:
|
||||
```bash
|
||||
SLUG=$(~/.claude/skills/gstack/browse/bin/remote-slug 2>/dev/null || basename "$(git rev-parse --show-toplevel 2>/dev/null || pwd)")
|
||||
BRANCH=$(git rev-parse --abbrev-ref HEAD 2>/dev/null | tr '/' '-' || echo 'no-branch')
|
||||
DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-$BRANCH-design-*.md 2>/dev/null | head -1)
|
||||
[ -z "$DESIGN" ] && DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-design-*.md 2>/dev/null | head -1)
|
||||
[ -n "$DESIGN" ] && echo "Design doc found: $DESIGN" || echo "No design doc found"
|
||||
```
|
||||
|
||||
If a design doc is now found, read it and continue the review.
|
||||
If none was produced (user may have cancelled), proceed with standard review.
|
||||
|
||||
### Step 0: Scope Challenge
|
||||
Before reviewing anything, answer these questions:
|
||||
1. **What existing code already partially or fully solves each sub-problem?** Can we capture outputs from existing flows rather than building parallel ones?
|
||||
|
||||
@@ -2021,11 +2021,43 @@ Say to the user via AskUserQuestion:
|
||||
> not per-product — it captures the thinking behind this specific change."
|
||||
|
||||
Options:
|
||||
- A) Run /${first} first (in another window, then come back)
|
||||
- A) Run /${first} now (we'll pick up the review right after)
|
||||
- B) Skip — proceed with standard review
|
||||
|
||||
If they skip: "No worries — standard review. If you ever want sharper input, try
|
||||
/${first} first next time." Then proceed normally. Do not re-offer later in the session.`;
|
||||
/${first} first next time." Then proceed normally. Do not re-offer later in the session.
|
||||
|
||||
If they choose A:
|
||||
|
||||
Say: "Running /${first} inline. Once the design doc is ready, I'll pick up
|
||||
the review right where we left off."
|
||||
|
||||
Read the ${first} skill file from disk using the Read tool:
|
||||
\`~/.claude/skills/gstack/${first}/SKILL.md\`
|
||||
|
||||
Follow it inline, **skipping these sections** (already handled by the parent skill):
|
||||
- Preamble (run first)
|
||||
- AskUserQuestion Format
|
||||
- Completeness Principle — Boil the Lake
|
||||
- Search Before Building
|
||||
- Contributor Mode
|
||||
- Completion Status Protocol
|
||||
- Telemetry (run last)
|
||||
|
||||
If the Read fails (file not found), say:
|
||||
"Could not load /${first} — proceeding with standard review."
|
||||
|
||||
After /${first} completes, re-run the design doc check:
|
||||
\`\`\`bash
|
||||
SLUG=$(~/.claude/skills/gstack/browse/bin/remote-slug 2>/dev/null || basename "$(git rev-parse --show-toplevel 2>/dev/null || pwd)")
|
||||
BRANCH=$(git rev-parse --abbrev-ref HEAD 2>/dev/null | tr '/' '-' || echo 'no-branch')
|
||||
DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-$BRANCH-design-*.md 2>/dev/null | head -1)
|
||||
[ -z "$DESIGN" ] && DESIGN=$(ls -t ~/.gstack/projects/$SLUG/*-design-*.md 2>/dev/null | head -1)
|
||||
[ -n "$DESIGN" ] && echo "Design doc found: $DESIGN" || echo "No design doc found"
|
||||
\`\`\`
|
||||
|
||||
If a design doc is now found, read it and continue the review.
|
||||
If none was produced (user may have cancelled), proceed with standard review.`;
|
||||
}
|
||||
|
||||
function generateDesignSketch(_ctx: TemplateContext): string {
|
||||
|
||||
@@ -773,6 +773,16 @@ describe('BENEFITS_FROM resolver', () => {
|
||||
const qaContent = fs.readFileSync(path.join(ROOT, 'qa', 'SKILL.md'), 'utf-8');
|
||||
expect(qaContent).not.toContain('Prerequisite Skill Offer');
|
||||
});
|
||||
|
||||
test('inline invocation — no "another window" language', () => {
|
||||
expect(ceoContent).not.toContain('another window');
|
||||
expect(engContent).not.toContain('another window');
|
||||
});
|
||||
|
||||
test('inline invocation — read-and-follow path present', () => {
|
||||
expect(ceoContent).toContain('office-hours/SKILL.md');
|
||||
expect(engContent).toContain('office-hours/SKILL.md');
|
||||
});
|
||||
});
|
||||
|
||||
// --- {{DESIGN_OUTSIDE_VOICES}} resolver tests ---
|
||||
|
||||
Reference in New Issue
Block a user