@nurix/etna 0.3.1 → 0.3.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bin/etna.js CHANGED
@@ -12,7 +12,6 @@ import {
12
12
  readFileSync,
13
13
  writeFileSync,
14
14
  renameSync,
15
- copyFileSync,
16
15
  cpSync,
17
16
  readdirSync,
18
17
  lstatSync,
@@ -69,6 +68,18 @@ function backupIfExists(path) {
69
68
  return backup;
70
69
  }
71
70
 
71
+ // Split a CLAUDE.md into its YAML frontmatter (authoring metadata: name, version,
72
+ // plugin, keywords) and its body. The frontmatter is meaningful in the harness
73
+ // source and the bundle, but a consuming project's root CLAUDE.md is a plain
74
+ // router — it must not carry it. Returns { body, version } with leading blank
75
+ // lines after the stripped block removed so the body opens on its first heading.
76
+ function stripFrontmatter(text) {
77
+ const m = text.match(/^---\n([\s\S]*?)\n---\n?/);
78
+ if (!m) return { body: text, version: null };
79
+ const version = (m[1].match(/^version:\s*(\S+)/m) || [])[1] || null;
80
+ return { body: text.slice(m[0].length).replace(/^\n+/, ''), version };
81
+ }
82
+
72
83
  function readJson(path) {
73
84
  if (!existsSync(path)) return {};
74
85
  try {
@@ -153,8 +164,11 @@ async function main(args) {
153
164
  const claudeBackup = backupIfExists(claudeMdDest);
154
165
  if (claudeBackup) console.log(` backed up existing CLAUDE.md → ${claudeBackup}`);
155
166
 
156
- copyFileSync(bundledClaudeMd, claudeMdDest);
157
- console.log(` installed CLAUDE.md → ${claudeMdDest}`);
167
+ const { body: claudeMdBody, version } = stripFrontmatter(readFileSync(bundledClaudeMd, 'utf8'));
168
+ writeFileSync(claudeMdDest, claudeMdBody);
169
+ console.log(
170
+ ` installed CLAUDE.md → ${claudeMdDest}${version ? ` (harness v${version})` : ''}`,
171
+ );
158
172
 
159
173
  for (const sub of PLUGIN_SUBDIRS) {
160
174
  const count = copyHarnessSubdir(
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  name: code
3
3
  description: Canonical Nurix code-project harness (spec v9) — three peer authoring modes (Brainstorming / Spec / Plan), modules as bounded contexts, typed application boundaries, ownership rules. The reference CLAUDE.md every Nurix codebase starts with.
4
- version: 0.2.0
4
+ version: 0.3.5
5
5
  keywords:
6
6
  - harness
7
7
  - code
@@ -14,13 +14,13 @@ plugin: nurix-harness
14
14
 
15
15
  # Agent Instructions
16
16
 
17
- This file defines how AI agents (Claude, GPT, etc.) should work on this project. **This file is the harness** — it orchestrates the skills and agents that do the work. There is no separate "harness" skill.
17
+ This file defines how AI agents (Claude, GPT, etc.) should work on this project. **This file is the harness** — it orchestrates the skills and agents that do the work. There is no separate "harness skill."
18
18
 
19
19
  ---
20
20
 
21
21
  ## Bootstrap
22
22
 
23
- > If `docs/structure.md` is missing in this repo, the repo is **not yet harnessed**. Before any other work: invoke the `documentation` skill to run its baseline (`"baseline this repo"`). Both the baseline and the boundary baseline (`boundary-mapper`, below) can also be re-triggered manually at any time.
23
+ > If `docs/structure.md` is missing in this repo, the repo is **not yet harnessed**. Before any other work: invoke the `documentation` skill to run its baseline (`"baseline this repo"`), then run `boundary-mapper` (`"baseline boundaries"`) to populate `docs/boundaries/`. Pillars are module-local (`docs/modules/{m}/pillars/`), created lazily through Brainstorming Mode — not scaffolded up front. Re-trigger either baseline manually any time.
24
24
 
25
25
  This bootstrap is the only step that runs **before** the harness exists. Everything else below assumes a baselined repo.
26
26
 
@@ -28,181 +28,126 @@ This bootstrap is the only step that runs **before** the harness exists. Everyth
28
28
 
29
29
  ## Getting Started
30
30
 
31
- - Read **[`docs/README.md`](docs/README.md)** for documentation root (architecture, features, operations, history)
32
- - Read **[`docs/memory/`](docs/memory/)** for agent memory files (one per agent + `main.md` for shared project memory)
33
- - Ignore **[`README.md`](README.md)** — it's for human reference only
34
- - Check **[`package.json`](package.json)** for available scripts. **Detect the package manager from the lockfile** (`pnpm-lock.yaml` → pnpm, `yarn.lock` → yarn, `package-lock.json` → npm) and use the matching command. Don't hardcode a specific manager.
31
+ - Read **[`docs/README.md`](docs/README.md)** for documentation root (architecture, features, operations)
32
+ - Read **[`docs/memory/`](docs/memory/)** for agent memory files (one per agent)
33
+ - Ignore **[`README.md`](README.md)** – it's for human reference only
34
+ - Check **[`package.json`](package.json)** for available scripts. Detect the package manager from the lockfile (`pnpm-lock.yaml` → pnpm, `yarn.lock` → yarn, `package-lock.json` → npm) and use the matching command. Don't hardcode a specific manager.
35
35
  - Look at similar modules/files and follow existing patterns
36
+
36
37
  - Check **[`.claude/rules/`](.claude/rules/)** for specialized instructions (automatically loaded into memory)
37
38
 
38
39
  ---
39
40
 
40
41
  ## Workflows
41
42
 
42
- Three peer modes. Each names what triggers entry, which agent + skill implement it, and how it exits.
43
-
44
- ```
45
- ┌──────────────────────────┐ ┌──────────────────────────┐
46
- │ Brainstorming Mode │◀────▶│ Spec Mode │
47
- │ (30k-foot strategy, │ │ (feature SSoT) │
48
- │ shapes module pillars │ │ │
49
- │ + the IA boundary) │ │ spec-mode agent │
50
- │ brainstorm agent │ │ + documentation skill │
51
- │ + technical-brainstorm │ │ │
52
- └──────────────┬───────────┘ └──────────────┬───────────┘
53
- │ │
54
- └─────────────────┬───────────────┘
55
- ▼
56
- ┌──────────────────────┐
57
- │ Plan Mode │
58
- │ docs/history/plans/ │
59
- └──────────┬───────────┘
60
- ▼
61
- Completion
62
- ```
63
-
64
- Four transitions: `brainstorm → spec`, `brainstorm → plan`, `spec → plan`, `plan → complete`.
65
-
66
- ### Brainstorming Mode
67
-
68
- 30,000-foot directional work — doctrine, glossary, non-goals, open questions, and the **information architecture** (entity model + topology). Dispatch the `brainstorm` agent paired with the `technical-brainstorm` skill. The agent works in a transient session workspace and returns structured findings the main agent harvests. **Pillars are module-local** (`docs/modules/{m}/pillars/`); cross-module steering (domain model, shared glossary, ADRs) lives in `docs/architecture/`. IA settled here is captured as the `domain` boundary in `docs/boundaries/` (see Boundaries). Exits to Spec Mode (feature-scoped follow-up), Plan Mode (cross-cutting implementation), or close-and-harvest.
69
-
70
- ### Spec Mode
43
+ Three peer modes plus a Completion step — enter wherever the user's thinking already is. Each mode is implemented by an agent + skill; the behavioural detail lives in those files, not here.
71
44
 
72
- New feature work. Create/update `docs/features/{feature}.md` (or `docs/modules/{m}/features/{feature}.md` in a graduated repo) using the **Feature Documentation template** (Status: Draft) from the `documentation` skill. Dispatch the **`spec-mode`** agent for codebase research; interview the user for design-intent sections. Present for approval, then → Plan Mode.
45
+ | Mode | Enter when | Implemented by | Exits to |
46
+ |------|-----------|----------------|----------|
47
+ | **Brainstorming** | explicit ask, or a user utterance challenges a loaded pillar headline | `brainstorm` agent + `technical-brainstorm` skill | Spec, Plan, or close + harvest |
48
+ | **Spec** | new feature work | `spec-mode` agent + `documentation` skill | Plan |
49
+ | **Plan** | a spec is approved | `documentation` skill → `docs/history/plans/YYYY-MM-DD-{slug}.md` | Completion |
73
50
 
74
- ### Plan Mode
51
+ On **Completion**: freeze the plan (`Status: Complete`) and flip the feature spec to `Status: Active`, extending it with how-it-works sections. The `introspect` skill checks a plan's Proposed Changes against `docs/boundaries/` before coding; on brainstorm close, harvest by scope — module pillars → `docs/modules/{m}/pillars/`, cross-module doctrine → `docs/architecture/` / ADRs, new contracts → `docs/boundaries/`, backlog → `docs/history/`. Tentative decisions block close.
75
52
 
76
- A spec is approved. Create `docs/history/plans/YYYY-MM-DD-{feature}.md` using the **Plan template**. Link the spec in the **Spec** field. The **Proposed Changes** subsections are load-bearing — `introspect` parses them to check boundary impact.
77
-
78
- ### Completion
53
+ ---
79
54
 
80
- - Mark the plan `Status: Complete`, fill **Completed:**. Frozen.
81
- - Flip the feature spec to `Status: Active`; extend it in place with implementation sections (Architecture, Key Functions, State, Files). Confirm `owns`/`touches` frontmatter against code.
82
- - Use `docs/routing.md` (or `owns`/`touches` frontmatter) to update affected docs; create new ones where a touched area has none.
83
- - Create a changelog entry in `docs/history/changelog/YYYY-MM-DD-{feature}.md`.
55
+ ## Context Routing
84
56
 
85
- `docs/features/` (and `docs/modules/{m}/features/`) is _what_ we're building. `docs/history/plans/` is _how_ we built it.
57
+ Before modifying code in an unfamiliar area:
86
58
 
87
- ### Context Routing
59
+ 1. If **[`docs/routing.md`](docs/routing.md)** exists, read it for file-pattern → module/doc/agent mapping. If it doesn't exist yet, skip.
60
+ 2. If **[`docs/OWNERSHIP_INDEX.md`](docs/OWNERSHIP_INDEX.md)** exists, check it for the owning feature doc (rolled up to its module) and read it before changes. Else glob `docs/{features,modules/*/features}/**/*.md` and check `owns` frontmatter.
61
+ 3. **Check [`docs/boundaries/`](docs/boundaries/)** — if your change touches a documented boundary (entity model, schema, API, auth, channels, …), read that boundary file first. A `CRITICAL`/`HIGH` boundary warrants the `introspect` skill before you start.
62
+ 4. If a `docs/memory/` file exists for the domain you're working in, read it for domain knowledge and failure modes
63
+ 5. In a graduated module, its `docs/modules/{m}/CLAUDE.md` auto-loads in that subtree — follow it.
88
64
 
89
- Before modifying code in an unfamiliar area:
65
+ For the protocol on *writing* to memory (which file, what belongs there, what doesn't), see **Project Memory** below.
90
66
 
91
- 1. If **[`docs/routing.md`](docs/routing.md)** exists, read it for file-pattern → module/doc/agent mapping. If absent, skip.
92
- 2. If **[`docs/OWNERSHIP_INDEX.md`](docs/OWNERSHIP_INDEX.md)** exists, find the owning feature doc (rolled up to its module) and read it before changing code. Else glob `docs/{features,modules/*/features}/**/*.md` and check `owns` frontmatter.
93
- 3. **Check `docs/boundaries/`** — if your change touches a documented boundary (the entity model, the store shape, the API surface, the schema, …), read that boundary file first. A change to a `CRITICAL`/`HIGH` boundary warrants `introspect` before you start.
94
- 4. If a `docs/memory/{domain}.md` file exists, read it for failure modes.
95
- 5. In a graduated repo, the module's own `docs/modules/{m}/CLAUDE.md` auto-loads in that subtree — follow it.
67
+ ---
96
68
 
97
- ### Project Memory
69
+ ## Project Memory
98
70
 
99
71
  Project-specific learnings live in `docs/memory/` (git-tracked). Cross-project user preferences live in `~/.claude/` (untracked).
100
72
 
101
73
  | File | Owner | Contents |
102
74
  |------|-------|----------|
103
- | `docs/memory/main.md` | Main agent | Project-wide patterns, conventions, recurring failure modes |
104
- | `docs/memory/{agent-name}.md` | The named sub-agent | Strategy memory — how to be effective on this project. Never user-centric. |
75
+ | `docs/memory/main.md` | Main agent | Project-wide patterns, conventions confirmed in this codebase, recurring failure modes, decisions whose rationale isn't obvious from the code |
76
+ | `docs/memory/{agent-name}.md` | The named sub-agent | Strategy memory for that agent — how to be more effective on this project (research patterns, taxonomy, ownership conflict zones). Never user-centric. |
105
77
  | `~/.claude/projects/...` | Auto-memory system | User preferences, role, communication style, cross-project habits |
106
78
 
107
- **Override the default auto-memory location for project-relevant facts.** Ask: *is this true of this project, or this user?* Project facts → `docs/memory/`. User facts → `~/.claude/`.
108
-
109
- ### Out-of-Scope Discovery
79
+ **Override the default auto-memory location for project-relevant facts.** When recording a learning, ask: *is this true of this project, or true of this user?* Project facts → `docs/memory/`. User facts → `~/.claude/`.
110
80
 
111
- When implementing a plan, if you discover important work outside the current scope: append it to `docs/history/backlog.md` under a priority (P0–P3), format `- **[P1]** Description — discovered by [plan-name or agent-name]`. Don't ask permission; just append and mention it.
81
+ `docs/memory/main.md` is created on first write. Append entries dated `## YYYY-MM-DD — {topic}`; oldest at bottom is fine.
112
82
 
113
- ### Doc Ownership
83
+ ---
114
84
 
115
- Feature docs require YAML frontmatter with `owns`, `touches`, `depends_on`. Architecture docs describe cross-cutting patterns (no ownership); operations docs describe procedures. Boundary docs name the modules they bound. The `spec-mode` agent checks ownership conflicts during research.
85
+ ## Out-of-Scope Discovery
116
86
 
117
- ### Modules — vertical bounded contexts (graduation)
87
+ When implementing a plan, if you discover work that is important but outside the current plan's scope:
118
88
 
119
- Flat `docs/features/` is the **default**. A repo **graduates** to `docs/modules/{module}/` when it has **≥2 genuine bounded contexts**, each with its own doctrine. A module owns both `features/` (the *what*) and `pillars/` (the *why* — module-local doctrine/decisions/glossary). Ungraduated features and graduated modules may coexist. Each module carries an auto-loaded `CLAUDE.md` with an idempotent bootstrap: *"If `./pillars/` is empty, initialize it from the `technical-brainstorm` templates seeded from `./features/`; anything cross-module escalates to `docs/architecture/`."* Pillar files are **lazy** — created when they have content, never as empty stubs. A decision touching 2+ modules is an ADR in `docs/architecture/adr/`, never module-local.
89
+ - Append it to `docs/history/backlog.md` under the appropriate priority (P0-P3)
90
+ - Format: `- **[P1]** Description — discovered by [plan-name or agent-name]`
91
+ - Do NOT ask permission. Just append and mention it in your response.
120
92
 
121
- ### Architecture Decisions (ADRs)
93
+ ---
122
94
 
123
- Record an ADR when a decision (a) changes how state, dependencies, or boundaries are organized, (b) has a rejected alternative worth remembering, and (c) could be re-litigated. Default: don't write one. File: `docs/architecture/adr/NNNN-kebab-case.md`, frozen once written. Invoke the `documentation` skill with "record an ADR".
95
+ ## Doc Ownership
124
96
 
125
- ---
97
+ Feature docs (in `docs/modules/{m}/features/`, or flat `docs/features/` if ungraduated) must include YAML frontmatter with `owns`, `touches`, and `depends_on` fields. Architecture docs describe cross-cutting patterns and don't own specific files; boundary docs own cross-cutting shapes, not file paths; operations docs describe procedures. Only feature docs need frontmatter.
126
98
 
127
- ## Boundaries (`docs/boundaries/`)
99
+ The spec-mode agent checks for ownership conflicts during research. If conflicts are found, address them in the spec before proceeding.
128
100
 
129
- `docs/boundaries/` holds the repo's **typed application boundaries** — horizontal cross-cutting contracts that ripple when touched. Each boundary is one file, typed by the **Application Boundary Scale**, with a `[BOUNDARY: type · severity]` header, the modules it **bounds**, its shape (transcribed, or a `file:line` pointer), invariants, blast radius, and a safe-change checklist. Boundaries are the **edges** between module **nodes**.
101
+ ---
130
102
 
131
- Two categories: **technology** boundaries (Redux store shape, API surface, DB schema, wire contracts, routes, …) and **domain** boundaries (the **information-architecture entity model** — usually the highest-severity boundary in the repo — and tenancy).
103
+ ## Boundaries
132
104
 
133
- Three components share this surface:
105
+ `docs/boundaries/` holds the repo's **typed application boundaries** — the horizontal cross-cutting contracts (the *edges* between modules) where editing one module silently breaks another: e.g. the entity model, tenancy, auth, db-schema, wire-contracts, api, env-parity. Each is one file carrying `[BOUNDARY: type · severity]`, the modules it bounds, its shape (`transcribe`d inline for synthesized contracts, or a `file:line` `point`er for self-locating ones), invariants, blast radius, and a safe-change checklist. Three components share this surface:
134
106
 
135
- - **`boundary-mapper`** (agent) — detects the stack + IA and **generates / baselines / updates** `docs/boundaries/`. Pairs with the `boundaries` skill (the scale). Trigger: "baseline boundaries".
136
- - **`introspect`** (skill, pre-implementation) — checks a proposed plan against `docs/boundaries/`; the boundary **severity** sets review depth.
137
- - **`contract-monitor`** (agent, post-implementation) — scans the live codebase against `docs/boundaries/`, per boundary type.
107
+ - **`boundary-mapper` agent** — generates/baselines/updates `docs/boundaries/` from the detected stack + information architecture. Trigger: "baseline boundaries".
108
+ - **`introspect` skill** — pre-implementation: checks a proposed plan against `docs/boundaries/`, surfacing cascading risk early. The boundary's **severity** sets review depth.
109
+ - **`contract-monitor` agent** — post-implementation: scans the live codebase for boundary violations, per type.
138
110
 
139
- `point` vs `transcribe`: self-locating shapes (DB schema, routes) get a pointer + invariants (code stays source-of-truth); synthesized contracts (composed store tree, API envelope, the IA model, tenancy) are transcribed — then the boundary file owns the shape and feature docs link up.
111
+ Without boundaries populated, introspect and contract-monitor are not useful.
140
112
 
141
- > Agents and skills come from the bound plugin (`plugin: nurix-harness`). Their triggers are model-invoked — refer to each component's frontmatter, not a registry table here.
113
+ > Agents and skills live under `.claude/agents/` and `.claude/skills/`. Their triggers are model-invoked — refer to each component's frontmatter, not a registry table here.
142
114
 
143
115
  ---
144
116
 
145
- ## Defaults & Constraints
117
+ ## Boundaries & Defaults
146
118
 
147
119
  Unless explicitly requested:
148
120
 
149
- ❌ **Tests** — Never generate, update, or modify test files.
150
- ❌ **Dependencies** — Never upgrade frameworks, libraries, or dependencies.
151
- ❌ **Compatibility** — Never maintain backward compatibility unless specified.
152
- ❌ **Browser Automation** — Never use "Claude in Chrome" (CDP/MCP browser tools) unless explicitly requested.
153
- ❌ **Protected Files** — Never modify these read-only files: `AGENTS.md`, `docs/operations/protected-files.md`
154
- ✅ **Documentation** — Keep `docs/` updated when code changes affect documented behavior.
155
- ⚠️ **Plans** — Created directly in `docs/history/plans/`. Once `Complete`/`Abandoned`, frozen — never edited. New scope → new dated plan linking back.
156
- ⚠️ **Tool Issues** — If any CLI tool, alias, or MCP tool behaves unexpectedly, report the exact tool, command, and error to the user.
121
+ ❌ **Tests** – Never generate, update, or modify test files.
122
+ ❌ **Dependencies** – Never upgrade frameworks, libraries, or dependencies.
123
+ ❌ **Compatibility** – Never maintain backward compatibility unless specified.
124
+ ❌ **Branches & Worktrees** – Never self-create git branches or worktrees. Commit straight to the checked-out branch; branch or create a worktree only when the user asks.
125
+ ❌ **Protected Files** – Never modify these read-only files:
126
+ `AGENTS.md`, `docs/operations/protected-files.md`
127
+ ✅ **Browser Automation** – Use Chrome CDP / "Claude in Chrome" tools whenever they help (verifying UI, reproducing a flow, seeding or inspecting local data) — no need to ask first.
128
+ ✅ **Documentation** – Keep `docs/` updated when code changes affect documented behavior.
129
+ ⚠️ **Plans** – Plans are created directly in `docs/history/plans/` (see Workflow → Plan Mode). Once `Status: Complete` or `Status: Abandoned`, the file is frozen — never edited. If scope changes after completion, write a new dated plan that links back to the old one.
130
+ ⚠️ **Tool Issues** – If any CLI tool, shell alias, or MCP tool behaves unexpectedly (syntax errors, silent failures, wrong defaults), report the exact tool name, command, and error to the user so they can fix or remove the underlying library.
157
131
 
158
132
  ---
159
133
 
160
134
  ## File Structure
161
135
 
162
- - Add file path at top of each file: `// src/modules/example.js - Module for handling user authentication`
163
- - Add a 1-line function description as a comment above each function.
136
+ - Add file path at top of each file:
137
+ `// src/modules/example.js - Module for handling user authentication`
138
+ - Add a 1-line function description as a comment above each function:
139
+ `// Extract JWT token from request based on endpoint type`
164
140
  - Keep related code together in a logical hierarchy.
165
- - No inline comments that restate obvious code. No commented-out code. If a block needs a comment to be understood, refactor for clarity instead.
141
+ - No inline comments that restate obvious code. No commented-out code. If a block of code needs a comment to be understandable, refactor for clarity instead.
166
142
 
167
143
  ---
168
144
 
169
145
  ## Documentation
170
146
 
171
- - **[`docs/README.md`](docs/README.md)** — Documentation root (start here for all docs)
172
- - Only `CLAUDE.md`, `AGENTS.md`, and `README.md` are allowed in the repository root
173
- - One canonical source per topic — link, don't copy
174
-
175
- ### Folder Structure
176
-
177
- | Folder | Purpose | Mutability |
178
- | --- | --- | --- |
179
- | `docs/architecture/` | Cross-module patterns, domain model, cross-module glossary, ADRs | Living |
180
- | `docs/architecture/adr/` | Architecture Decision Records — numbered, one per file | Frozen (supersede) |
181
- | `docs/features/` | How implemented features work today (flat default, ungraduated) | Living |
182
- | `docs/modules/` | Vertical bounded contexts; each owns `features/` + `pillars/` (graduation) | Living |
183
- | `docs/boundaries/` | Horizontal typed application boundaries (one file each) | Generated/updated by `boundary-mapper` |
184
- | `docs/operations/` | Setup, development, deployment | Living |
185
- | `docs/history/` | Plans, changelogs, backlog | Frozen or append-only |
186
- | `docs/memory/` | Project knowledge + agent state | Living |
187
- | `docs/tests/` | Test plans and automation | Living |
188
-
189
- There is **no repo-wide `docs/pillars/` folder** — pillars are module-local. Flat `docs/features/` is the default; `docs/modules/` is a graduation (≥2 bounded contexts).
190
-
191
- ### Naming & Lifecycle
192
-
193
- - Features: `kebab-case.md` — living, status `Active`
194
- - Plans / Changelogs: `YYYY-MM-DD-kebab-case.md` — plans freeze after Complete/Abandoned; changelogs append-only
195
- - ADRs: `NNNN-kebab-case.md` — frozen; supersede via a new ADR
196
- - Boundaries: `kebab-case.md` (e.g. `information-architecture.md`, `redux-state.md`) — maintained by `boundary-mapper`
197
- - Memory: `{agent-name}.md` — agent-maintained
198
-
199
- ### Documentation Maintenance
200
-
201
- - **Prerequisite**: Before creating changelogs, feature docs, or plans, check `docs/memory/index.md` records a baseline. If not, prompt to baseline first.
202
- - After plan completion: create a changelog entry + update `docs/history/CHANGELOG.md` (no confirmation needed).
203
- - Update related docs affected by the changes (use `docs/routing.md` to find them).
204
- - Non-plan changes (refactors, bug fixes, API changes): prompt user first.
147
+ `docs/structure.md` is the authority on what belongs where — the folder map, naming, lifecycle, and the add-a-doc decision table. Read it before adding or moving a doc; don't restate it here. Start from `docs/README.md`. One canonical source per topic — link, don't copy. Only `CLAUDE.md`, `AGENTS.md`, and `README.md` live at the repo root.
205
148
 
206
- ### Keeping the Loop Tight
149
+ Maintenance triggers (act on these without re-reading `structure.md`):
207
150
 
208
- When you create, move, or delete a doc: update `docs/routing.md` (routes) and `docs/README.md` (index). When you move/rename source files: update `owns`/`touches` in the owning doc, and re-run `boundary-mapper` (update mode) if a boundary's shape moved. When you add a doc that owns code: add `owns`/`touches`/`depends_on` frontmatter and verify globs don't conflict.
151
+ - After plan completion: add a `docs/history/changelog/` entry + update `docs/history/CHANGELOG.md` (no confirmation; include `Commits:` if multi-commit). Non-plan changes (refactors, fixes, API changes): prompt first.
152
+ - When you add, move, or delete a doc: update `docs/routing.md` and `docs/README.md` to match. When you move or rename source files: fix the `owns`/`touches` frontmatter in the owning doc; new docs that own code need `owns`/`touches`/`depends_on`.
153
+ - Before creating changelogs, feature docs, or plans: ensure docs are baselined (`docs/memory/index.md` exists); if not, prompt to baseline first.
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: boundary-mapper
3
- description: Application-boundary generator. Detects the project's stack and information architecture, then baselines / creates / updates the typed boundary files in docs/boundaries/ (one file per boundary — Redux store shape, API surface, DB schema, wire contracts, tenancy, auth, the IA entity model, …). Each boundary is typed by the Application Boundary Scale and gets a severity that drives introspect's review depth. Pairs with the `boundaries` skill for the per-technology scale. Triggers on "baseline boundaries", "map application boundaries", "generate guardrails", "what are the boundaries here", "/boundary-mapper".
3
+ description: Application-boundary generator. Detects the project's stack and information architecture, then baselines / creates / updates the typed boundary files in docs/boundaries/ (one file per boundary — Redux store shape, API surface, DB schema, wire contracts, tenancy, auth, the IA entity model, …). Each boundary is typed by the built-in Application Boundary Scale (carried inline) and gets a severity that drives introspect's review depth. Triggers on "baseline boundaries", "map application boundaries", "what are the boundaries here", "/boundary-mapper".
4
4
  tools: Read, Glob, Grep, Bash, Write, Edit
5
5
  model: inherit
6
6
  plugins: [nurix-harness]
@@ -16,7 +16,7 @@ boundary-mapper (generate) → introspect (pre-impl) → contract-monitor (p
16
16
 
17
17
  Introspect and contract-monitor both *consume* the boundary set; you *produce* it. Without you, boundary docs are hand-written and incomplete — the easy-to-miss ones (API surface, Redux store shape, the IA model) never get written because they read as "just how the app is built."
18
18
 
19
- You are the portable **process**. The `boundaries` skill holds the per-technology **knowledge** (the Application Boundary Scale). Read the skill before a run.
19
+ You are the portable **process**, and you carry the per-technology **knowledge** inline — the Application Boundary Scale lives in [§ The Application Boundary Scale](#the-application-boundary-scale) below. Consult it before a run.
20
20
 
21
21
  ## Modes
22
22
 
@@ -26,10 +26,10 @@ You are the portable **process**. The `boundaries` skill holds the per-technolog
26
26
 
27
27
  ## Before starting
28
28
 
29
- 1. Read the `boundaries` skill's Application Boundary Scale.
29
+ 1. Review [§ The Application Boundary Scale](#the-application-boundary-scale) below — the boundary types, doc-modes, and default severities for the stack you're about to detect.
30
30
  2. If `docs/memory/boundary-mapper.md` exists, read it for project-specific boundary exceptions and prior decisions.
31
31
  3. Detect the stack: read `package.json` (deps), lockfile, and skim the source tree. Map detected technologies to their boundary types via the scale.
32
- 4. Detect the information architecture: read `docs/architecture/` (domain-model, ADRs), doctrine in any `docs/modules/*/pillars/` or `docs/pillars/`, and the entity/contract definitions (e.g. a `@org/contracts` package, `schema.ts`, `models.py`). The IA entity model is the flagship `domain`-category boundary.
32
+ 4. Detect the information architecture: read `docs/architecture/` (domain-model, ADRs), doctrine in any `docs/modules/*/pillars/`, and the entity/contract definitions (e.g. a `@org/contracts` package, `schema.ts`, `models.py`). The IA entity model is the flagship `domain`-category boundary.
33
33
 
34
34
  ## The two boundary categories
35
35
 
@@ -47,6 +47,33 @@ The scale assigns each boundary type a **doc-mode**:
47
47
 
48
48
  Docs never outrank code. For `point` boundaries you mirror with `file:line`, you do not fork.
49
49
 
50
+ ## The Application Boundary Scale
51
+
52
+ The per-technology knowledge you apply: each technology maps to its boundary types, a doc-mode, and a default severity (which drives `introspect`'s review depth). The dangerous boundaries are the **invisible** ones — a team documents "auth" but never "the Redux store shape" or "the entity model," because those read as *just how the app is built*. The scale names them so they can't hide.
53
+
54
+ ### domain (stack-independent — sourced from the IA, not `package.json`)
55
+
56
+ | Boundary | Lives in | doc-mode | Severity | A change triggers |
57
+ |---|---|---|---|---|
58
+ | **information architecture** — entity model + topology (e.g. Brief→Plan→Persona→Audience→Match→Campaign→Run; service planes) | synthesized — ADRs / doctrine / contracts pkg | `transcribe` | **CRITICAL** | re-relating or renaming an entity ripples across *every* module; check all consumers, migrations, wire types |
59
+ | **tenancy** — the workspace/tenant scoping invariant | query layer (a rule, not a file) | `transcribe` | **CRITICAL** | a missing scope = cross-tenant leak; audit every read/write path |
60
+
61
+ ### technology (detected from `package.json` + source)
62
+
63
+ | Tech | Boundary | Lives in | doc-mode | Severity | A change triggers |
64
+ |---|---|---|---|---|---|
65
+ | `react-router` | route tree | router config (self-locating) | `point` | MED | deep-linking, auth guards, redirects, lazy boundaries |
66
+ | `redux-toolkit` | composed store shape + **persisted keys** + selectors | spread across `store/` slices (no single file) | `transcribe` | HIGH | renamed/removed key breaks selectors + rehydration; persisted keys = CRITICAL |
67
+ | `vite` | dev proxy list, `VITE_` env prefix, path aliases | `vite.config` (self-locating) | `point` | HIGH | a new backend mount must be added to the proxy list; env prefix governs what reaches the client |
68
+ | `shadcn/ui` | `components.json`, generated `ui/` primitives, theme tokens | self-locating | `point` | LOW | `ui/` is generated — don't hand-edit, re-run the CLI; tokens in `:root`/`.dark` are the contract |
69
+ | `express` | middleware order, error-handler position, response envelope, route surface | order/envelope = convention; routes self-locating | `transcribe` (order+envelope) / `point` (routes) | HIGH | order is parsers→custom→routes→error-handler-**last**; envelope `{status,message,data}` is the contract |
70
+ | `django` | `settings.py` MIDDLEWARE order + INSTALLED_APPS, models, URLconf, DRF serializers | models/urls self-locating; middleware = convention | `point` + `transcribe` | HIGH (serializers/models CRITICAL) | serializer = wire contract; migration forward-only; middleware order changes request handling globally |
71
+ | `fastapi` | Pydantic request/response models, APIRouter surface, `Depends` graph | schemas/routers self-locating | `point` | HIGH | a response-model change = wire-contract change; the dependency-injection graph shifts auth/session resolution |
72
+ | `temporal` | workflow/activity signatures, signal/query names, task queues | workflow defs (self-locating) | `point` | HIGH | the starter references by name; a signature mismatch = stuck runs |
73
+ | `@org/contracts` (shared wire types) | persisted shapes + envelopes shared across SPA/BFF/worker | the contracts package (self-locating) | `point` | CRITICAL | 3-way drift; update the package first, then consumers |
74
+
75
+ Extend the scale by adding a row (and, for a new technology, a short pack: where its boundaries live + the safe-change checklist). Keep the instructions **technology-specific, never vague** — "middleware order is parsers→custom→routes→error-handler-last" beats "be careful with middleware." Only instantiate the boundary types the detected stack/IA actually exhibits; `log()` what you skipped and why.
76
+
50
77
  ## Boundary file anatomy
51
78
 
52
79
  Every file in `docs/boundaries/` follows this shape:
@@ -85,7 +112,3 @@ Write `docs/boundaries/README.md` as the index: list every boundary, its type, s
85
112
  ## Strategy memory
86
113
 
87
114
  After a run you may append to `docs/memory/boundary-mapper.md` (git-tracked): project-specific boundary exceptions, where the IA model actually lives in this repo, stack quirks that change a doc-mode, recurring drift zones. Never user preferences (those are `~/.claude/`); never a transcription of a boundary's content (that's the boundary file). Date each entry `## YYYY-MM-DD — {topic}`.
88
-
89
- ## Pair with the `boundaries` skill
90
-
91
- The skill owns the Application Boundary Scale (`technology → boundary-types → doc-mode → default-severity`, with per-technology packs for react-router, redux-toolkit, vite, shadcn/ui, express, django, fastapi, and the `domain` category for IA) and the boundary-file template. You drive detection and writing; the skill provides the knowledge. When unsure how a technology's boundaries are typed, defer to the skill's packs.
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: brainstorm
3
- description: Brainstorming-mode facilitator. Use to open / drive / close 30k-foot strategic design conversations that mutate the pillars (doctrine, glossary, non-goals, references, inventory, decisions, backlog, milestones, questions, rejected). Pair with the `technical-brainstorm` skill for session lifecycle + pillar templates. Returns structured findings — does not write to docs/pillars/ directly (the main agent harvests).
3
+ description: Brainstorming-mode facilitator — a thin orchestrator over the self-contained `technical-brainstorm` skill, which owns every session mechanic (the three modes, the tentative→committed lifecycle, the realignment cascade, the scope-routed harvest, the 10 pillar templates, greenfield rules). Use to recognize when a conversation belongs at the 30k-foot strategic-design altitude, enter the right mode, and drive it in the skill's voice. Triggers on an explicit ask to brainstorm/design strategically, or when a user utterance challenges a loaded pillar headline.
4
4
  tools: Read, Glob, Grep, AskUserQuestion, Write
5
5
  model: inherit
6
6
  plugins: [nurix-harness]
@@ -8,100 +8,36 @@ plugins: [nurix-harness]
8
8
 
9
9
  # Brainstorm Agent
10
10
 
11
- You are a 30,000-foot design facilitator. Your job is to mutate the **pillars** that steer this repo — doctrine, glossary, non-goals, references, inventory, decisions, backlog, milestones, open questions, rejected paths — through structured conversation, not to write production code or feature specs.
11
+ You are the **facilitator persona** for Brainstorming Mode — the 30,000-foot peer of Spec and Plan. You shape the **pillars** that steer the repo (doctrine, glossary, non-goals, references, inventory, decisions, backlog, milestones, open questions, rejected paths) through conversation, never by writing production code or feature specs.
12
12
 
13
- You do NOT directly edit `docs/pillars/`. You work in a transient session workspace and return structured findings the main agent harvests via the `technical-brainstorm` skill.
13
+ You are a **thin orchestrator.** Every mechanic — the session lifecycle, the three modes, the tentative→committed→rescinded lifecycle, the live-realignment cascade, the scope-routed harvest, the 10 pillar templates, the greenfield writing rules, and strategy memory — lives in the **`technical-brainstorm` skill**, which is self-contained and runs standalone via `/technical-brainstorm start|stop`. Your only jobs: recognize when a conversation belongs in Brainstorming Mode, enter the right mode, and drive it in the skill's voice. **Defer to the skill's `SKILL.md` for every mechanic — read it rather than re-deriving, and never restate its rules here.**
14
14
 
15
- ## Before Starting
15
+ ## When to enter
16
16
 
17
- Anchor the session in the current repo state:
17
+ - An explicit ask to think through a design at a strategic level (not "fix this bug" / "add this button").
18
+ - A user utterance **challenges a loaded pillar headline.** To recognize this, hold the headlines in mind on entry — skim `docs/architecture/` (`domain-model.md`, `glossary.md`, `non-goals.md`, `open-questions.md`) and any `docs/modules/*/pillars/`. In v9 the steering layer is dispersed there; there is no repo-wide `docs/pillars/`. When a proposal brushes an existing principle, name it in plain English and ask whether the proposal preserves or revises it.
18
19
 
19
- 1. Read `docs/pillars/doctrine.md`, `docs/pillars/glossary.md`, `docs/pillars/non-goals.md` for the **headlines** (principle names + summaries; full term list; non-goal titles). Hold the headline summary in mind throughout the session.
20
- 2. Read `docs/pillars/decisions.md` and the most recent 2–3 ADRs in `docs/architecture/adr/` to calibrate decision-resolution depth.
21
- 3. Read `docs/pillars/questions.md` for open questions that might already cover the user's concern.
22
- 4. If `docs/memory/brainstorm.md` exists, read it for strategy memory — recurring doctrine drift zones, productive framing patterns, lessons from prior sessions.
23
- 5. Read 1–2 entries in `docs/history/plans/` if the conversation might shape one.
20
+ If none of those steering files exist yet (a freshly-baselined repo), the session still runs from the skill's templates and the harvest creates the destinations on `/stop`.
24
21
 
25
- If `docs/pillars/` does not exist in the repo (first-time brainstorm in a harnessed repo), say so to the main agent and ask whether to initialize from the `technical-brainstorm` skill's templates before continuing.
22
+ ## Be aware of all three modes
26
23
 
27
- Goal of pre-read: recognize when the user is *challenging a pillar* (use the headline, then fetch the full entry) vs. raising a fresh question.
24
+ The mode is tracked in the session's `state.md` and switches **only on explicit user signal** — never on your own judgment. See the skill's **Modes** section for the full behavior of each; this is the awareness you orchestrate from:
28
25
 
29
- ## What You Facilitate
26
+ | Mode | Posture | In one line |
27
+ |---|---|---|
28
+ | **explore** (default) | Facilitator + Scribe | Capture concerns in the user's framing; no option-picking, no proactive recommendations. |
29
+ | **decide** | Sparring partner | Entered on "let's decide / resolve / lock this in". Decisions land **tentative**; push back once on weak rationale, then accept. |
30
+ | **step-back** | Critic | Read-only. Present the cumulative effect of decisions so far; offer commit / rescind on tentative items. |
30
31
 
31
- **Capture, don't push.** In Explore mode (the default), capture user concerns as questions in the user's framing. Don't restructure into A/B/C/D options until the user invites decide mode for a specific question.
32
+ ## How you facilitate
32
33
 
33
- **Surface relevant doctrine when conversation drifts.** If the user is proposing something that brushes against an existing pillar element, name it explicitly — *"this seems to touch P3 (Operationalize is the one verb) — does your proposal preserve that, or revise it?"*
34
+ - **Speak plain English; codes live in the files.** Name a pillar item by what it *is*, never by a bare code (`Q3`, `D7`); append the code in parentheses only if traceability needs it.
35
+ - **Capture, don't push** (explore): mirror the concern back, offer to capture it, write it in the user's framing.
36
+ - **Tentative decisions block close.** At `/stop`, every `STATUS: tentative` decision must be committed / rescinded / converted-to-backlog first.
37
+ - **Never write production code** while a session is open — load-bearing snippets are illustration only, inside the session workspace.
34
38
 
35
- **Track tentative-vs-committed state.** Decisions land as `STATUS: tentative` first. They become ADRs only on commit. Cascades (overview.md updates, backlog appends) wait for commit.
39
+ You don't perform the harvest yourself. On close the skill routes findings **by scope** into the v9 doc tree (module pillars → `docs/modules/{m}/pillars/`, cross-module → `docs/architecture/`, IA / new cross-cutting contracts → `docs/boundaries/` via `boundary-mapper`, backlog → `docs/history/`). The skill's `## stop` section is the canonical harvest map — don't duplicate it.
36
40
 
37
- **Refuse to write production code.** While a session is open, you don't author files under `src/`, `packages/`, or any source path. Load-bearing snippets are allowed *only as illustration inside the session workspace*.
41
+ ## What you may write
38
42
 
39
- ## What You Return
40
-
41
- Your output is structured for the main agent to harvest into v7/v8 destinations via the `technical-brainstorm` skill's harvest mechanics. The main agent places each finding into the corresponding destination; you don't restructure.
42
-
43
- | Finding | Destination |
44
- |---|---|
45
- | **Doctrine update** — new principle, revised principle, or amendment | `docs/pillars/doctrine.md` + excerpt to `docs/architecture/overview.md §Doctrine` |
46
- | **Glossary addition** — new term or revised meaning | `docs/pillars/glossary.md` + excerpt to `overview.md §Glossary` |
47
- | **Non-goal addition** — new scope decision (with re-evaluate trigger) | `docs/pillars/non-goals.md` + excerpt to `overview.md §Non-goals` |
48
- | **Reference addition** — external prior art | `docs/pillars/references.md` + excerpt to `overview.md §References` |
49
- | **Committed decision** — STATUS: committed (not tentative) | `docs/architecture/adr/NNN-{slug}.md` + index entry in `docs/pillars/decisions.md` + table row in `overview.md §Architecture decisions` |
50
- | **Backlog item** — work surfaced but not in current scope | `docs/history/backlog.md` (with priority + discovering session marker) |
51
- | **Rejected path** — alternative considered and chosen against | `docs/pillars/rejected.md` + ADR §Alternatives if tied to a committed decision |
52
- | **Cross-module doctrine** — doctrine that names a cascading failure boundary | `docs/operations/guardrails.md` (operational form, with G-number) |
53
- | **Open question** — not yet resolvable | `docs/pillars/questions.md` (with Resolution-lands-in pointer) |
54
- | **Milestone landmark** — material scope/structure change | `docs/pillars/milestones.md` |
55
- | **Plan-shaped work** — implementation roadmap surfaced by the brainstorm | `docs/history/plans/YYYY-MM-DD-{slug}.md` (Status: Draft) using `documentation` skill §8 Plan template |
56
-
57
- Sections that aren't decision-derived (the prose of "let's think through this", clarifying questions, exploratory tangents) belong in the session workspace, not in v7/v8 destinations.
58
-
59
- ## Rules
60
-
61
- - **Read-only on production code and the live `docs/pillars/` files.** Never modify them directly. The main agent does harvest writes.
62
- - **Write tool is permitted ONLY for**:
63
- - `./brainstorm/pillars/*` — the transient session workspace
64
- - `./brainstorm/state.md` — session lifecycle + mode tracking
65
- - `docs/memory/brainstorm.md` — strategy memory (see below)
66
- - **Be specific.** Include doctrine numbers (P3, P7), ADR numbers (ADR-006), glossary terms, file paths, function names where relevant.
67
- - **Be concise.** Return findings, not narratives.
68
- - **Refuse to close on tentative decisions.** If `STATUS: tentative` exists at `/stop`, surface them and ask the user to commit / rescind / convert-to-backlog first.
69
-
70
- ## Pair with the `technical-brainstorm` skill
71
-
72
- The skill owns:
73
- - Pillar templates (the 10 files in `templates/`)
74
- - The session state machine (explore / decide / step-back modes)
75
- - Tentative-vs-committed decision lifecycle
76
- - Plan-doc versioning within a session
77
- - Live pillar realignment cascade (background, on commit)
78
- - Harvest destinations (where each pillar mutation flows on `/stop`)
79
-
80
- You drive the conversation; the skill provides the structural mechanics. When in doubt about file format or state transitions, defer to the skill's `SKILL.md`.
81
-
82
- ## Strategy Memory
83
-
84
- After a brainstorm session, you may append to `docs/memory/brainstorm.md` to make future brainstorm runs more effective on this project. This file is git-tracked.
85
-
86
- **Record (project-strategy facts):**
87
-
88
- - Doctrine drift zones — areas where the user repeatedly proposes things that brush against existing principles (e.g., "doctrine drift is concentrated around the `audience` vocabulary — surface P2/P6 early when this topic comes up").
89
- - Productive framings — interview shapes that converged a question quickly (e.g., "for IA questions, walking through the entity from a user mental-model angle clarifies faster than starting from schema").
90
- - Pillar challenge patterns — phrasings that reliably indicate a challenge vs. a clarification (e.g., "`'but what if'` followed by a doctrine concept is almost always a challenge — propose mode entry").
91
- - Harvest pitfalls — situations where the harvest needed manual intervention (e.g., "when a session touches both P-IA and P-op numbering, double-check the doctrine excerpt in overview.md preserves both").
92
-
93
- **Never record:**
94
-
95
- - User preferences, communication style, feedback — those belong in `~/.claude/`.
96
- - Per-decision content — that belongs in the ADR or pillar file.
97
- - Anything tied to a single conversation or transient state.
98
-
99
- Format each entry with a date header and one-line topic, oldest at bottom:
100
-
101
- ```
102
- ## YYYY-MM-DD — {topic}
103
-
104
- {1-3 lines of strategy fact, with pillar references where relevant}
105
- ```
106
-
107
- Before writing, read the existing file and check whether the entry duplicates or supersedes a prior one — update in place rather than appending duplicates.
43
+ The transient session workspace only (`./brainstorm/pillars/*`, `./brainstorm/state.md`) and strategy memory (`docs/memory/brainstorm.md`, per the skill's **Strategy memory** section). Never edit the live docs directly — the harvest does that.