@bookedsolid/reagent 0.12.1 → 0.13.0

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.
Files changed (56) hide show
  1. package/README.md +373 -943
  2. package/dist/cli/commands/init/index.d.ts.map +1 -1
  3. package/dist/cli/commands/init/index.js +45 -35
  4. package/dist/cli/commands/init/index.js.map +1 -1
  5. package/dist/cli/commands/init/mcp-config.d.ts +11 -0
  6. package/dist/cli/commands/init/mcp-config.d.ts.map +1 -0
  7. package/dist/cli/commands/init/mcp-config.js +64 -0
  8. package/dist/cli/commands/init/mcp-config.js.map +1 -0
  9. package/dist/cli/commands/init/policy.d.ts +1 -1
  10. package/dist/cli/commands/init/policy.d.ts.map +1 -1
  11. package/dist/cli/commands/init/policy.js +5 -3
  12. package/dist/cli/commands/init/policy.js.map +1 -1
  13. package/dist/cli/index.js +2 -11
  14. package/dist/cli/index.js.map +1 -1
  15. package/hooks/_lib/common.sh +18 -0
  16. package/hooks/blocked-paths-enforcer.sh +17 -9
  17. package/hooks/settings-protection.sh +5 -3
  18. package/package.json +2 -9
  19. package/profiles/astro/hooks/astro-ssr-guard.sh +1 -0
  20. package/profiles/drupal/hooks/drupal-coding-standards.sh +1 -0
  21. package/profiles/drupal/hooks/hook-update-guard.sh +1 -0
  22. package/profiles/lit-wc/hooks/cem-integrity-gate.sh +1 -0
  23. package/profiles/lit-wc/hooks/shadow-dom-guard.sh +1 -0
  24. package/profiles/nextjs/hooks/server-component-drift.sh +1 -0
  25. package/dist/cli/commands/daemon/eject.d.ts +0 -13
  26. package/dist/cli/commands/daemon/eject.d.ts.map +0 -1
  27. package/dist/cli/commands/daemon/eject.js +0 -74
  28. package/dist/cli/commands/daemon/eject.js.map +0 -1
  29. package/dist/cli/commands/daemon/index.d.ts +0 -5
  30. package/dist/cli/commands/daemon/index.d.ts.map +0 -1
  31. package/dist/cli/commands/daemon/index.js +0 -64
  32. package/dist/cli/commands/daemon/index.js.map +0 -1
  33. package/dist/cli/commands/daemon/restart.d.ts +0 -10
  34. package/dist/cli/commands/daemon/restart.d.ts.map +0 -1
  35. package/dist/cli/commands/daemon/restart.js +0 -20
  36. package/dist/cli/commands/daemon/restart.js.map +0 -1
  37. package/dist/cli/commands/daemon/start.d.ts +0 -2
  38. package/dist/cli/commands/daemon/start.d.ts.map +0 -1
  39. package/dist/cli/commands/daemon/start.js +0 -143
  40. package/dist/cli/commands/daemon/start.js.map +0 -1
  41. package/dist/cli/commands/daemon/status.d.ts +0 -2
  42. package/dist/cli/commands/daemon/status.d.ts.map +0 -1
  43. package/dist/cli/commands/daemon/status.js +0 -90
  44. package/dist/cli/commands/daemon/status.js.map +0 -1
  45. package/dist/cli/commands/daemon/stop.d.ts +0 -2
  46. package/dist/cli/commands/daemon/stop.d.ts.map +0 -1
  47. package/dist/cli/commands/daemon/stop.js +0 -73
  48. package/dist/cli/commands/daemon/stop.js.map +0 -1
  49. package/dist/config/daemon-loader.d.ts +0 -16
  50. package/dist/config/daemon-loader.d.ts.map +0 -1
  51. package/dist/config/daemon-loader.js +0 -76
  52. package/dist/config/daemon-loader.js.map +0 -1
  53. package/dist/types/daemon.d.ts +0 -45
  54. package/dist/types/daemon.d.ts.map +0 -1
  55. package/dist/types/daemon.js +0 -2
  56. package/dist/types/daemon.js.map +0 -1
package/README.md CHANGED
@@ -1,1081 +1,511 @@
1
1
  # @bookedsolid/reagent
2
2
 
3
- Zero-trust MCP gateway and agentic infrastructure for AI-assisted development.
3
+ Zero-trust MCP server for AI-assisted development. Every tool call — policy enforced.
4
4
 
5
- Reagent is four things:
5
+ reagent sits between Claude Code and every tool your AI agent can reach. It enforces
6
+ graduated autonomy policies, redacts secrets before they touch the model, logs a
7
+ hash-chained audit trail, and can halt all agent operations with a single command.
8
+ Put it in `.mcp.json` once, and every project that uses it gets the same safety layer.
6
9
 
7
- 1. **MCP Gateway** (`reagent serve`) — a proxy server that sits between your AI assistant (Claude Code, Cursor, etc.) and downstream MCP tool servers. Every tool call flows through a zero-trust middleware chain: policy enforcement, tier classification, blocked path enforcement, secret redaction, and hash-chained audit logging.
10
+ ## What it is
8
11
 
9
- 2. **Config Scaffolder** (`reagent init`) installs safety hooks, behavioral policies, quality gates, agent teams, and developer tooling into any project.
12
+ reagent is an MCP server. You declare it in `.mcp.json` and Claude Code spawns it via
13
+ stdio transport when a session starts. Every tool call — whether to reagent's own native
14
+ tools or to any downstream MCP server you've configured — flows through a 12-layer
15
+ middleware chain before it executes.
10
16
 
11
- 3. **Stack Analyzer** (`reagent catalyze`) detects your project's tech stack and generates a gap analysis report showing which hooks, gates, and agents are missing. Produces Markdown and HTML reports.
17
+ reagent can also proxy tool calls to other MCP servers. Instead of listing your
18
+ filesystem server, GitHub server, and other tools directly in `.mcp.json`, you list them
19
+ in `.reagent/gateway.yaml`. reagent connects to each one on startup, discovers their
20
+ tools, and re-registers those tools on itself under namespaced names. Every proxied call
21
+ goes through the same middleware chain as native tool calls — policy, redaction, audit,
22
+ rate-limiting, and the kill switch all apply.
12
23
 
13
- 4. **Project Management Layer** lightweight task tracking with JSONL event store, native MCP tools, GitHub issue sync, and a product-owner agent for task planning.
24
+ `reagent init` scaffolds a project with the full safety infrastructure: Claude Code hooks,
25
+ `policy.yaml`, `gateway.yaml`, agent team files, cursor rules, and quality gates. Profiles
26
+ let you start from a base configuration (client-engagement or bst-internal) and layer in
27
+ tech-stack-specific hooks (astro, nextjs, lit-wc, drupal).
14
28
 
15
- ## Why Reagent?
16
-
17
- AI coding assistants are powerful but unconstrained. Reagent adds the missing governance layer:
18
-
19
- - **Policy enforcement** — graduated autonomy levels (L0 read-only through L3 full access) control which tiers of tools an agent can invoke
20
- - **Kill switch** — `reagent freeze` immediately blocks all tool calls across every connected MCP server
21
- - **Blocked path enforcement** — tool arguments referencing protected paths (including `.reagent/` itself) are denied before execution
22
- - **Secret redaction** — tool arguments and outputs are scanned for AWS keys, GitHub tokens, API keys, PEM private keys, Discord tokens, and more — redacted before they reach the AI or the downstream tool
23
- - **Audit trail** — every tool invocation is logged as hash-chained JSONL with serialized writes for chain integrity
24
- - **Tool blocking** — individual tools can be permanently blocked regardless of autonomy level
25
- - **Tier downgrade protection** — `tool_overrides` cannot lower a tool's tier below its static or convention-based classification
26
- - **Security hooks** — 20 Claude Code hooks enforce settings protection, secret scanning, dangerous command interception, blocked path enforcement, symlink traversal prevention, network exfiltration blocking, and more
27
- - **Quality gates** — commit and push review gates with triage scoring, review caching, and agent-spawned code review
28
- - **Task management** — native MCP tools for task CRUD, GitHub issue sync, and a product-owner agent with guardrails
29
+ The kill switch is a file: `.reagent/HALT`. When it exists, every hook and every tool call
30
+ returns an immediate denial with the reason from the file. `reagent freeze` creates it;
31
+ `reagent unfreeze` removes it.
29
32
 
30
33
  ## Quick Start
31
34
 
32
- ### As an MCP Gateway
33
-
34
35
  ```bash
35
36
  npm install -g @bookedsolid/reagent
36
-
37
- # Initialize a project with policy and gateway config
38
- reagent init --profile bst-internal
39
-
40
- # Configure your downstream MCP servers in .reagent/gateway.yaml
41
- # Then start the gateway
42
- reagent serve
37
+ cd your-project
38
+ reagent init
43
39
  ```
44
40
 
45
- Point your AI assistant's MCP configuration at the gateway:
41
+ That's it. `reagent init` writes `.mcp.json` to your project root:
46
42
 
47
43
  ```json
48
44
  {
49
45
  "mcpServers": {
50
46
  "reagent": {
47
+ "type": "stdio",
51
48
  "command": "npx",
52
- "args": ["-y", "@bookedsolid/reagent", "serve"]
49
+ "args": ["reagent", "serve"]
53
50
  }
54
51
  }
55
52
  }
56
53
  ```
57
54
 
58
- All downstream tool calls now flow through Reagent's middleware chain.
59
-
60
- ### As a Config Scaffolder
61
-
62
- ```bash
63
- npx @bookedsolid/reagent init
64
-
65
- # With a base profile
66
- npx @bookedsolid/reagent init --profile bst-internal
67
- npx @bookedsolid/reagent init --profile client-engagement
68
-
69
- # With a tech stack profile
70
- npx @bookedsolid/reagent init --profile nextjs
71
- npx @bookedsolid/reagent init --profile lit-wc
72
-
73
- # With optional integrations
74
- npx @bookedsolid/reagent init --github # scaffold GitHub labels + milestones
75
- npx @bookedsolid/reagent init --discord # configure Discord notifications
76
-
77
- # Preview without changes
78
- npx @bookedsolid/reagent init --dry-run
79
- ```
80
-
81
- ## Installing Reagent in Your Project
82
-
83
- This section documents the end-to-end setup for a new project — including the nuances of MCP transport, token passing, and env var expansion that aren't obvious from first principles.
55
+ Restart Claude Code. It will pick up `.mcp.json` and spawn `reagent serve` automatically.
56
+ reagent loads your `.reagent/policy.yaml` and `.reagent/gateway.yaml`, connects to any
57
+ downstream servers, and starts listening on stdio.
84
58
 
