brainclaw 1.7.5 → 1.9.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.
- package/README.md +28 -11
- package/dist/brainclaw-vscode.vsix +0 -0
- package/dist/cli.js +139 -13
- package/dist/commands/add-step.js +1 -1
- package/dist/commands/bootstrap.js +2 -26
- package/dist/commands/check-security-mcp.js +50 -33
- package/dist/commands/check-security.js +86 -43
- package/dist/commands/claim.js +22 -21
- package/dist/commands/confirm.js +26 -0
- package/dist/commands/context-diff.js +1 -1
- package/dist/commands/dispatch-watch.js +142 -0
- package/dist/commands/doctor.js +113 -2
- package/dist/commands/estimation-report.js +115 -16
- package/dist/commands/harvest.js +502 -16
- package/dist/commands/init.js +123 -21
- package/dist/commands/loops-handlers.js +4 -0
- package/dist/commands/mcp-read-handlers.js +198 -29
- package/dist/commands/mcp.js +615 -92
- package/dist/commands/memory.js +21 -17
- package/dist/commands/migrate.js +81 -17
- package/dist/commands/prune.js +78 -4
- package/dist/commands/reflect.js +26 -20
- package/dist/commands/register-agent.js +57 -1
- package/dist/commands/repair.js +20 -0
- package/dist/commands/session-end.js +15 -6
- package/dist/commands/session-start.js +18 -1
- package/dist/commands/setup-security.js +39 -18
- package/dist/commands/setup.js +26 -27
- package/dist/commands/stale.js +16 -2
- package/dist/commands/uninstall.js +126 -34
- package/dist/commands/update-step.js +6 -0
- package/dist/commands/worktree.js +60 -0
- package/dist/core/actions.js +12 -3
- package/dist/core/agent-capability.js +11 -13
- package/dist/core/agent-files.js +844 -547
- package/dist/core/agent-integrations.js +0 -3
- package/dist/core/agent-inventory.js +67 -0
- package/dist/core/agent-registry.js +163 -29
- package/dist/core/agentrun-reconciler.js +33 -2
- package/dist/core/agentruns.js +7 -1
- package/dist/core/ai-agent-detection.js +31 -44
- package/dist/core/archival.js +15 -9
- package/dist/core/assignment-reconciler.js +56 -0
- package/dist/core/assignment-sweeper.js +127 -4
- package/dist/core/assignments.js +69 -11
- package/dist/core/bootstrap.js +233 -67
- package/dist/core/brainclaw-version.js +22 -0
- package/dist/core/candidates.js +21 -1
- package/dist/core/claims.js +313 -150
- package/dist/core/config.js +6 -1
- package/dist/core/context-diff.js +148 -20
- package/dist/core/context.js +129 -8
- package/dist/core/coordination.js +22 -3
- package/dist/core/dispatch-status.js +109 -5
- package/dist/core/dispatcher.js +65 -11
- package/dist/core/entity-operations.js +45 -24
- package/dist/core/entity-registry.js +31 -5
- package/dist/core/event-log.js +138 -21
- package/dist/core/events/checkpoint.js +258 -0
- package/dist/core/events/genesis.js +220 -0
- package/dist/core/events/journal.js +507 -0
- package/dist/core/events/materialize.js +126 -0
- package/dist/core/events/registry-post-image.js +110 -0
- package/dist/core/events/verify.js +109 -0
- package/dist/core/execution-adapters.js +23 -0
- package/dist/core/execution.js +25 -0
- package/dist/core/facade-schema.js +48 -0
- package/dist/core/gc-semantic.js +130 -5
- package/dist/core/handoff-snapshot.js +68 -0
- package/dist/core/ids.js +19 -8
- package/dist/core/instruction-templates.js +34 -115
- package/dist/core/io.js +39 -3
- package/dist/core/json-store.js +10 -1
- package/dist/core/lock.js +153 -28
- package/dist/core/loops/bootstrap-acquire.js +25 -1
- package/dist/core/loops/facade-schema.js +2 -0
- package/dist/core/loops/hooks/survey-signals-baseline.js +36 -0
- package/dist/core/loops/index.js +1 -0
- package/dist/core/loops/presets/bootstrap.js +7 -0
- package/dist/core/loops/store.js +17 -0
- package/dist/core/loops/verbs.js +24 -1
- package/dist/core/markdown.js +8 -76
- package/dist/core/mcp-command-resolution.js +245 -0
- package/dist/core/memory-compactor.js +5 -3
- package/dist/core/memory-lifecycle.js +282 -0
- package/dist/core/merge-risk.js +150 -0
- package/dist/core/messaging.js +8 -1
- package/dist/core/migration.js +11 -1
- package/dist/core/observer-mode.js +26 -0
- package/dist/core/operations/memory-mutation.js +90 -65
- package/dist/core/operations/plan.js +27 -1
- package/dist/core/protocol-skills.js +210 -0
- package/dist/core/reflection-safety.js +6 -7
- package/dist/core/reputation.js +84 -2
- package/dist/core/runtime-signals.js +71 -9
- package/dist/core/runtime.js +84 -1
- package/dist/core/schema.js +125 -0
- package/dist/core/security-detectors.js +125 -0
- package/dist/core/security-extract.js +189 -0
- package/dist/core/security-guard.js +107 -29
- package/dist/core/security-packages.js +121 -0
- package/dist/core/security-scoring.js +76 -9
- package/dist/core/security.js +34 -2
- package/dist/core/sequence.js +11 -2
- package/dist/core/setup-flow.js +141 -13
- package/dist/core/spawn-check.js +110 -4
- package/dist/core/staleness.js +109 -1
- package/dist/core/state.js +250 -54
- package/dist/core/store-resolution.js +19 -5
- package/dist/core/worktree.js +169 -7
- package/dist/facts.js +8 -8
- package/dist/facts.json +7 -7
- package/docs/PROTOCOL.md +223 -0
- package/docs/cli.md +11 -10
- package/docs/concepts/coordinator-runbook.md +129 -0
- package/docs/concepts/dispatch-lifecycle.md +17 -0
- package/docs/concepts/event-log-store-critique-A.md +333 -0
- package/docs/concepts/event-log-store-critique-B.md +353 -0
- package/docs/concepts/event-log-store-phase0-measurements.md +58 -0
- package/docs/concepts/event-log-store-proposal-A.md +365 -0
- package/docs/concepts/event-log-store-proposal-B.md +404 -0
- package/docs/concepts/event-log-store.md +928 -0
- package/docs/concepts/identity-model-proposal.md +371 -0
- package/docs/concepts/memory.md +5 -4
- package/docs/concepts/observer-protocol.md +361 -0
- package/docs/concepts/parallel-merge-protocol.md +71 -0
- package/docs/concepts/plans-and-claims.md +43 -0
- package/docs/concepts/skills.md +78 -0
- package/docs/concepts/workspace-bootstrapping.md +61 -0
- package/docs/integrations/agents.md +4 -4
- package/docs/integrations/cline.md +10 -11
- package/docs/integrations/codex.md +2 -2
- package/docs/integrations/continue.md +5 -5
- package/docs/integrations/copilot.md +14 -12
- package/docs/integrations/openclaw.md +7 -6
- package/docs/integrations/overview.md +7 -7
- package/docs/integrations/roo.md +3 -3
- package/docs/integrations/windsurf.md +6 -6
- package/docs/mcp-schema-changelog.md +51 -20
- package/docs/quickstart.md +48 -47
- package/docs/security.md +174 -15
- package/docs/storage.md +4 -2
- package/package.json +8 -6
package/docs/security.md
CHANGED
|
@@ -4,8 +4,10 @@ brainclaw is designed to be safe by default.
|
|
|
4
4
|
|
|
5
5
|
## Security model
|
|
6
6
|
|
|
7
|
-
### No network access
|
|
8
|
-
The CLI does not need to call external services to function.
|
|
7
|
+
### No network access by default
|
|
8
|
+
The CLI does not need to call external services to function. The optional
|
|
9
|
+
supply-chain gate (see below) is the one feature that talks to a remote
|
|
10
|
+
service, and it is off until explicitly enabled.
|
|
9
11
|
|
|
10
12
|
### No telemetry
|
|
11
13
|
brainclaw does not collect or send usage data.
|
|
@@ -19,35 +21,192 @@ That makes review easier, but it also means users must be careful about what the
|
|
|
19
21
|
|
|
20
22
|
## Built-in safety behaviors
|
|
21
23
|
|
|
22
|
-
|
|
24
|
+
### Content scanning (scanText)
|
|
23
25
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
- `token`
|
|
27
|
-
- `password`
|
|
26
|
+
Whenever content is added to `.brainclaw/` brainclaw scans the text in three
|
|
27
|
+
layers:
|
|
28
28
|
|
|
29
|
-
|
|
29
|
+
1. **User-configured regex patterns** from `redaction.patterns`. The
|
|
30
|
+
defaults catch words like `api_key`, `secret`, `token`, `password`.
|
|
31
|
+
2. **Structural detectors** for well-known token shapes — GitHub PATs
|
|
32
|
+
(`ghp_`, `gho_`, `github_pat_…`), AWS access keys (`AKIA…`/`ASIA…`),
|
|
33
|
+
Google API keys (`AIza…`), Slack tokens and webhooks, Stripe
|
|
34
|
+
`sk_live_/sk_test_` keys, JWTs, PEM-encoded private keys, and URLs
|
|
35
|
+
with embedded `user:password@host` credentials.
|
|
36
|
+
3. **Entropy detector** that flags high-Shannon-entropy substrings near
|
|
37
|
+
a secret keyword (api_key/token/secret/password/auth/...). This
|
|
38
|
+
catches custom-shaped keys the structural list does not enumerate.
|
|
30
39
|
|
|
31
|
-
|
|
32
|
-
|
|
40
|
+
In `security.mode: warn` matches surface as warnings; in
|
|
41
|
+
`security.strict_redaction: true` (or `security.mode: strict`) the same
|
|
42
|
+
matches block the write.
|
|
33
43
|
|
|
34
|
-
|
|
44
|
+
### Sensitive paths
|
|
45
|
+
|
|
46
|
+
When `security.block_sensitive_paths: true` (default), content that
|
|
47
|
+
references paths like `.env`, `secrets/`, `.git/`, or `node_modules/`
|
|
48
|
+
emits a warning.
|
|
49
|
+
|
|
50
|
+
### Configuration
|
|
35
51
|
|
|
36
52
|
```yaml
|
|
37
53
|
security:
|
|
38
|
-
mode: warn # 'warn' or 'strict'
|
|
54
|
+
mode: warn # 'warn' or 'strict' — affects redaction scanning
|
|
39
55
|
strict_redaction: false # if true, blocks entries with sensitive content
|
|
40
56
|
block_sensitive_paths: true
|
|
57
|
+
token_detection:
|
|
58
|
+
enabled: true # turn off all structural + entropy detection
|
|
59
|
+
entropy:
|
|
60
|
+
enabled: true
|
|
61
|
+
min_length: 32 # minimum substring length to consider
|
|
62
|
+
min_entropy: 4.0 # minimum Shannon entropy (bits/char)
|
|
63
|
+
detectors: # per-detector override map; explicit false disables a detector
|
|
64
|
+
aws_access_key: true
|
|
65
|
+
jwt: true
|
|
66
|
+
|
|
67
|
+
redaction:
|
|
68
|
+
enabled: true
|
|
69
|
+
patterns:
|
|
70
|
+
- '(?i)api[_-]?key'
|
|
71
|
+
- '(?i)secret'
|
|
72
|
+
- '(?i)token'
|
|
73
|
+
- '(?i)password'
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
## Supply-chain pre-install gate
|
|
77
|
+
|
|
78
|
+
`brainclaw setup-security` enables a preinstall gate that intercepts
|
|
79
|
+
`npm`/`pnpm`/`yarn`/`pip`/`pip3` install commands and asks Socket.dev's
|
|
80
|
+
scoring service whether the requested packages are risky.
|
|
81
|
+
|
|
82
|
+
```
|
|
83
|
+
brainclaw setup-security --mode advisory # default — warn-only
|
|
84
|
+
brainclaw setup-security --mode enforced # block risky installs
|
|
41
85
|
```
|
|
42
86
|
|
|
87
|
+
### Advisory vs enforced
|
|
88
|
+
|
|
89
|
+
The mode determines what happens when the gate decides a package is
|
|
90
|
+
risky:
|
|
91
|
+
|
|
92
|
+
- **advisory** — verdicts are surfaced (printed warning, security trap
|
|
93
|
+
created) but the install is *not* aborted.
|
|
94
|
+
- **enforced** — a `block` verdict aborts the install with a non-zero
|
|
95
|
+
exit code.
|
|
96
|
+
|
|
97
|
+
The mode is read from `security.preinstall.mode` and can be overridden
|
|
98
|
+
per call with `brainclaw check-security --mode <advisory|enforced>`.
|
|
99
|
+
|
|
100
|
+
### Exit codes
|
|
101
|
+
|
|
102
|
+
`brainclaw check-security` emits exit codes that already encode the mode
|
|
103
|
+
decision, so wrapper scripts are mode-agnostic:
|
|
104
|
+
|
|
105
|
+
| Exit | Meaning |
|
|
106
|
+
|------|------------------------------------------------------------|
|
|
107
|
+
| 0 | pass — no risky packages |
|
|
108
|
+
| 1 | warn — advisory-mode block, or warn-threshold verdict |
|
|
109
|
+
| 2 | block — enforced-mode block; the wrapper aborts the install|
|
|
110
|
+
|
|
111
|
+
The wrapper scripts (`<.brainclaw/security/bin>/npm`, `pnpm`, `yarn`,
|
|
112
|
+
`pip`, `pip3` and their `.ps1` counterparts) call the CLI and react
|
|
113
|
+
purely to the exit code, so flipping advisory↔enforced is a config
|
|
114
|
+
change — no regeneration required.
|
|
115
|
+
|
|
116
|
+
### Composite scoring
|
|
117
|
+
|
|
118
|
+
Each package gets five sub-scores from Socket (supply-chain,
|
|
119
|
+
vulnerability, quality, maintenance, license) on a 0–100 scale. The
|
|
120
|
+
gate combines them into a single composite using configurable weights:
|
|
121
|
+
|
|
122
|
+
```yaml
|
|
123
|
+
security:
|
|
124
|
+
preinstall:
|
|
125
|
+
weights:
|
|
126
|
+
supply_chain: 0.35
|
|
127
|
+
vulnerability: 0.30
|
|
128
|
+
quality: 0.15
|
|
129
|
+
maintenance: 0.15
|
|
130
|
+
license: 0.05
|
|
131
|
+
thresholds:
|
|
132
|
+
composite_pass: 70 # composite >= 70 → pass
|
|
133
|
+
composite_warn: 50 # composite >= 50 but < 70 → warn; below → block
|
|
134
|
+
supply_chain_block: 30 # hard block when supply_chain < 30
|
|
135
|
+
vulnerability_block: 20 # hard block when vulnerability < 20
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
Weights are normalized to sum to 1.0 automatically — a config like
|
|
139
|
+
`{ supply_chain: 1, vulnerability: 1 }` is rescaled rather than
|
|
140
|
+
producing composites above 100. Thresholds are clamped to `[0,100]`
|
|
141
|
+
and `composite_warn` is capped at `composite_pass` so the verdict
|
|
142
|
+
function stays monotonic.
|
|
143
|
+
|
|
144
|
+
### Allowlist / denylist
|
|
145
|
+
|
|
146
|
+
```yaml
|
|
147
|
+
security:
|
|
148
|
+
preinstall:
|
|
149
|
+
allowlist:
|
|
150
|
+
- npm:internal-pkg # ecosystem-scoped
|
|
151
|
+
- npm:axios@1.14.0 # exact version pin
|
|
152
|
+
- lodash # bare name — any ecosystem, any version
|
|
153
|
+
denylist:
|
|
154
|
+
- npm:axios@1.14.1 # known-compromised version
|
|
155
|
+
- pypi:bad-pkg
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
Matching is exact on each component. Bare names match by package name
|
|
159
|
+
only; an `ecosystem:` prefix scopes the match to that ecosystem;
|
|
160
|
+
appending `@version` (or `==version` for pip-style) requires an exact
|
|
161
|
+
version. The wildcard `@*` matches any version (useful for explicit
|
|
162
|
+
"any version" entries).
|
|
163
|
+
|
|
164
|
+
This is a hard tightening from the MVP: previously `denylist: ['lodash']`
|
|
165
|
+
matched any package whose purl contained the substring `lodash`, so
|
|
166
|
+
`react-lodash` was silently blocked. The new matcher requires exact
|
|
167
|
+
package-name equality.
|
|
168
|
+
|
|
169
|
+
### Package extraction sources
|
|
170
|
+
|
|
171
|
+
`check-security` can pull the list of packages from three places, which
|
|
172
|
+
may be combined:
|
|
173
|
+
|
|
174
|
+
- `--packages axios,express@1.2.3` — comma-separated specs
|
|
175
|
+
- `--requirements requirements.txt` — pip-style requirements file;
|
|
176
|
+
recursive `-r` includes, env markers, and extras are handled
|
|
177
|
+
- `--lockfile package-lock.json` — npm package-lock (v1, v2, v3);
|
|
178
|
+
scans top-level direct deps and devDeps
|
|
179
|
+
|
|
180
|
+
The wrappers auto-translate `npm install -r foo.txt` → `--requirements`,
|
|
181
|
+
skip filesystem paths and URL specs that aren't registry packages
|
|
182
|
+
(`./local-pkg`, `git+https://…`, `*.tgz`, `*.whl`), and handle the
|
|
183
|
+
common npm/pip flag conventions.
|
|
184
|
+
|
|
185
|
+
### Offline / fetch-error fallback
|
|
186
|
+
|
|
187
|
+
When the Socket call fails (network down, service unreachable), the
|
|
188
|
+
gate uses `security.preinstall.fallback_on_error`:
|
|
189
|
+
|
|
190
|
+
- `block` — fail closed regardless of mode
|
|
191
|
+
- `warn` — surface a warning, continue with whatever cached scores
|
|
192
|
+
exist; if no cache exists the gate exits with code 1
|
|
193
|
+
- `pass` — silent fall-through (the install proceeds)
|
|
194
|
+
|
|
195
|
+
Cached scores have a TTL of `cache_ttl_hours` (default 24) and live
|
|
196
|
+
in `.brainclaw/security/cache.json`.
|
|
197
|
+
|
|
43
198
|
## Recommended stance
|
|
44
199
|
|
|
45
|
-
- do not store secrets
|
|
200
|
+
- do not store secrets — even with detection, the safer move is to never
|
|
201
|
+
write them
|
|
46
202
|
- review what gets committed
|
|
47
203
|
- keep machine-local observations machine-local when appropriate
|
|
48
204
|
- use stricter redaction settings in sensitive environments
|
|
205
|
+
- run `setup-security --mode advisory` first; flip to `enforced` once
|
|
206
|
+
the team has gotten used to the verdicts
|
|
49
207
|
|
|
50
208
|
## Important nuance
|
|
51
209
|
|
|
52
|
-
brainclaw reduces hidden behavior, but it does not remove the need for
|
|
53
|
-
It warns; the team still decides what belongs
|
|
210
|
+
brainclaw reduces hidden behavior, but it does not remove the need for
|
|
211
|
+
operational discipline. It warns; the team still decides what belongs
|
|
212
|
+
in shared memory.
|
package/docs/storage.md
CHANGED
|
@@ -7,7 +7,7 @@ brainclaw is local-first and workspace-centric.
|
|
|
7
7
|
```text
|
|
8
8
|
.brainclaw/
|
|
9
9
|
config.yaml ← Project configuration
|
|
10
|
-
project.md ←
|
|
10
|
+
project.md ← Legacy derived readable view (best-effort, regenerable)
|
|
11
11
|
events.jsonl ← Append-only event log (agent notifications)
|
|
12
12
|
audit.log ← Append-only audit trail (before/after snapshots)
|
|
13
13
|
memory/
|
|
@@ -42,7 +42,9 @@ Benefits:
|
|
|
42
42
|
- isolated corruption (one bad file does not affect others)
|
|
43
43
|
|
|
44
44
|
### Derived views are best-effort
|
|
45
|
-
|
|
45
|
+
`.brainclaw/project.md` is a **legacy derived view** regenerated from canonical state via `rebuildProjectMd()`. It is not a write target and no longer carries live claims, plans, handoffs, or runtime state — use `brainclaw agent-board`, `brainclaw context`, or MCP board/context tools for that operational data.
|
|
46
|
+
|
|
47
|
+
Root `PROJECT.md` is different: it is the durable project vision and should contain stable product, architecture, and contribution guidance that does not expire every session.
|
|
46
48
|
|
|
47
49
|
Failures to regenerate `project.md` are logged but never block mutations. If it gets stale, `brainclaw doctor` detects the drift.
|
|
48
50
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "brainclaw",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.9.0",
|
|
4
4
|
"description": "Shared project memory for humans and coding agents.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
@@ -26,23 +26,25 @@
|
|
|
26
26
|
"clean:build": "node scripts/clean-build.mjs dist dist-test",
|
|
27
27
|
"clean:dist": "node scripts/clean-build.mjs dist",
|
|
28
28
|
"clean:dist-test": "node scripts/clean-build.mjs dist-test",
|
|
29
|
-
"build": "npm run
|
|
30
|
-
"build:cli": "npm run clean:dist && tsc && node scripts/copy-default-profiles.mjs",
|
|
31
|
-
"
|
|
29
|
+
"build": "npm run build:cli && node scripts/build-vsix.mjs --optional",
|
|
30
|
+
"build:cli": "npm run clean:dist && tsc && node scripts/copy-default-profiles.mjs",
|
|
31
|
+
"build:release": "npm run build:cli && node scripts/emit-site-facts.mjs && node scripts/build-vsix.mjs",
|
|
32
|
+
"emit:facts": "npm run build:cli && node scripts/emit-site-facts.mjs",
|
|
32
33
|
"dev": "npm run clean:dist && tsc && node scripts/copy-default-profiles.mjs && node dist/cli.js",
|
|
33
34
|
"dev:mcp": "tsc && node scripts/copy-default-profiles.mjs",
|
|
34
35
|
"build:mcp-schemas": "npm run clean:dist && tsc && node scripts/build-mcp-schemas.mjs",
|
|
35
36
|
"dev:link": "npm link && echo 'Symlink created: global brainclaw → local repo. MCP agents now use dist/ directly.'",
|
|
36
|
-
"build:test": "npm run build && npm run clean:dist-test && tsc -p tsconfig.test.json",
|
|
37
|
+
"build:test": "npm run build:cli && npm run clean:dist-test && tsc -p tsconfig.test.json",
|
|
37
38
|
"pack:check": "node scripts/check-pack.mjs",
|
|
38
39
|
"test": "npm run build:test && node scripts/run-tests.mjs default",
|
|
39
40
|
"test:unit": "npm run build:test && node scripts/run-tests.mjs unit",
|
|
40
41
|
"test:smoke": "npm run build:test && node scripts/run-tests.mjs smoke",
|
|
41
42
|
"test:e2e": "npm run build:test && node scripts/run-tests.mjs e2e",
|
|
42
43
|
"test:all": "npm run build:test && node scripts/run-tests.mjs all",
|
|
44
|
+
"test:cross": "npm run build:test && node scripts/test-cross.mjs default",
|
|
43
45
|
"test:coverage": "npm run build:test && c8 --all --src dist-test/src --reporter=text-summary --reporter=lcov --exclude=dist-test/tests/** --exclude=dist-test/scripts/** node scripts/run-tests.mjs default",
|
|
44
46
|
"test:coverage:check": "npm run build:test && c8 --all --check-coverage --lines 55 --functions 60 --branches 65 --statements 55 --src dist-test/src --reporter=text-summary --exclude=dist-test/tests/** --exclude=dist-test/scripts/** node scripts/run-tests.mjs default",
|
|
45
|
-
"prepublishOnly": "npm run build &&
|
|
47
|
+
"prepublishOnly": "npm run build:release && npm run pack:check"
|
|
46
48
|
},
|
|
47
49
|
"keywords": [
|
|
48
50
|
"cli",
|