You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Add per-question `roles` + `priority` to Question. Both quick and full
modes now filter to the user's role and ask at most MAX_QUESTIONS (10),
keeping the highest-priority questions — roughly 5 shared fundamentals +
5 role-specialty per role. Sections become purely thematic grouping;
role logic lives on the questions.
- session.ts: filterByRole + selectSections (role filter then top-10 cap)
- checklists.ts: review/retag every quick + full question with roles + priority
- stack.ts: priority on each candidate so stack questions compete for slots
- cli.ts: roleSections (uncapped, for --list) + buildSections (capped, for sessions)
- index.ts: export selectSections, filterByRole, MAX_QUESTIONS
- README/CLAUDE: document the model; bump 0.3.0 -> 0.4.0
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Copy file name to clipboardExpand all lines: CLAUDE.md
+23-10Lines changed: 23 additions & 10 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -6,8 +6,10 @@ Guidance for working in this repository.
6
6
7
7
`think-before` — a small, **zero-runtime-dependency** TypeScript CLI published to npm. It walks a developer through a fast yes/no checklist *before* they make a change, so the side-effects of "simple" changes surface on the whiteboard instead of in production.
8
8
9
-
-**`quick` mode (default)** — ~15 blast-radius questions for the "I'm about to touch the big app" moment.
10
-
-**`full` mode** — a full pre-development discovery checklist, with `--role designer|engineer|developer` to filter (shared sections always shown).
9
+
-**`quick` mode (default)** — blast-radius questions for the "I'm about to touch the big app" moment.
Both modes are **role-tailored and capped at 10 questions** (`MAX_QUESTIONS` in `src/session.ts`). Every `Question` declares the `roles` it applies to (omit = everyone) and a `priority`; `--role designer|engineer|developer` filters to the matching questions, and when more than 10 are eligible the highest-priority ones win. The aim is ~5 shared fundamentals + ~5 role-specialty per role.
11
13
12
14
Answers are single keypresses (`y`/`n`/`s`/`?`/`q`). On a real terminal it runs **full-screen** (alternate screen buffer, classic-installer style, one boxed question at a time); piped/non-TTY input auto-falls back to scrolling **line mode**. Risky answers get flagged; the user gets a summary and an optional Markdown report.
13
15
@@ -33,13 +35,13 @@ ESM, `module: NodeNext`. Source in `src/`, compiled to `dist/`. Relative imports
|`src/checklists.ts`|**The content.** The `quick` and `full` checklist data. This is where base questions are added/edited. |
38
+
|`src/checklists.ts`|**The content.** The `quick` and `full` checklist data. This is where base questions are added/edited. Each question carries `roles` (omit = everyone) + `priority` (higher = asked first). Sections are now purely thematic grouping (`roles: ["shared"]`); role logic lives on the questions. |
37
39
|`src/detect.ts`| Read-only project scan. `detectProject`/`safeDetect` classify the cwd as frontend/backend/fullstack/unknown by matching framework deps + marker files; `kindLabel` formats it. |
38
40
|`src/stack.ts`| The stack-specific question bank. `stackSection(detection, role)` builds an extra `Section` of questions relevant to the detected stack, filtered by role. |
39
41
|`src/config.ts`| User-level persistence at `~/.config/think-before/config.json` (honors `$XDG_CONFIG_HOME`). Stores per-project role + detection. |
40
42
|`src/prompt.ts`| Single-keypress prompts: `askYesNo` and `askChoice` (role picker), with a shared non-TTY line-reader fallback for piped/CI input. Used by **line mode**. |
41
43
|`src/tui.ts`| The full-screen (alternate-screen-buffer) installer-style UI. `runTui` drives role → welcome → one boxed question per screen → final, and **always restores the terminal**. `tuiAvailable()` gates it on a real TTY. |
42
-
|`src/session.ts`|`runSession` (drives the **line-mode** prompts, records + flags answers) and `filterSections` (role filtering). |
44
+
|`src/session.ts`|`runSession` (drives the **line-mode** prompts, records + flags answers); `filterSections` (section-level role filter); `filterByRole` (per-question role filter) + `selectSections` (role filter then cap to the top `MAX_QUESTIONS` by priority). |
43
45
|`src/report.ts`| Terminal summary (`printSummary`), Markdown report (`buildMarkdown`/`saveReport`), and `printList`. |
44
46
|`src/cli.ts`| Entry point (`bin`). Arg parsing, help/version, detection, role resolution + persistence, `config` mode, orchestration, save logic. |
45
47
|`src/index.ts`| Public library API (re-exports for programmatic use). |
@@ -48,14 +50,14 @@ Data flow: `cli` parses args → `safeDetect(cwd)` → resolve role (flag > save
48
50
-**TUI** (default on a real TTY): `runTui` asks for role if unknown, shows a welcome/detection screen, runs the questions full-screen, returns the `SessionResult` + chosen role. `cli` then persists, and prints the detection banner + `printSummary` into the *restored* terminal.
49
51
-**Line mode** (piped/non-TTY, or `--no-tui`): `askRole` if needed → banner → `runSession`.
50
52
51
-
Both then share `printSummary` → optional `buildMarkdown`/`saveReport`. Sections are built by a shared `buildSections(role)`closure (`filterSections` + append `stackSection`) so both modes stay in sync. `--list` always uses line mode.
53
+
Both then share `printSummary` → optional `buildMarkdown`/`saveReport`. Sections are built by two shared closures in `cli.ts`: `roleSections(role)` (`filterSections` + append `stackSection` + `filterByRole`) is the full role-relevant set, and `buildSections(role)` wraps it in `selectSections` to cap at 10. Sessions (TUI + line) use `buildSections`; `--list` uses `roleSections` (uncapped, the full reference for a role) and always uses line mode.
52
54
53
55
## Conventions & gotchas
54
56
55
-
-**Editing questions:** each `Question` declares `risky: "yes" | "no"` (which answer raises a flag) and an optional `why` (shown on `?` and beside flags). Keep questions phrased so a yes/no answer is meaningful. Most `full` questions are "Have you / do you know…" so a `no` is the gap.
56
-
-**Stack questions** live in `src/stack.ts` as `CANDIDATES`, each with `roles` (who it applies to) and a `when(detection)` predicate. To support a new framework, add its dep/marker to the maps in `src/detect.ts`; to add a tailored question, add a `CANDIDATES` entry. Detection is **read-only and must never throw** — `safeDetect` swallows errors, and `detectProject` only reads a handful of manifest files + checks marker folders (it peeks one level into `apps/`/`packages/`/`services/` for monorepos).
57
+
-**Editing questions:** each `Question` declares `risky: "yes" | "no"` (which answer raises a flag), an optional `why` (shown on `?` and beside flags), the `roles` it applies to (omit = everyone), and a `priority`. Keep questions phrased so a yes/no answer is meaningful. Most `full` questions are "Have you / do you know…" so a `no` is the gap. **Mind the cap:** only the top `MAX_QUESTIONS` (10) by priority per role are asked — when adding a question, set a priority that reflects whether it should displace an existing one for that role. Aim to keep each role at roughly 5 shared + 5 specialty in the top 10 (eyeball it with `--role X --list` for the full set and a piped session for the capped set).
58
+
-**Stack questions** live in `src/stack.ts` as `CANDIDATES`, each with `roles` (who it applies to), a `when(detection)` predicate, and a `priority` (last arg to the `q()` helper) so they compete with base questions for the 10 slots. To support a new framework, add its dep/marker to the maps in `src/detect.ts`; to add a tailored question, add a `CANDIDATES` entry. Detection is **read-only and must never throw** — `safeDetect` swallows errors, and `detectProject` only reads a handful of manifest files + checks marker folders (it peeks one level into `apps/`/`packages/`/`services/` for monorepos).
57
59
-**Config persistence is best-effort:**`saveConfig` may fail on a read-only home; `cli.ts` wraps it in try/catch and continues. Don't make a run depend on config being writable. Tests should set `XDG_CONFIG_HOME` to a temp dir to avoid touching the real `~/.config`.
58
-
-**Role** is resolved as: `--role` flag > saved per-project role > `defaultRole` > interactive `askChoice` (TTY only). In non-TTY with nothing saved, role stays `undefined`(all sections shown). Role now affects `quick` mode too (it filters the stack section), so don't reintroduce the old "role only affects full mode" guard.
60
+
-**Role** is resolved as: `--role` flag > saved per-project role > `defaultRole` > interactive `askChoice` (TTY only). In non-TTY with nothing saved, role stays `undefined`— then **all** questions are eligible and the cap returns a cross-role top 10 (a sensible "pick a role for a tailored set" fallback). Role now drives **both** modes via per-question `roles` (not just the stack section), so don't reintroduce the old "role only affects full mode" guard.
59
61
-**Zero runtime dependencies — keep it that way.** Colors are hand-rolled ANSI in `colors.ts`; prompts use Node's `readline` directly. Don't add runtime deps without a strong reason.
60
62
-**Non-TTY input** uses ONE shared `readline` interface (`src/prompt.ts`). Do not create a `readline` interface per question — that drops buffered piped input. Call `closeInput()` at the end so the process can exit.
61
63
-**TUI terminal restoration is sacred.**`src/tui.ts` enters the alternate screen + raw mode + hides the cursor; `restore()` must undo all of it. It's idempotent and wired to `finally`, `process.on("exit")`, and SIGINT/SIGTERM handlers — keep all those paths. In raw mode `Ctrl-C` arrives as a `ctrl+c`*keypress* (ISIG is off), normalized to `"quit"` like `q`; the signal handlers are backstops. If you add a new early-return/throw inside `runTui`, the `finally` already covers it — don't bypass it. Testing the TUI needs a PTY (`expect`); piped input can't exercise it (it falls back to line mode by design).
@@ -81,7 +83,18 @@ Published as **`@geekyants/think-before`** (scoped). The installed binary is sti
81
83
82
84
`prepublishOnly` runs the build. `files` ships only `dist/`, `README.md`, `LICENSE`. `publishConfig.access` is `public` so the scoped package publishes publicly (scoped packages default to private/paid).
83
85
86
+
**Publish via GitHub Actions, not from your laptop.**`.github/workflows/release.yml` publishes to npm when a `vX.Y.Z` tag is pushed. It uses an org **Automation** npm token (repo secret `NPM_TOKEN`) which bypasses 2FA/OTP — a local `npm publish` will fail on an OTP prompt. The workflow verifies the tag matches `package.json` version, builds, publishes with `--provenance`, and creates a GitHub Release.
87
+
88
+
To cut a release:
89
+
90
+
```bash
91
+
npm version patch # (or minor/major) bumps package.json + makes a vX.Y.Z commit & tag
92
+
git push --follow-tags # pushing the tag triggers the Release workflow
93
+
```
94
+
95
+
If the version was already bumped by hand (package.json edited, committed), just tag and push the tag to match:
96
+
84
97
```bash
85
-
npm login # must be a member of the @geekyants npm org
86
-
npm publish # access:public is already set in package.json
98
+
git tag v$(node -p "require('./package.json').version")
Copy file name to clipboardExpand all lines: README.md
+13-12Lines changed: 13 additions & 12 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -38,15 +38,15 @@ think-before # the installed command is just `think-be
38
38
39
39
| Mode | What it's for |
40
40
| --- | --- |
41
-
|`quick`*(default)*| The "I'm about to touch the big app" moment. ~16 sharp questions about blast radius, data, contracts, your safety net, and timing. |
42
-
|`full`| A team-level pre-development discovery sweep: problem, users, scope, risks, plus role sections for designers, engineers, and developers. |
41
+
|`quick`*(default)*| The "I'm about to touch the big app" moment. Blast radius, data, contracts, your safety net, and timing. |
42
+
|`full`| A team-level pre-development discovery sweep: problem, users, scope, risks, plus the questions specific to your role. |
43
43
44
-
In `full` mode you can focus on one role (shared sections are always included):
44
+
Both modes ask **at most 10 questions** — the ones most relevant to *you*. Every question is tagged with the roles it applies to and a priority; pick a role and you get your fundamentals plus your own specialty, never a wall of questions meant for someone else:
think-before full --role engineer# discovery, architecture-focused
49
+
think-before full --role developer# discovery, implementation-focused
50
50
```
51
51
52
52
## Smart, stack-aware questions
@@ -72,7 +72,7 @@ Skip the scan anytime with `--no-detect`.
72
72
73
73
## Your role & saved config
74
74
75
-
The first time you run it in a project, it asks **what your role is** (designer / engineer / developer) and tailors the stack questions to you. Your answer — plus the detected stack — is remembered per project in:
75
+
The first time you run it in a project, it asks **what your role is** (designer / engineer / developer) and tailors the whole question set to you. Your answer — plus the detected stack — is remembered per project in:
It uses the terminal's alternate screen buffer (like `vim` or `less`), so when you're done — or quit with `q`/`Ctrl-C` — your terminal is restored exactly as it was, and the summary + report prompt print into your normal scrollback.
@@ -151,14 +151,15 @@ The report is plain Markdown — drop it into a PR description, a ticket, or you
@@ -172,7 +173,7 @@ npm run build # compile to dist/
172
173
npm start # run the built CLI
173
174
```
174
175
175
-
Want to add or tweak questions? They live in [`src/checklists.ts`](src/checklists.ts) — each question declares which answer (`yes`/`no`) is the risky one, plus an optional `why`. PRs welcome.
176
+
Want to add or tweak questions? They live in [`src/checklists.ts`](src/checklists.ts) — each question declares which answer (`yes`/`no`) is the risky one, an optional `why`, the `roles` it applies to, and a `priority` (higher = asked first when the 10-question cap kicks in). PRs welcome.
Copy file name to clipboardExpand all lines: package.json
+1-1Lines changed: 1 addition & 1 deletion
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
{
2
2
"name": "@geekyants/think-before",
3
-
"version": "0.3.0",
3
+
"version": "0.4.0",
4
4
"description": "A fast yes/no reflection CLI to surface the side-effects of a change before you make it. Scans your project (frontend/backend/full-stack) and asks stack-relevant questions. Think before you touch the big app.",
0 commit comments