85
- ### Step 1 — Run `reagent init`
59
+ To verify the installation:
86
60
 
87
61
  ```bash
88
- cd /path/to/your-project
89
- npx @bookedsolid/reagent init --profile bst-internal
62
+ reagent check
90
63
  ```
91
64
 
92
- This installs hooks, policy, agent team, gateway config template, and Claude settings. It also writes a managed block into `CLAUDE.md` with agent behavioral rules.
93
-
94
- To pick up an updated hook suite after a reagent version bump:
65
+ ## How it works
95
66
 
96
- ```bash
97
- npx @bookedsolid/reagent upgrade
98
67
  ```
99
-
100
- `upgrade` re-syncs hooks that are already installed and bumps `installed_by` in `policy.yaml`. It never adds new hooks without consent.
101
-
102
- ### Step 2 — Configure `.mcp.json`
103
-
104
- **Use stdio transport not HTTP.** Claude Code's HTTP MCP transport requires OAuth 2.1, which the reagent server does not implement. The stdio transport is what works:
105
-
106
- ```json
107
- {
108
- "mcpServers": {
109
- "reagent": {
110
- "command": "npx",
111
- "args": ["-y", "@bookedsolid/reagent", "serve"]
112
- }
113
- }
114
- }
68
+ Claude Code ──stdio──▶ reagent serve (MCP server)
69
+
70
+ ├─ native tools: task_create, task_list, task_update, ...
71
+
72
+ └─ proxied tools from .reagent/gateway.yaml
73
+ └─ every tool call through the middleware chain
115
74
  ```
116
75
 
117
- > **Why `npx` instead of `reagent`?** Using the bare `reagent` command requires a global install. `npx` works from any project, always uses the registry version, and avoids "command not found" errors on machines where reagent isn't globally installed.
76
+ ### The middleware chain
118
77
 
119
- > **Env vars in `.mcp.json`:** Claude Code does **not** expand `${VAR}` syntax in `.mcp.json` env values the literal string `${MY_TOKEN}` is passed to the process, not the value. If reagent needs tokens to pass to downstream MCP servers (e.g., Discord bots), use the gateway proxy pattern instead (see Step 3). The gateway **does** expand `${VAR}` from the shell environment at startup.
78
+ Every tool call whether native or proxiedpasses through this chain in order:
120
79
 
121
- If you need to pass env vars to `reagent serve` itself (e.g., tokens used by native tools like `discord_notify`), set them in your shell environment rather than in `.mcp.json`:
122
-
123
- ```bash
124
- # In your shell profile or .env (never committed):
125
- export BOOKED_DISCORD_BOT_TOKEN="..."
126
80
  ```
127
-
128
- ### Step 3 Configure downstream MCP servers (gateway proxy)
129
-
130
- If your project uses other MCP servers that need secrets (API keys, bot tokens, etc.), proxy them through reagent's gateway rather than adding them directly to `.mcp.json`. This is the **only** way to pass env vars reliably from Claude Code.
131
-
132
- Edit `.reagent/gateway.yaml`:
133
-
134
- ```yaml
135
- version: '1'
136
-
137
- servers:
138
- discord-ops:
139
- command: npx
140
- args: ['-y', 'discord-ops@latest']
141
- env:
142
- BOOKED_DISCORD_BOT_TOKEN: '${BOOKED_DISCORD_BOT_TOKEN}'
143
- CLARITY_DISCORD_BOT_TOKEN: '${CLARITY_DISCORD_BOT_TOKEN}'
81
+ audit → session → kill-switch → tier → policy → blocked-paths →
82
+ rate-limit circuit-breaker redact injection result-size-cap → execute
144
83
  ```
145
84
 
146
- The `${VAR}` syntax here is resolved by reagent from `process.env` at gateway startup it works because reagent inherits the shell environment from Claude Code's process. The spawned child MCP server receives the resolved values.
85
+ **audit**Outermost layer. Records every invocation as a hash-chained JSONL entry
86
+ in `.reagent/audit.jsonl` before anything else runs. Denials are logged too. The chain
87
+ integrity means no entry can be modified without invalidating all subsequent hashes.
147
88
 
148
- Do **not** add the same server to both `gateway.yaml` and `.mcp.json` directly `reagent init` warns about this. Direct `.mcp.json` entries with `${VAR}` env values will pass the literal string, not the token.
89
+ **session** — Associates the call with a session UUID. Sessions are in-memory for the
90
+ lifetime of the `reagent serve` process.
149
91
 
150
- ### Step 4 Commit the config files
92
+ **kill-switch** Reads `.reagent/HALT` on every call. If the file exists, the call is
93
+ immediately denied with the reason from the file. No exceptions.
151
94
 
152
- `reagent init` generates files in two categories:
95
+ **tier** — Classifies the tool call as `read`, `write`, or `destructive` using the tool
96
+ name and the tier map from `gateway.yaml` tool overrides. Tier determines which autonomy
97
+ levels can call it.
153
98
 
154
- | File | Commit? |
155
- | ---------------------------- | --------------------------------------------------- |
156
- | `.reagent/policy.yaml` | Yes defines autonomy level for the team |
157
- | `.reagent/gateway.yaml` | Yes — documents which MCP servers this project uses |
158
- | `.claude/settings.json` | Yes — permission gates for Claude Code |
159
- | `.claude/hooks/` | Yes — safety and quality hooks |
160
- | `.claude/agents/` | Yes — agent team definitions |
161
- | `CLAUDE.md` (managed block) | Yes — behavioral rules for AI agents |
162
- | `.reagent/tasks.jsonl` | No — gitignored, local task store |
163
- | `.reagent/audit/` | No — gitignored, local audit log |
164
- | `.reagent/review-cache.json` | No — gitignored, local review cache |
99
+ **policy** Enforces `autonomy_level` from `policy.yaml`. L0 allows reads only. L1
100
+ allows reads and writes. L2 allows reads, writes, and PR creation. L3 allows everything.
101
+ A tool at a tier above the configured level is denied.
165
102
 
166
- ### Upgrading an existing install
103
+ **blocked-paths** Scans tool arguments for references to paths listed in
104
+ `policy.yaml:blocked_paths`. If an argument contains a blocked path, the call is denied.
105
+ This protects `.reagent/`, `.github/workflows/`, `.env`, and whatever else you configure.
167
106
 
168
- When a new version of reagent ships with updated hooks or agents:
107
+ **rate-limit** Enforces per-server `calls_per_minute` limits from `gateway.yaml`.
108
+ Calls that exceed the limit are denied. Legitimate calls don't burn rate budget for
109
+ calls already denied by earlier middleware.
169
110
 
170
- ```bash
171
- npx @bookedsolid/reagent upgrade
172
- ```
111
+ **circuit-breaker** — Tracks downstream server failures. After a configurable threshold
112
+ of consecutive errors, the breaker opens and calls to that server are denied until it
113
+ resets. Prevents cascading failures when a downstream MCP server is unhealthy.
173
114
 
174
- This re-syncs all hooks in `.claude/hooks/` and `.husky/` that were installed by a previous `reagent init`. It will not add hooks that weren't installed originally.
115
+ **redact** Scans tool arguments and results for secrets: AWS keys, GitHub tokens,
116
+ API keys, PEM private keys, Discord tokens, Stripe keys, generic bearer tokens, and
117
+ more. Matching values are replaced with `[REDACTED]` before they reach the model or
118
+ the downstream server.
175
119
 
176
- ### How `reagent serve` runs in Claude Code
120
+ **injection** Scans tool results from downstream servers for prompt injection patterns.
121
+ In `block` mode (default), detected injection attempts are denied. In `warn` mode, they
122
+ are flagged in the audit log but allowed through.
177
123
 
178
- When Claude Code reads `.mcp.json`, it spawns `npx -y @bookedsolid/reagent serve` as a child process. The MCP protocol runs over stdio between Claude Code and the reagent process. Reagent then spawns its own child processes for each entry in `gateway.yaml`, also over stdio.
124
+ **result-size-cap** Caps tool results at `gateway.options.max_result_size_kb` (default:
125
+ 1 MB). Oversized responses are truncated with a note. Prevents large downstream responses
126
+ from bloating context.
179
127
 
180
- The resulting process tree:
128
+ **execute** — The innermost layer. Calls the actual tool. For native tools, runs the
129
+ handler directly. For proxied tools, forwards the call to the downstream MCP server via
130
+ its stdio transport.
181
131
 
182
- ```
183
- Claude Code
184
- └── reagent serve (stdio MCP to Claude Code)
185
- └── discord-ops (stdio MCP, proxied through reagent)
186
- └── other-server (stdio MCP, proxied through reagent)
187
- ```
132
+ ### Policy and autonomy levels
188
133
 
189
- All tool calls from Claude Code go through reagent's middleware chain before reaching downstream servers.
134
+ `reagent init` writes `.reagent/policy.yaml` to your project:
190
135
 
191
- ## Commands
192
-
193
- | Command | Description |
194
- | ------------------------------- | ------------------------------------------------- |
195
- | `reagent serve` | Start the MCP gateway server (stdio transport) |
196
- | `reagent serve` | Start the MCP gateway server (stdio transport) |
197
- | `reagent init` | Install reagent config into the current directory |
198
- | `reagent upgrade` | Re-sync hooks and bump installed_by in policy |
199
- | `reagent catalyze` | Analyze project stack and generate gap report |
200
- | `reagent check` | Verify what reagent components are installed |
201
- | `reagent freeze --reason "..."` | Create `.reagent/HALT` — suspends all tool calls |
202
- | `reagent unfreeze` | Remove `.reagent/HALT` — resumes tool calls |
203
- | `reagent cache check <sha>` | Check review cache for a file SHA |
204
- | `reagent cache set <sha> <res>` | Store a review result (pass/fail/advisory) |
205
- | `reagent cache clear` | Clear all cached review results |
206
- | `reagent help` | Show usage help |
207
-
208
- ### `reagent init` Options
209
-
210
- | Flag | Description | Default |
211
- | ------------------------- | ---------------------------------------------- | ------------------- |
212
- | `--profile <name>` | Profile to install | `client-engagement` |
213
- | `--dry-run` | Preview what would be installed without writes | — |
214
- | `--github` | Scaffold GitHub labels, milestones, and topics | — |
215
- | `--discord` | Configure Discord notifications in gateway | — |
216
- | `--guild-id <id>` | Discord server ID (used with `--discord`) | — |
217
- | `--alerts-channel <id>` | Discord channel for security alerts | — |
218
- | `--tasks-channel <id>` | Discord channel for task events | — |
219
- | `--releases-channel <id>` | Discord channel for release events | — |
220
- | `--dev-channel <id>` | Discord channel for dev activity | — |
221
-
222
- ### `reagent upgrade` Options
223
-
224
- | Flag | Description | Default |
225
- | ----------- | -------------------------------------------- | ------- |
226
- | `--dry-run` | Preview what would be updated without writes | — |
136
+ ```yaml
137
+ version: '1'
138
+ profile: 'client-engagement'
139
+ installed_by: 'reagent@0.10.0'
140
+ installed_at: '2026-04-01T00:00:00.000Z'
141
+
142
+ # Autonomy levels:
143
+ # L0 Read-only; every write requires explicit user approval
144
+ # L1 Writes allowed to non-blocked paths; destructive operations blocked
145
+ # L2 Writes + PR creation allowed; destructive tier blocked
146
+ # L3 All writes allowed; advisory on anomalous patterns
147
+ autonomy_level: L2
148
+ max_autonomy_level: L3
149
+
150
+ # Human must approve any autonomy level increase
151
+ promotion_requires_human_approval: true
227
152
 
228
- Re-syncs hooks in `.claude/hooks/` and `.husky/` that were installed by a previous `reagent init`. Updates `installed_by` in `.reagent/policy.yaml`. Never adds hooks that weren't originally installed.
153
+ # Block AI attribution in commits and PRs
154
+ block_ai_attribution: true
229
155
 
230
- ### `reagent catalyze` Options
156
+ # Paths hooks and agents must never modify
157
+ blocked_paths:
158
+ - '.reagent/'
159
+ - '.github/workflows/'
160
+ - '.env'
161
+ - '.env.*'
231
162
 
232
- | Flag | Description | Default |
233
- | ------------- | ---------------------------------------------------- | ------- |
234
- | `--plan` | Analyze stack and generate gap report (default) | ✓ |
235
- | `--audit` | Compare current state against last plan, show drift | — |
236
- | `--dry-run` | Print analysis without writing files | — |
237
- | `[targetDir]` | Directory to analyze (defaults to current directory) | `cwd` |
163
+ # Optional: Discord webhook for halt/promote notifications
164
+ notification_channel: ''
238
165
 
239
- `--plan` generates `catalyze-report.md` and `catalyze-report.html` listing gaps by severity. `--audit` re-runs analysis and diffs against the previous report to surface new or resolved gaps.
166
+ quality_gates:
167
+ push_review: false
168
+ ```
240
169
 
241
- ### `reagent freeze` Options
170
+ The `autonomy_level` controls what tier of tools an agent can call. Raise it to give
171
+ an agent more authority; lower it (or freeze) to restrict it. `max_autonomy_level` is a
172
+ ceiling set by a human — no agent instruction can escalate beyond it.
242
173
 
243
- | Flag | Description | Default |
244
- | ----------------- | ---------------------------------- | --------------- |
245
- | `--reason <text>` | Reason for freeze (stored in HALT) | `Manual freeze` |
174
+ `block_ai_attribution: true` causes the `commit-msg` hook to reject commits that contain
175
+ `Co-Authored-By` lines with AI names, `Generated with [Tool]` footers, or similar
176
+ structural attribution markers. Casual mentions of AI tools in commit messages are
177
+ still allowed.
246
178
 
247
- ### `reagent cache` Subcommands
179
+ ### The kill switch
248
180
 
249
- The review cache stores code review results to avoid redundant agent reviews on unchanged code.
181
+ Create a HALT file to immediately block all agent operations:
250
182
 
251
183
  ```bash
252
- # Check if a file has a cached review
253
- reagent cache check abc123 --branch main --base def456
254
-
255
- # Store a review result
256
- reagent cache set abc123 pass --branch main --reviewer code-reviewer --findings 0 --ttl 86400
257
-
258
- # Clear all cache entries
259
- reagent cache clear
184
+ reagent freeze --reason "releasing to production no agent changes"
260
185
  ```
261
186
 
262
- | Flag | Description | Default |
263
- | ------------------- | ------------------------- | --------- |
264
- | `--branch <name>` | Branch name for cache key | `""` |
265
- | `--base <commit>` | Base commit for cache key | `""` |
266
- | `--reviewer <name>` | Reviewer agent name | `unknown` |
267
- | `--findings <n>` | Number of findings | `0` |
268
- | `--ttl <seconds>` | Cache entry TTL | `86400` |
269
-
270
- Cache file: `.reagent/review-cache.json`, keyed on `${branch}:${baseCommit}:${fileSHA256}`.
271
-
272
- ## MCP Gateway
187
+ This creates `.reagent/HALT` with your reason as the content. Every hook checks for this
188
+ file at the top of its script. Every tool call checks it at the kill-switch middleware
189
+ layer. Nothing gets through.
273
190
 
274
- ### How It Works
191
+ Remove it when you're ready to resume:
275
192
 
193
+ ```bash
194
+ reagent unfreeze
276
195
  ```
277
- AI Assistant (Claude Code, Cursor, etc.)
278
- |
279
- | stdio (MCP protocol)
280
- v
281
- +-----------------------------+
282
- | Reagent Gateway |
283
- | |
284
- | +------------------------+ |
285
- | | Middleware Chain | |
286
- | | | |
287
- | | 1. Audit (outermost) | |
288
- | | 2. Session context | |
289
- | | 3. Kill switch | |
290
- | | 4. Tier classify | |
291
- | | 5. Policy enforce | |
292
- | | 6. Blocked paths | |
293
- | | 7. Secret redaction | |
294
- | | 8. [Execute] | |
295
- | +------------------------+ |
296
- | |
297
- | Native Tools: |
298
- | task_create, task_update |
299
- | task_list, task_get |
300
- | task_delete |
301
- | task_sync_github |
302
- | repo_scaffold |
303
- | project_sync |
304
- | discord_notify |
305
- | |
306
- +----------+------------------+
307
- | stdio (MCP protocol)
308
- v
309
- Downstream MCP Servers
310
- (discord-ops, filesystem, etc.)
311
- ```
312
-
313
- The gateway:
314
196
 
315
- 1. Connects to all downstream MCP servers defined in `.reagent/gateway.yaml`
316
- 2. Discovers their tools via MCP `tools/list`
317
- 3. Re-registers each tool on the gateway with namespace prefixes (`servername__toolname`)
318
- 4. Registers native first-party tools through the same middleware chain
319
- 5. Wraps every tool call in the middleware chain
320
- 6. Listens on stdio for incoming MCP requests from the AI assistant
197
+ The HALT file is a plain text file in your project. You can also create or delete it
198
+ manually, or add it to your release process as a safety gate.
321
199
 
322
- ### Native MCP Tools
200
+ ## Connecting additional MCP servers
323
201
 
324
- Reagent registers 9 first-party tools directly on the gateway. These go through the same middleware chain (audit, policy, blocked paths, redaction) as proxied tools.
325
-
326
- | Tool | Description |
327
- | ------------------ | ------------------------------------------------------- |
328
- | `task_create` | Create a new task in `.reagent/tasks.jsonl` |
329
- | `task_update` | Update a task's status, title, urgency, or fields |
330
- | `task_list` | List tasks with optional status/urgency/phase filter |
331
- | `task_get` | Get a single task by ID (T-NNN format) |
332
- | `task_delete` | Cancel a task (soft delete via cancelled event) |
333
- | `task_sync_github` | Sync local tasks to GitHub issues (requires `gh`) |
334
- | `repo_scaffold` | Set GitHub repo description, topics, labels, milestones |
335
- | `project_sync` | Sync tasks to a GitHub Project board |
336
- | `discord_notify` | Send a notification to a configured Discord channel |
337
-
338
- ### Gateway Configuration
339
-
340
- Create `.reagent/gateway.yaml`:
202
+ Instead of listing servers directly in `.mcp.json` (which would bypass reagent's
203
+ middleware), add them to `.reagent/gateway.yaml`:
341
204
 
342
205
  ```yaml
343
206
  version: '1'
344
- servers:
345
- discord-ops:
346
- command: node
347
- args:
348
- - /path/to/discord-ops/dist/index.js
349
- env:
350
- DISCORD_BOT_TOKEN: '${DISCORD_BOT_TOKEN}'
351
- tool_overrides:
352
- get_messages:
353
- tier: read
354
- send_message:
355
- tier: write
356
- purge_messages:
357
- tier: destructive
358
- delete_channel:
359
- tier: destructive
360
- blocked: true
361
- ```
362
-
363
- **Environment variable resolution:** Use `${VAR_NAME}` syntax in env values — Reagent resolves them from `process.env` at startup. Missing env vars produce a warning and resolve to empty string.
364
-
365
- **Tool overrides:** Each downstream tool can be assigned a tier (`read`, `write`, `destructive`) and optionally blocked entirely. Overrides cannot lower a tool's tier below its static or convention-based classification (the override is ignored with a warning if attempted).
366
-
367
- #### Discord Notifications (optional)
368
-
369
- When `--discord` is passed to `reagent init`, a `discord_ops` block is appended to gateway.yaml:
370
-
371
- ```yaml
372
- discord_ops:
373
- guild_id: '1234567890'
374
- channels:
375
- alerts: '111'
376
- tasks: '222'
377
- releases: '333'
378
- dev: '444'
379
- ```
380
-
381
- The `discord_notify` native tool reads this config to route notifications. All Discord notifications are fire-and-forget (fail-silent).
382
-
383
- ### Tool Namespacing
384
-
385
- Downstream tools are namespaced as `servername__toolname` to prevent collisions:
386
-
387
- ```
388
- discord-ops__send_message
389
- discord-ops__get_messages
390
- filesystem__read_file
391
- filesystem__write_file
392
- ```
393
207
 
394
- ### Multiple Downstream Servers
395
-
396
- ```yaml
397
- version: '1'
398
208
  servers:
399
- discord-ops:
400
- command: node
401
- args: [/path/to/discord-ops/dist/index.js]
402
209
  filesystem:
403
210
  command: npx
404
- args: [-y, '@modelcontextprotocol/server-filesystem', '/allowed/path']
211
+ args: ['@modelcontextprotocol/server-filesystem', '/home/user/projects']
212
+
405
213
  github:
406
214
  command: npx
407
- args: [-y, '@modelcontextprotocol/server-github']
215
+ args: ['@modelcontextprotocol/server-github']
408
216
  env:
409
- GITHUB_PERSONAL_ACCESS_TOKEN: '${GITHUB_TOKEN}'
410
- ```
411
-
412
- All tools from all servers are aggregated into a single gateway.
217
+ GITHUB_TOKEN: '${GITHUB_PERSONAL_ACCESS_TOKEN}'
413
218
 
414
- ## Middleware Chain
219
+ postgres:
220
+ command: npx
221
+ args: ['@modelcontextprotocol/server-postgres', '${DATABASE_URL}']
222
+ calls_per_minute: 60
223
+ max_concurrent_calls: 5
224
+ tool_overrides:
225
+ execute_query:
226
+ tier: destructive
415
227
 
416
- Every tool call passes through the middleware chain in onion (Koa-style) order. The chain is designed with security invariants:
228
+ gateway:
229
+ max_result_size_kb: 512
230
+ ```
417
231
 
418
- ### 1. Audit (outermost)
232
+ When `reagent serve` starts, it connects to each server, discovers its tools, and
233
+ re-registers them on the reagent MCP server with namespaced names
234
+ (e.g., `filesystem__read_file`, `github__create_issue`). Every call to a proxied tool
235
+ goes through the full middleware chain before forwarding.
419
236
 
420
- Records every invocation including denials and errors — as a hash-chained JSONL entry. Written to `.reagent/audit/YYYY-MM-DD.jsonl`. Each record contains:
237
+ **`tool_overrides`** let you reclassify a tool's tier or block it entirely:
421
238
 
422
- ```json
423
- {
424
- "timestamp": "2026-04-09T12:00:00.000Z",
425
- "session_id": "a1b2c3d4-...",
426
- "tool_name": "send_message",
427
- "server_name": "discord-ops",
428
- "tier": "write",
429
- "status": "allowed",
430
- "autonomy_level": "L1",
431
- "duration_ms": 42,
432
- "prev_hash": "0000...0000",
433
- "hash": "abc123..."
434
- }
239
+ ```yaml
240
+ tool_overrides:
241
+ execute_query:
242
+ tier: destructive # Treat this tool as destructive regardless of its name
243
+ drop_table:
244
+ blocked: true # Always deny calls to this tool, regardless of autonomy level
435
245
  ```
436
246
 
437
- The `prev_hash` field chains records together — tamper with one record and every subsequent hash becomes invalid. Audit writes are serialized via a queue to maintain hash chain linearity under concurrent invocations. The `autonomy_level` is sourced from the loaded policy object, not from mutable invocation context.
438
-
439
- ### 2. Session Context
247
+ **`calls_per_minute`** and **`max_concurrent_calls`** are per-server rate limits enforced
248
+ by the rate-limit middleware.
440
249
 
441
- Attaches a unique session ID (UUID via `crypto.randomUUID()`) to every invocation. Each gateway instance generates one session ID at startup.
250
+ `${ENV_VAR}` references in `env` blocks are resolved at startup from the environment
251
+ where `reagent serve` runs.
442
252
 
443
- ### 3. Kill Switch
253
+ ## Profiles
444
254
 
445
- Checks for `.reagent/HALT` file. If present, the invocation is immediately denied. The HALT file contents become the denial reason. Reads are capped at 1024 bytes. The file is validated as a regular file (symlinks outside `.reagent/` are rejected).
255
+ `reagent init` accepts a `--profile` flag to install a pre-built configuration:
446
256
 
447
257
  ```bash
448
- # Emergency stopall tool calls blocked immediately
449
- reagent freeze --reason "security incident at 2026-04-09T12:00:00Z"
258
+ # Base profiles (full setup install one or the other)
259
+ reagent init # client-engagement (default)
260
+ reagent init --profile bst-internal # BST internal projects
450
261
 
451
- # Resume
452
- reagent unfreeze
262
+ # Tech stack profiles (add to a base profile)
263
+ reagent init --profile lit-wc # Lit/Web Components hooks
264
+ reagent init --profile astro # Astro framework hooks
265
+ reagent init --profile nextjs # Next.js App Router hooks
266
+ reagent init --profile drupal # Drupal CMS hooks
453
267
  ```
454
268
 
455
- ### 4. Tier Classification
456
-
457
- Classifies the tool into one of three tiers using a layered approach:
458
-
459
- | Source | Priority | Description |
460
- | ---------------- | -------- | ------------------------------------------ |
461
- | Static map | 1st | Known tools with explicit tier assignments |
462
- | Convention-based | 2nd | Prefix patterns for unknown tools |
463
- | Default | 3rd | Falls back to `write` |
464
-
465
- **Convention-based classification** allows non-Discord downstream servers to get sensible defaults:
466
-
467
- | Prefix pattern | Tier |
468
- | ------------------------------------------------------------------------------------------------------------ | ------------- |
469
- | `get_`, `list_`, `search_`, `query_`, `read_`, `fetch_`, `check_`, `health_`, `describe_`, `show_`, `count_` | `read` |
470
- | `delete_`, `drop_`, `purge_`, `remove_`, `destroy_`, `ban_`, `kick_`, `revoke_`, `truncate_` | `destructive` |
471
- | Everything else | `write` |
472
-
473
- **Tier levels:**
474
-
475
- | Tier | Description | Examples |
476
- | ------------- | ------------------------------- | ------------------------------------------------ |
477
- | `read` | Observes state, no side effects | `get_messages`, `list_channels`, `health_check` |
478
- | `write` | Modifies state | `send_message`, `create_channel`, `edit_message` |
479
- | `destructive` | Irreversible state changes | `delete_channel`, `purge_messages`, `ban_member` |
480
-
481
- ### 5. Policy Enforcement
482
-
483
- Checks the tool's tier against the project's autonomy level. The policy middleware re-derives the tier from the tool name independently — it never trusts `ctx.tier` from prior middleware.
484
-
485
- | Autonomy Level | Allowed Tiers |
486
- | ------------------ | -------------------------------- |
487
- | `L0` (read-only) | `read` |
488
- | `L1` (standard) | `read` + `write` |
489
- | `L2` (elevated) | `read` + `write` |
490
- | `L3` (full access) | `read` + `write` + `destructive` |
491
-
492
- Also checks for explicitly blocked tools — a tool marked `blocked: true` in gateway config is denied regardless of autonomy level.
493
-
494
- ### 6. Blocked Paths
495
-
496
- Scans all string-valued tool arguments for references to paths listed in the policy's `blocked_paths`. The `.reagent/` directory is always protected regardless of policy configuration. Matching uses normalized path containment (backslashes converted to forward slashes, relative path variants checked).
497
-
498
- ### 7. Secret Redaction
499
-
500
- Operates both **pre-execution** (scanning tool arguments before they reach the downstream tool) and **post-execution** (scanning tool output before it reaches the AI). Detected patterns are replaced with `[REDACTED]`:
269
+ Tech stack profiles compose on top of the `client-engagement` base by default. You can
270
+ specify a different base:
501
271
 
502
- - AWS Access Keys (`AKIA...`)
503
- - AWS Secret Keys
504
- - GitHub Tokens (`ghp_...`, `gho_...`, `ghs_...`, `ghu_...`, `ghr_...`)
505
- - Generic API Keys
506
- - Bearer Tokens
507
- - PEM Private Keys (RSA, EC, DSA)
508
- - Discord Bot Tokens
509
- - Base64-encoded AWS Keys
510
-
511
- Redaction uses `redactDeep` to walk object structures in-place with a circular reference guard (WeakSet). Input is sanitized (null bytes and control characters stripped) before pattern matching.
512
-
513
- ### Security Invariants
514
-
515
- - **Denial is permanent** — once any middleware denies an invocation, no subsequent middleware can revert it (enforced by `executeChain`)
516
- - **Audit records everything** audit is outermost, so even kill-switch denials are recorded
517
- - **Policy re-derives tier** — never trusts mutable context; always re-classifies from tool name
518
- - **Fail-closed** — errors in kill-switch or policy checks result in denial, not passthrough
519
- - **All logging to stderr** — stdout is reserved for the MCP stdio transport
520
- - **Per-tool timeout** each downstream tool call has a 30-second timeout with timer cleanup to prevent leaks
521
- - **Graceful shutdown**`process.exitCode = 0` (not `process.exit(0)`) to allow event loop drain
522
-
523
- ## Claude Code Hooks
524
-
525
- Reagent installs 20 Claude Code hooks that enforce security, quality, and project management policies. Hooks are shell scripts that run as PreToolUse or PostToolUse interceptors.
526
-
527
- ### Hook Architecture
528
-
529
- Hooks use a shared library (`hooks/_lib/common.sh`) providing:
530
-
531
- | Function | Purpose |
532
- | -------------- | ----------------------------------------------------- |
533
- | `reagent_root` | Find the `.reagent/` directory by walking up from cwd |
534
- | `check_halt` | Exit with code 2 if `.reagent/HALT` exists |
535
- | `require_jq` | Verify jq is available |
536
- | `json_output` | Build structured JSON response (block/allow/advisory) |
537
- | `triage_score` | Score a diff as trivial/standard/significant |
538
-
539
- ### Exit Code Convention
540
-
541
- | Code | Meaning |
542
- | ---- | ------------------- |
543
- | `0` | Allow the tool call |
544
- | `2` | Block the tool call |
545
-
546
- ### Security Hooks
547
-
548
- #### `settings-protection.sh` (PreToolUse: Write, Edit)
549
-
550
- **P0 Critical.** Prevents agents from modifying their own safety rails. Blocks writes to:
551
-
552
- - `.claude/settings.json`, `.claude/settings.local.json`
553
- - `.claude/hooks/*`
554
- - `.husky/*`
555
- - `.reagent/policy.yaml`, `.reagent/HALT`, `.reagent/review-cache.json`
556
-
557
- Includes case-insensitive bypass detection and URL-decode normalization to prevent encoding attacks.
558
-
559
- #### `blocked-paths-enforcer.sh` (PreToolUse: Write, Edit)
560
-
561
- **P0 Critical.** Reads `blocked_paths` from `.reagent/policy.yaml` and blocks writes to matching paths. Handles both inline YAML arrays (`[a, b]`) and block sequences. Supports directory prefix matching, glob patterns, and exact match.
562
-
563
- #### `dangerous-bash-interceptor.sh` (PreToolUse: Bash)
564
-
565
- Intercepts dangerous shell commands before execution:
566
-
567
- | Detection | Blocked Command Pattern |
568
- | --------- | ----------------------------------------------------------------------------------- |
569
- | H1 | `git push --force` / `-f` to protected branches (main, master, staging, production) |
570
- | H2 | `rm -rf /` or `rm -rf ~` |
571
- | H3 | `chmod 777` |
572
- | H4 | `curl \| sh`, `wget \| sh` (pipe-to-shell) |
573
- | H5 | `> /dev/sda` (disk overwrite) |
574
- | H6 | `:(){ :\|:& };:` (fork bomb) |
575
- | H7 | `mkfs` (disk format) |
576
- | H8 | `dd if=` (disk copy) |
577
- | H9 | `.env` file access via cat/less/head/tail |
578
- | H10 | `shutdown`, `reboot`, `halt`, `poweroff` |
579
- | H11 | `kill -9`, `killall`, `pkill` |
580
- | H12 | `iptables` / `ufw` (firewall modification) |
581
- | H13 | `git push --no-verify` |
582
- | H14 | `git -c core.hooksPath=` (hook path override) |
583
- | H15 | `REAGENT_BYPASS` environment variable |
584
- | H16 | Alias/function definitions containing bypass strings |
585
-
586
- #### `secret-scanner.sh` (PreToolUse: Write, Edit)
587
-
588
- Scans file content being written for secrets:
589
-
590
- - AWS Access Keys (`AKIA...`)
591
- - PEM private key headers (RSA, EC, DSA)
592
- - GitHub PATs (`ghp_`, `gho_`, `ghs_`, `ghu_`, `ghr_` with 36+ chars)
593
- - Stripe live keys (`sk_live_`)
594
- - Generic `SECRET=`/`PASSWORD=`/`TOKEN=`/`API_KEY=` assignments with real values
595
-
596
- Allows placeholders (`<your_key_here>`, `changeme`, `xxx`), `process.env` references, and `.env.example` files.
597
-
598
- #### `env-file-protection.sh` (PreToolUse: Write, Edit)
599
-
600
- Blocks writes to `.env` files (`.env`, `.env.local`, `.env.production`, etc.). Allows `.env.example` and `.env.template` files.
601
-
602
- #### `attribution-advisory.sh` (PreToolUse: Bash)
603
-
604
- When `block_ai_attribution` is enabled in policy.yaml, blocks `gh pr create`, `gh pr edit`, and `git commit` commands containing AI attribution patterns:
605
-
606
- - `Co-Authored-By` with AI names (Claude, Copilot, GPT, Cursor, etc.)
607
- - `Generated with [Tool]` footers
608
- - `AI-generated` markers
609
-
610
- #### `symlink-guard.sh` (PreToolUse: Write, Edit)
611
-
612
- Detects symlink traversal attempts — blocks writes to paths that resolve through a symlink outside the project root.
613
-
614
- #### `network-exfil-guard.sh` (PreToolUse: Bash)
615
-
616
- Blocks `curl`/`wget`/`fetch` commands targeting non-allowlisted external hosts from within Claude tool calls. Prevents data exfiltration via outbound HTTP.
617
-
618
- #### `import-guard.sh` (PreToolUse: Write, Edit)
619
-
620
- Flags dangerous import patterns being written to source files — `eval`, `Function()`, dynamic `require()` with user-controlled input, and known supply-chain risk patterns.
621
-
622
- #### `git-config-guard.sh` (PreToolUse: Bash)
623
-
624
- Blocks `git config` commands that override hook paths, rewrite signing, or modify credential helpers in ways that could bypass security controls.
625
-
626
- #### `ci-config-protection.sh` (PreToolUse: Write, Edit)
627
-
628
- Blocks writes to `.github/workflows/` and other CI configuration files. Prevents agents from modifying pipeline definitions that run in elevated contexts.
629
-
630
- ### Quality Gate Hooks
631
-
632
- #### `commit-review-gate.sh` (PreToolUse: Bash)
633
-
634
- Intercepts `git commit` commands and applies triage-based review:
635
-
636
- | Triage Level | Criteria | Action |
637
- | --------------- | ------------------------------------- | ---------------------------------------------- |
638
- | **Trivial** | <20 changed lines, no sensitive paths | Pass immediately |
639
- | **Standard** | 20-200 changed lines | Check review cache; pass if cached |
640
- | **Significant** | >200 lines OR sensitive paths | Block; instruct agent to spawn `code-reviewer` |
641
-
642
- Sensitive paths: `.reagent/`, `.claude/`, `.env`, `auth`, `security`, `.github/workflows`.
643
-
644
- Returns `additionalContext` instructing the agent to spawn a `code-reviewer` specialist agent when blocked.
645
-
646
- #### `push-review-gate.sh` (PreToolUse: Bash)
647
-
648
- Intercepts `git push` commands. Analyzes the full diff against the target branch:
649
-
650
- 1. Computes triage score of all commits being pushed
651
- 2. Checks review cache for cached results
652
- 3. On cache miss for standard/significant changes: blocks with instructions to spawn `code-reviewer` and `security-engineer` agents
653
-
654
- #### `architecture-review-gate.sh` (PostToolUse: Write, Edit)
655
-
656
- **Advisory only (never blocks).** Flags writes to architecture-sensitive paths:
657
-
658
- - `src/types/`, `src/gateway/`, `src/config/`
659
- - `src/cli/commands/init/`
660
- - `package.json`, `tsconfig*.json`
661
- - `.github/workflows/`
662
-
663
- Returns a stderr advisory suggesting the agent consider architectural implications.
664
-
665
- ### Project Management Hooks
666
-
667
- #### `task-link-gate.sh` (PreToolUse: Bash)
668
-
669
- **Opt-in** (requires `task_link_gate: true` in policy.yaml). Intercepts `git commit` commands and checks that the commit message contains a task ID reference (`T-NNN` format). Allows merge commits, version bumps, and `chore:`/`style:`/`ci:` prefixed commits without task references.
670
-
671
- #### `dependency-audit-gate.sh` (PreToolUse: Bash)
272
+ ```bash
273
+ reagent init --profile lit-wc --base-profile bst-internal
274
+ ```
275
+
276
+ The `client-engagement` profile installs:
277
+
278
+ - Claude Code hooks for dangerous bash interception, secret scanning, env file protection,
279
+ dependency auditing, commit review, push review, security disclosure gates, settings
280
+ protection, blocked path enforcement, changeset security, and architecture review
281
+ - Cursor rules: no-hallucination, verify-before-act, attribution
282
+ - `block_ai_attribution: true` in `policy.yaml`
283
+ - `blocked_paths: ['.reagent/', '.github/workflows/', '.env', '.env.*']`
284
+ - Quality gates: commit review (trivial threshold: 20 lines, significant: 200 lines),
285
+ push review, architecture advisory
286
+ - PM layer enabled with max 50 open tasks
287
+
288
+ ## Hooks
289
+
290
+ reagent installs 23 Claude Code hooks into `.claude/hooks/`. Every hook checks for
291
+ `.reagent/HALT` at the top if it exists, the hook returns exit code 2 (hard block)
292
+ immediately.
293
+
294
+ **Pre-tool-use hooks (Bash matcher):**
295
+
296
+ - `dangerous-bash-interceptor` — Blocks `rm -rf` with broad targets, `curl | bash`,
297
+ `chmod 777`, force-push to protected branches, and other high-risk bash patterns.
298
+ Uses a severity tiering system: HIGH blocks outright, MEDIUM warns.
299
+ - `env-file-protection` Prevents reads and writes to `.env`, `.env.*`, and other
300
+ secret-bearing files.
301
+ - `dependency-audit-gate` — Intercepts `npm install`, `pnpm add`, and similar commands.
302
+ Verifies the package exists in the npm registry before allowing installation.
303
+ - `commit-review-gate` Before a `git commit`, checks the diff size. Significant
304
+ changes trigger a structured review request that the agent must satisfy.
305
+ - `push-review-gate` Before `git push`, performs a final quality gate check.
306
+ - `security-disclosure-gate` Intercepts `gh issue create` and similar commands. Blocks
307
+ public disclosure of security vulnerabilities; routes to the configured disclosure mode
308
+ (issues, security advisories, etc.).
309
+ - `pr-issue-link-gate` Requires every PR to reference a GitHub issue.
310
+ - `attribution-advisory` — When `block_ai_attribution` is enabled, blocks `git commit`
311
+ and `gh pr create/edit` commands that include AI attribution markers in their content.
312
+
313
+ **Pre-tool-use hooks (Write|Edit matcher):**
314
+
315
+ - `secret-scanner` — Scans file content being written or edited for secrets: AWS keys,
316
+ GitHub tokens, PEM private keys, Discord tokens, Stripe keys, and more. Blocks the
317
+ write if a secret is detected.
318
+ - `settings-protection` — Prevents writes to `.claude/settings.json` that would disable
319
+ hooks or add risky permissions. Allows agent writes to task files and non-security
320
+ operational files.
321
+ - `blocked-paths-enforcer` — Enforces `blocked_paths` from `policy.yaml` for file
322
+ writes and edits. The middleware chain enforces this for tool calls; this hook enforces
323
+ it for direct file operations.
324
+ - `changeset-security-gate` — Validates changeset files before they are written. Prevents
325
+ injection of malicious content into the changeset workflow.
326
+
327
+ **Post-tool-use hooks (Write|Edit matcher):**
328
+
329
+ - `architecture-review-gate` After significant file edits, checks the change against
330
+ the project's architecture plan and flags deviations.
331
+
332
+ **Additional hooks installed by tech stack profiles:**
333
+
334
+ - `commit-msg` (husky) — Enforces commit message format and rejects AI attribution
335
+ markers when `block_ai_attribution: true`.
336
+ - `pre-commit` (husky) — Runs quality checks before each commit.
337
+ - `pre-push` (husky) Runs the full preflight before push.
338
+
339
+ The hooks in `.claude/hooks/` use a shared `_lib/` directory for common functions
340
+ including HALT checking, policy loading, and output formatting.
341
+
342
+ ## Task management
343
+
344
+ reagent includes a lightweight project management layer with native MCP tools. Tasks
345
+ are stored as append-only JSONL in `.reagent/tasks.jsonl`. Each line is a JSON event
346
+ (created, started, completed, blocked, cancelled) with a task ID in `T-NNN` format.
347
+
348
+ **Native MCP tools:**
349
+
350
+ - `task_create` Create a task with title, description, urgency (critical/normal/low),
351
+ phase, milestone, assignee, and optional parent task ID.
352
+ - `task_update` Update a task's status (started, completed, blocked, cancelled) and
353
+ fields. When a task is completed and has a `github_issue` reference, the linked issue
354
+ is closed automatically.
355
+ - `task_list` — List tasks with optional filters for status, urgency, and phase.
356
+ - `task_get` Get a single task by ID.
357
+ - `task_delete` — Soft-delete a task (appends a `cancelled` event).
358
+ - `task_sync_github` Sync local tasks to GitHub issues (requires `gh` CLI).
359
+ - `repo_scaffold` — Scaffold GitHub repo metadata: description, topics, labels
360
+ (`reagent:task`, `reagent:critical`, `reagent:blocked`), and milestones.
361
+ - `project_sync` Sync tasks with GitHub issues to a GitHub Projects v2 board.
362
+ - `discord_notify` Send a notification to a configured Discord channel
363
+ (alerts, releases, tasks, dev). Requires `discord_ops` in `gateway.yaml` and
364
+ `DISCORD_BOT_TOKEN` in the environment.
365
+
366
+ All native tools go through the same middleware chain as proxied tools — the kill switch,
367
+ policy, blocked paths, redaction, and audit all apply.
368
+
369
+ The `/tasks` slash command and the `pm-status` agent provide a product-owner view of
370
+ the task board from within Claude Code conversations.
371
+
372
+ **Example `tasks.jsonl` entries:**
373
+
374
+ ```jsonl
375
+ {"id":"T-001","type":"created","title":"Implement login flow","urgency":"critical","timestamp":"2026-04-01T10:00:00.000Z"}
376
+ {"id":"T-001","type":"started","title":"Implement login flow","assignee":"frontend-specialist","timestamp":"2026-04-01T10:05:00.000Z"}
377
+ {"id":"T-001","type":"completed","title":"Implement login flow","commit_refs":["abc1234"],"pr_ref":"#42","timestamp":"2026-04-01T14:30:00.000Z"}
378
+ ```
379
+
380
+ ## CLI reference
381
+
382
+ ```
383
+ reagent init [options]
384
+ --profile <name> Profile to install (default: client-engagement)
385
+ --base-profile <name> Base profile to use with a tech stack profile
386
+ --dry-run Preview what would be installed without writing files
387
+ --github Configure GitHub integration in gateway.yaml
388
+ --discord Configure Discord notifications in gateway.yaml
389
+ --guild-id <id> Discord guild ID
390
+ --alerts-channel <id> Discord channel ID for security alerts
391
+ --tasks-channel <id> Discord channel ID for task events
392
+ --releases-channel Discord channel ID for release events
393
+ --dev-channel <id> Discord channel ID for dev activity
672
394
 
673
- Intercepts `npm install`, `pnpm add`, `yarn add`, and `npx` commands. Extracts package names and verifies each exists in the npm registry via `npm view` before allowing the install.
395
+ reagent serve
396
+ Starts the MCP server on stdio. Loaded by Claude Code via .mcp.json.
397
+ Reads .reagent/policy.yaml and .reagent/gateway.yaml from the current directory.
674
398
 
675
- ### Safety Hooks
399
+ reagent check
400
+ Checks which reagent components are installed in the current project.
676
401
 
677
- #### `output-validation.sh` (PostToolUse)
402
+ reagent freeze --reason "<reason>"
403
+ Creates .reagent/HALT with the provided reason. Immediately blocks all
404
+ agent tool calls and hook-guarded bash commands.
678
405
 
679
- Scans tool output returned to the AI for secrets before they enter the model's context. Same pattern set as `secret-scanner.sh`.
406
+ reagent unfreeze
407
+ Removes .reagent/HALT. Resumes agent operations.
680
408
 
681
- #### `file-size-guard.sh` (PreToolUse: Write)
409
+ reagent catalyze [targetDir]
410
+ --plan Analyze project stack and generate a gap analysis report (default)
411
+ --audit Compare current state against the last plan and show drift
412
+ --dry-run Print analysis without writing files
682
413
 
683
- Blocks writes of files exceeding a configurable size threshold. Prevents runaway code generation from creating oversized blobs.
414
+ reagent upgrade [--dry-run]
415
+ Re-syncs installed hooks from the current package version and updates the
416
+ version stamp in policy.yaml. Run after upgrading the reagent package.
684
417
 
685
- #### `rate-limit-guard.sh` (PreToolUse)
418
+ reagent cache <set|get|del> <key> [value]
419
+ Manages the review cache used by commit-review-gate and push-review-gate.
420
+ ```
686
421
 
687
- Tracks tool call frequency per session and blocks when a per-minute threshold is exceeded. Logged to `.reagent/rate-limit.log`.
422
+ ## Configuration
688
423
 
689
- ## Policy File
424
+ ### `.reagent/policy.yaml`
690
425
 
691
- `.reagent/policy.yaml` controls agent behavior:
426
+ The primary policy file. Committed to the repo. Describes the autonomy level, blocked
427
+ paths, and quality gate settings for this project.
692
428
 
693
429
  ```yaml
694
430
  version: '1'
695
- profile: bst-internal
696
- installed_by: 'reagent@0.7.2'
697
- installed_at: '2026-04-09T00:00:00.000Z'
698
- autonomy_level: L1
699
- max_autonomy_level: L2
431
+ profile: 'client-engagement'
432
+ autonomy_level: L2 # L0 | L1 | L2 | L3
433
+ max_autonomy_level: L3 # ceiling — agents cannot escalate beyond this
700
434
  promotion_requires_human_approval: true
701
- block_ai_attribution: true
435
+ block_ai_attribution: true # reject AI attribution in commits and PRs
702
436
  blocked_paths:
703
437
  - '.reagent/'
438
+ - '.github/workflows/'
704
439
  - '.env'
705
440
  - '.env.*'
706
- notification_channel: ''
707
- task_link_gate: false
708
- ```
709
-
710
- | Field | Type | Description |
711
- | ----------------------------------- | ---------- | ------------------------------------------------------------- |
712
- | `version` | `string` | Schema version (currently `"1"`) |
713
- | `profile` | `string` | Profile name used during init |
714
- | `installed_by` | `string` | Tool and version that generated this file |
715
- | `installed_at` | `string` | ISO 8601 timestamp of installation |
716
- | `autonomy_level` | `enum` | Current level (L0-L3) — controls which tool tiers are allowed |
717
- | `max_autonomy_level` | `enum` | Ceiling — `autonomy_level` is clamped to this on load |
718
- | `promotion_requires_human_approval` | `boolean` | Whether level changes need human sign-off |
719
- | `block_ai_attribution` | `boolean` | When true, commit-msg hook rejects AI attribution markers |
720
- | `blocked_paths` | `string[]` | Paths the agent must never modify (`.reagent/` always added) |
721
- | `notification_channel` | `string` | Optional notification channel identifier |
722
- | `task_link_gate` | `boolean` | When true, commits must reference a task ID (T-NNN) |
723
-
724
- The `max_autonomy_level` field is enforced at config load time: if `autonomy_level` exceeds `max_autonomy_level`, it is clamped down with a warning.
725
-
726
- ## Project Management
727
-
728
- Reagent includes a lightweight project management layer for tracking tasks alongside code.
729
-
730
- ### Task Store
731
-
732
- Tasks are stored as an append-only event log in `.reagent/tasks.jsonl`. Each line is a JSON event:
733
-
734
- ```json
735
- {"id":"T-001","type":"created","title":"Implement review cache","urgency":"normal","phase":"Phase 2","timestamp":"2026-04-09T12:00:00.000Z"}
736
- {"id":"T-001","type":"started","title":"Implement review cache","timestamp":"2026-04-09T13:00:00.000Z"}
737
- {"id":"T-001","type":"completed","title":"Implement review cache","commit_refs":["abc123"],"timestamp":"2026-04-09T14:00:00.000Z"}
441
+ notification_channel: '' # Discord webhook for halt/promote events
442
+ quality_gates:
443
+ push_review: false
738
444
  ```
739
445
 
740
- The current state of each task is materialized by replaying events — the latest event for each task ID determines its status. This append-only design means no data is ever lost and concurrent writes are safe with advisory file locking.
741
-
742
- #### Task Schema
743
-
744
- | Field | Type | Required | Description |
745
- | -------------- | ------------------------------------------------- | -------- | ----------------------------- |
746
- | `id` | `string` (T-NNN) | Yes | Auto-incrementing task ID |
747
- | `type` | `created\|started\|completed\|blocked\|cancelled` | Yes | Event type |
748
- | `title` | `string` (1-200 chars) | Yes | Task title |
749
- | `description` | `string` | No | Detailed description |
750
- | `urgency` | `critical\|normal\|low` | No | Defaults to `normal` |
751
- | `phase` | `string` | No | Project phase |
752
- | `milestone` | `string` | No | Milestone reference |
753
- | `assignee` | `string` | No | Assigned agent or person |
754
- | `parent_id` | `string` (T-NNN) | No | Parent task for hierarchy |
755
- | `commit_refs` | `string[]` | No | Related commit SHAs |
756
- | `pr_ref` | `string` | No | Related PR reference |
757
- | `blocked_by` | `string` | No | What's blocking this task |
758
- | `github_issue` | `number` | No | Linked GitHub issue number |
759
- | `timestamp` | `string` (ISO 8601) | Yes | Event timestamp |
760
- | `session_id` | `string` | No | Agent session that created it |
761
-
762
- All fields are validated with Zod on read. Malformed lines are skipped with a stderr warning.
763
-
764
- ### GitHub Bridge
765
-
766
- The GitHub bridge syncs local tasks to GitHub issues:
446
+ ### `.reagent/gateway.yaml`
767
447
 
768
- - **Detection:** checks for `gh` CLI with `gh auth status`. Falls back to `local-only` mode if unavailable.
769
- - **Sync scope:** only creates issues with the `reagent:` label. Never imports all repository issues.
770
- - **Rate limiting:** 300-second cooldown between sync operations.
771
- - **Conflict resolution:** local JSONL is the source of truth; GitHub is the display layer.
772
- - **Auto-close:** when a task is marked completed and has a linked `github_issue`, the corresponding issue is closed via `gh issue close`.
448
+ Declares downstream MCP servers and global gateway options.
773
449
 
774
- ### MCP Tools
775
-
776
- The 9 native tools are registered directly on the gateway and go through the full middleware chain:
777
-
778
- ```
779
- task_create — Create a task: title (required), description, urgency, phase, milestone, assignee, parent_id
780
- task_update — Update a task: id (required), type (started|completed|blocked|cancelled), plus any updatable fields
781
- task_list — List tasks: optional filters for status, urgency, phase
782
- task_get — Get one task by ID (T-NNN format)
783
- task_delete — Soft-delete (cancelled event) a task by ID
784
- task_sync_github — Trigger GitHub issue sync (requires gh CLI)
785
- repo_scaffold — Set GitHub repo description, topics, labels, and milestones
786
- project_sync — Sync tasks to a GitHub Project board
787
- discord_notify — Send a notification to a configured Discord channel
788
- ```
789
-
790
- ### Slash Commands
791
-
792
- | Command | Description |
793
- | ------------ | ---------------------------------------------------------------- |
794
- | `/tasks` | Render a markdown table of current tasks from tasks.jsonl |
795
- | `/plan-work` | Invoke the product-owner agent to propose tasks for a goal |
796
- | `/restart` | Session handoff command for agent continuity |
797
- | `/rea` | Invoke the REA (Reactive Execution Agent) for team orchestration |
798
-
799
- ## Config Scaffolder
800
-
801
- `reagent init` configures your repository with:
802
-
803
- - **Git hooks** — commit-msg validation, pre-commit checks, and pre-push quality gates (via Husky)
804
- - **Cursor rules** — AI behavioral constraints for Cursor IDE (no-hallucination, verify-before-act, attribution)
805
- - **Claude hooks** — 20 safety and quality hooks (see [Claude Code Hooks](#claude-code-hooks) section)
806
- - **Claude settings** — permission boundaries for Claude Code (`.claude/settings.json`)
807
- - **Policy file** — `.reagent/policy.yaml` with graduated autonomy levels
808
- - **CLAUDE.md** — project-level AI agent instructions (managed block with markers)
809
- - **Agent team** — 89 AI agent definitions installed to `.claude/agents/` (see [AGENTS.md](./AGENTS.md))
810
- - **Commands** — `/restart`, `/rea`, `/tasks`, `/plan-work` slash commands
811
- - **Gateway config** — `.reagent/gateway.yaml` template for MCP server configuration
812
- - **Task store** — `.reagent/tasks.jsonl` (empty, gitignored) for project management
813
-
814
- ### What Gets Installed
815
-
816
- | Path | Committed | Purpose |
817
- | ---------------------------- | --------------- | ------------------------------------ |
818
- | `.reagent/policy.yaml` | Yes | Autonomy levels and agent policy |
819
- | `.reagent/gateway.yaml` | Yes | MCP gateway downstream server config |
820
- | `.reagent/audit/` | No (gitignored) | Hash-chained JSONL audit logs |
821
- | `.reagent/tasks.jsonl` | No (gitignored) | Task event store |
822
- | `.reagent/review-cache.json` | No (gitignored) | Review cache for quality gates |
823
- | `.cursor/rules/` | Yes | Cursor IDE behavioral rules |
824
- | `.husky/commit-msg` | Yes | Git commit message validation |
825
- | `.husky/pre-commit` | Yes | Pre-commit checks |
826
- | `.husky/pre-push` | Yes | Pre-push quality gates |
827
- | `.claude/hooks/` | No (gitignored) | Claude Code safety hooks |
828
- | `.claude/settings.json` | No (gitignored) | Claude Code permissions |
829
- | `.claude/agents/` | No (gitignored) | Agent team definitions (89 agents) |
830
- | `.claude/commands/` | Yes | Slash commands |
831
- | `CLAUDE.md` | Yes | AI agent project instructions |
832
-
833
- ### Profiles
834
-
835
- #### Base Profiles
836
-
837
- | Profile | Use Case | Default Autonomy | Blocked Paths |
838
- | ------------------- | -------------------------- | ---------------- | --------------------------------------------------- |
839
- | `client-engagement` | Client consulting projects | L1 / max L2 | `.reagent/`, `.github/workflows/`, `.env`, `.env.*` |
840
- | `bst-internal` | BST's own repositories | L1 / max L2 | `.reagent/`, `.env` |
841
-
842
- Both profiles install the full hook suite, quality gates, Cursor rules, and Claude commands.
843
-
844
- #### Tech Stack Profiles
845
-
846
- Tech stack profiles extend the base installation with domain-specific hooks and gates. Pass them with `--profile`:
847
-
848
- | Profile | Stack | Extra Hooks |
849
- | -------- | ------------------ | ----------------------------------------------------- |
850
- | `nextjs` | Next.js App Router | `server-component-drift.sh` — RSC boundary violations |
851
- | `lit-wc` | Lit/Web Components | `shadow-dom-guard.sh`, `cem-integrity-gate.sh` |
852
- | `drupal` | Drupal CMS | `drupal-coding-standards.sh`, `hook-update-guard.sh` |
853
- | `astro` | Astro | `astro-ssr-guard.sh` — SSR/static boundary violations |
854
-
855
- Each tech profile also ships a `gates.yaml` (preflight checks for CI) and a recommended agent list.
856
-
857
- ```bash
858
- # Install with a tech stack profile
859
- npx @bookedsolid/reagent init --profile nextjs
860
- npx @bookedsolid/reagent init --profile lit-wc
861
- ```
862
-
863
- ### Idempotent
450
+ ```yaml
451
+ version: '1'
864
452
 
865
- Run `reagent init` as many times as you want. It skips files that are already up-to-date and only updates what has changed. Policy files are never overwritten if they already exist.
453
+ servers:
454
+ filesystem:
455
+ command: npx
456
+ args: ['@modelcontextprotocol/server-filesystem', '/path/to/project']
866
457
 
867
- ### Verify Installation
458
+ github:
459
+ command: npx
460
+ args: ['@modelcontextprotocol/server-github']
461
+ env:
462
+ GITHUB_TOKEN: '${GITHUB_PERSONAL_ACCESS_TOKEN}'
463
+ calls_per_minute: 120
464
+ tool_overrides:
465
+ delete_repository:
466
+ blocked: true
868
467
 
869
- ```bash
870
- reagent check
468
+ gateway:
469
+ max_result_size_kb: 512
871
470
  ```
872
471
 
873
- ## Agent Team
874
-
875
- Reagent installs 89 AI agent definitions into `.claude/agents/` covering engineering, AI platforms, and project management roles. Each agent has:
876
-
877
- - A domain-specific system prompt and tool access list
878
- - Zero-trust protocol (read before writing, verify before claiming, HALT compliance)
879
- - Persona metadata (name, inspiration) grounded in real domain pioneers
472
+ Fields per server entry:
880
473
 
881
- See **[AGENTS.md](./AGENTS.md)** for the full roster with descriptions.
474
+ | Field | Description |
475
+ | ---------------------- | --------------------------------------------------- |
476
+ | `command` | The executable to spawn |
477
+ | `args` | Arguments passed to the command |
478
+ | `env` | Environment variables (supports `${VAR}` expansion) |
479
+ | `tool_overrides` | Per-tool tier overrides or hard blocks |
480
+ | `calls_per_minute` | Rate limit for this server (0 = unlimited) |
481
+ | `max_concurrent_calls` | Concurrency limit (0 = unlimited) |
882
482
 
883
- Key agents available in every project:
483
+ ### `~/.reagent/daemon.yaml`
884
484
 
885
- | Agent | Role |
886
- | ---------------------- | ----------------------------------------------------------------------- |
887
- | `reagent-orchestrator` | Team orchestrator — routes tasks to specialists, governs AI operations |
888
- | `product-owner` | Task backlog management with built-in guardrails |
889
- | `code-reviewer` | Code review with TypeScript, accessibility, performance, security focus |
890
- | `security-engineer` | Application security, OWASP, penetration testing |
891
- | `principal-engineer` | Architecture decisions and cross-cutting concerns |
485
+ Removed. reagent no longer uses a daemon or process supervisor. Claude Code owns the
486
+ `reagent serve` process lifecycle via stdio transport in `.mcp.json`.
892
487
 
893
- ## Removing Reagent
894
-
895
- To remove reagent from a project:
488
+ ## Contributing / Development
896
489
 
897
490
  ```bash
898
- # Remove reagent-managed files
899
- rm -rf .cursor/rules/ .claude/hooks/ .claude/settings.json .claude/agents/
900
- rm -rf .claude/commands/restart.md .claude/commands/rea.md
901
- rm -rf .claude/commands/tasks.md .claude/commands/plan-work.md
902
- rm -rf .reagent/
903
-
904
- # Remove the reagent-managed block from CLAUDE.md (between the marker comments)
905
- # Then remove husky hooks if no longer needed:
906
- rm -f .husky/commit-msg .husky/pre-commit .husky/pre-push
907
- ```
908
-
909
- ## Architecture
910
-
911
- ```
912
- @bookedsolid/reagent
913
- ├── src/
914
- │ ├── cli/ # CLI entry point and commands
915
- │ │ ├── index.ts # ESM entry point, routes to commands
916
- │ │ ├── commands/
917
- │ │ │ ├── init/ # Modular init step-runner (14 steps)
918
- │ │ │ │ ├── index.ts # Step sequencer
919
- │ │ │ │ ├── types.ts # InstallResult, ProfileConfig
920
- │ │ │ │ ├── gitignore.ts # .gitignore entries
921
- │ │ │ │ ├── cursor-rules.ts # Cursor IDE rules
922
- │ │ │ │ ├── husky-hooks.ts # Git hooks (Husky)
923
- │ │ │ │ ├── claude-hooks.ts # Claude Code hooks + settings.json
924
- │ │ │ │ ├── claude-md.ts # CLAUDE.md template
925
- │ │ │ │ ├── policy.ts # policy.yaml generation
926
- │ │ │ │ ├── gateway-config.ts # gateway.yaml generation
927
- │ │ │ │ ├── agents.ts # Agent file installation
928
- │ │ │ │ ├── commands.ts # Slash command installation
929
- │ │ │ │ ├── pm.ts # Task store scaffolding
930
- │ │ │ │ ├── profiles.ts # Tech stack profile installer
931
- │ │ │ │ ├── github.ts # GitHub repo scaffolding (--github)
932
- │ │ │ │ └── discord.ts # Discord config (--discord)
933
- │ │ │ ├── catalyze/ # Stack analyzer and gap detector
934
- │ │ │ │ ├── index.ts # --plan / --audit / --dry-run modes
935
- │ │ │ │ ├── stack-analyzer.ts # Detects project type from package.json
936
- │ │ │ │ ├── gap-detector.ts # Per-stack hook/gate/agent catalog
937
- │ │ │ │ ├── report-generator.ts # Markdown + HTML report output
938
- │ │ │ │ └── types.ts # ProjectType, Gap, GapAnalysis
939
- │ │ │ ├── cache.ts # Review cache CLI (check/set/clear)
940
- │ │ │ ├── check.ts # Installation verification
941
- │ │ │ ├── freeze.ts # Kill switch (freeze/unfreeze)
942
- │ │ │ └── serve.ts # Gateway server launcher
943
- │ │ └── utils.ts # Shared CLI utilities
944
- │ ├── config/ # Configuration loaders
945
- │ │ ├── policy-loader.ts # Zod-validated policy.yaml parser
946
- │ │ ├── gateway-config.ts # Zod-validated gateway.yaml parser
947
- │ │ └── tier-map.ts # Tool tier classification
948
- │ ├── gateway/ # MCP gateway core
949
- │ │ ├── server.ts # Gateway orchestrator (startup, shutdown)
950
- │ │ ├── client-manager.ts # Downstream MCP server connections
951
- │ │ ├── tool-proxy.ts # Tool discovery, namespacing, registration
952
- │ │ ├── native-tools.ts # 9 first-party MCP tools
953
- │ │ └── middleware/ # Middleware chain
954
- │ │ ├── chain.ts # Onion-style middleware executor
955
- │ │ ├── session.ts # Session ID attachment
956
- │ │ ├── kill-switch.ts # HALT file check
957
- │ │ ├── tier.ts # Tier classification
958
- │ │ ├── policy.ts # Autonomy level enforcement
959
- │ │ ├── blocked-paths.ts # Blocked path enforcement
960
- │ │ ├── redact.ts # Secret pattern redaction
961
- │ │ └── audit.ts # Hash-chained JSONL logging
962
- │ ├── pm/ # Project management layer
963
- │ │ ├── types.ts # Zod task schema (single source of truth)
964
- │ │ ├── task-store.ts # JSONL event store with advisory locking
965
- │ │ ├── github-bridge.ts # GitHub CLI integration (issues + projects)
966
- │ │ └── discord-notifier.ts # Discord notification dispatch
967
- │ └── types/ # TypeScript type definitions
968
- ├── hooks/ # Claude Code hook scripts (20 total)
969
- │ ├── _lib/
970
- │ │ └── common.sh # Shared hook library
971
- │ ├── settings-protection.sh
972
- │ ├── blocked-paths-enforcer.sh
973
- │ ├── dangerous-bash-interceptor.sh
974
- │ ├── secret-scanner.sh
975
- │ ├── env-file-protection.sh
976
- │ ├── attribution-advisory.sh
977
- │ ├── symlink-guard.sh
978
- │ ├── network-exfil-guard.sh
979
- │ ├── import-guard.sh
980
- │ ├── git-config-guard.sh
981
- │ ├── ci-config-protection.sh
982
- │ ├── commit-review-gate.sh
983
- │ ├── push-review-gate.sh
984
- │ ├── architecture-review-gate.sh
985
- │ ├── dependency-audit-gate.sh
986
- │ ├── task-link-gate.sh
987
- │ ├── output-validation.sh
988
- │ ├── file-size-guard.sh
989
- │ └── rate-limit-guard.sh
990
- ├── profiles/ # Init profiles
991
- │ ├── client-engagement.json # Base profile
992
- │ ├── bst-internal.json # Base profile
993
- │ ├── nextjs/ # Tech stack profile
994
- │ │ ├── hooks/server-component-drift.sh
995
- │ │ ├── gates.yaml
996
- │ │ └── agents.txt
997
- │ ├── lit-wc/ # Tech stack profile
998
- │ │ ├── hooks/{shadow-dom-guard,cem-integrity-gate}.sh
999
- │ │ ├── gates.yaml
1000
- │ │ └── agents.txt
1001
- │ ├── drupal/ # Tech stack profile
1002
- │ │ ├── hooks/{drupal-coding-standards,hook-update-guard}.sh
1003
- │ │ ├── gates.yaml
1004
- │ │ └── agents.txt
1005
- │ └── astro/ # Tech stack profile
1006
- │ ├── hooks/astro-ssr-guard.sh
1007
- │ ├── gates.yaml
1008
- │ └── agents.txt
1009
- ├── agents/ # 89 agent definitions (see AGENTS.md)
1010
- │ ├── product-owner.md
1011
- │ ├── reagent-orchestrator.md
1012
- │ ├── engineering/ # 64 engineering specialist agents
1013
- │ └── ai-platforms/ # 25 AI platform specialist agents
1014
- ├── templates/ # Template files for scaffolding
1015
- ├── husky/ # Husky git hook scripts
1016
- ├── cursor/ # Cursor IDE rules
1017
- └── commands/ # Claude slash commands
1018
- ├── restart.md
1019
- ├── rea.md
1020
- ├── tasks.md
1021
- └── plan-work.md
1022
- ```
1023
-
1024
- ## Package Exports
1025
-
1026
- ```json
1027
- {
1028
- ".": "types/index.js",
1029
- "./config": "config/policy-loader.js",
1030
- "./middleware": "gateway/middleware/chain.js"
1031
- }
491
+ pnpm install
492
+ pnpm build # compile TypeScript to dist/
493
+ pnpm tsc --noEmit # type-check without emitting
494
+ pnpm test # run all tests with vitest
495
+ pnpm preflight # full quality gate (build + typecheck + test + lint + format)
1032
496
  ```
1033
497
 
1034
- ## Requirements
1035
-
1036
- - Node.js >= 22
1037
- - Git repository (for hooks and init)
1038
- - `jq` (for hook scripts that parse JSON)
1039
- - `gh` CLI (optional, for GitHub issue sync and repo scaffolding)
1040
-
1041
- ## Dependencies
1042
-
1043
- 3 runtime dependencies:
1044
-
1045
- - `@modelcontextprotocol/sdk` — MCP client/server protocol
1046
- - `yaml` — YAML parsing for policy and gateway config
1047
- - `zod` — Schema validation for all configuration files
1048
-
1049
- ## Testing
498
+ Changesets workflow:
1050
499
 
1051
500
  ```bash
1052
- pnpm test
501
+ pnpm changeset # create a new changeset
502
+ pnpm changeset:version # bump versions and update CHANGELOG
503
+ pnpm changeset:publish # publish to npm
1053
504
  ```
1054
505
 
1055
- 462 tests across 41 test files covering:
1056
-
1057
- - CLI commands (init step-runner, catalyze, cache, check, freeze, profiles)
1058
- - Middleware chain (session, kill-switch, tier, policy, blocked-paths, redact, audit)
1059
- - Tier classification (static map, convention-based, overrides)
1060
- - Policy enforcement (autonomy levels, blocked tools, max clamping)
1061
- - Secret redaction (AWS, GitHub, PEM, Discord, generic patterns)
1062
- - Hook scripts (all 20 hooks, including v0.6.0 additions)
1063
- - Project management (task store CRUD, event materialization, advisory locking, Discord notifier)
1064
- - End-to-end gateway smoke tests (native + proxied tools)
1065
-
1066
- Quality gates (run via `pnpm preflight`):
1067
-
1068
- 1. Secret scan (gitleaks)
1069
- 2. Format check (prettier)
1070
- 3. Lint (eslint)
1071
- 4. Type check (tsc --noEmit)
1072
- 5. Tests (vitest)
1073
- 6. Pack dry-run (npm pack)
1074
-
1075
- ## Scope
1076
-
1077
- Reagent is a **local CLI tool** and **MCP gateway server**. It configures files in your repository and proxies MCP tool calls on your machine. It does not collect data, phone home, or operate as a hosted service.
1078
-
1079
- ## License
506
+ There is no Rust code in this project. The `daemon/` directory has been removed. The
507
+ project is pure TypeScript targeting Node.js 22+, compiled to ESM.
1080
508
 
1081
- MIT
509
+ The test suite lives in `src/__tests__/` and covers the middleware chain, all hooks,
510
+ the CLI init flow, config loaders, the task store, GitHub and Discord integrations,
511
+ and an end-to-end smoke test that spawns a real `reagent serve` process.