@letterblack/lbe-exec 1.2.3 → 1.2.5

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 (2) hide show
  1. package/README.md +137 -58
  2. package/package.json +1 -1
package/README.md CHANGED
@@ -2,9 +2,12 @@
2
2
 
3
3
  **Local-first execution governance for AI agents.**
4
4
 
5
+ > Use `@letterblack/lbe-exec` if you want LBE to control agent actions in a workspace.
6
+ > Use `@letterblack/lbe-sdk` if you only need validation decisions inside your own tool.
7
+
5
8
  Every action any agent proposes — file write, shell command, anything — passes
6
- through a local validation gate before it can execute. One SDK, any agent,
7
- zero cloud dependency.
9
+ through a local validation gate before it can execute. One package, any agent,
10
+ zero cloud dependency, no daemon required.
8
11
 
9
12
  ---
10
13
 
@@ -26,22 +29,29 @@ dependency, no daemon required.
26
29
 
27
30
  ![LBE gate sequence — Request flows through Policy, Identity, and Scope gates before reaching Action. A rejected request is routed to denial before it reaches execution.](assets/lbe-gates.png)
28
31
 
29
- Every request the agent produces enters a gate sequence:
30
-
31
- **Policy** — does the current project policy allow this action? Deny rules
32
- always win. If any deny rule matches, the gate closes before any other check
33
- runs.
32
+ Every request the agent produces enters a 7-gate pipeline. A failure at any
33
+ gate returns a structured denial — the remaining gates are not evaluated.
34
34
 
35
- **Identity** — is the request signed by a trusted, active key? The executor
36
- signs every request locally with an Ed25519 key it holds in memory. Expired
37
- keys, tampered signatures, and replayed nonces are all rejected.
38
-
39
- **Scope** — is the target inside the allowed workspace? Paths outside the
40
- project root, symlink escapes, and commands outside the explicit allowlist
41
- are blocked regardless of policy.
35
+ ```
36
+ [1] Schema required fields and structural validity
37
+
38
+ [2] Timestamp permitted clock-skew window (±10 minutes)
39
+
40
+ [3] Key lifecycle trusted key, active, not expired
41
+
42
+ [4] Signature Ed25519 request authenticity (signed locally, no network)
43
+
44
+ [5] Rate limit per-requester sliding-window limit
45
+
46
+ [6] Nonce single-use replay protection
47
+
48
+ [7] Policy configured authorization (deny-wins)
49
+
50
+ allow / deny / error — structured result returned to host
51
+ ```
42
52
 
43
- Only a request that clears all three gates reaches **Action** — the point
44
- where something is actually written to disk or a command actually runs.
53
+ The executor signs every request with a host-held key before validation.
54
+ No key material leaves the process.
45
55
 
46
56
  ---
47
57
 
@@ -51,20 +61,17 @@ where something is actually written to disk or a command actually runs.
51
61
 
52
62
  When a request clears every gate:
53
63
 
54
- 1. The agent produces an action proposalintent, target, content.
55
- 2. The executor signs it locally with a host-held Ed25519 key. No key material
56
- leaves the process.
57
- 3. The project policy is evaluated. The action is approved.
64
+ 1. The agent calls a convenience method`lbe.writeFile()`, `lbe.runShell()`, etc.
65
+ 2. The executor constructs and signs the request locally with a host-held Ed25519 key.
66
+ 3. All seven gates pass. The project policy approves the action.
58
67
  4. The write or command executes inside the configured project root.
59
- 5. The audit chain is extended. Every approved action appends a hash-linked
60
- entry to `lbe.audit.jsonl` permanently verifiable, impossible to silently
61
- remove.
62
- 6. A structured result is returned: whether it succeeded, which rules matched,
63
- and the audit entry identifier.
68
+ 5. The audit chain is extended every approved action appends a hash-linked
69
+ entry to `.lbe/audit.jsonl`, permanently verifiable, impossible to silently remove.
70
+ 6. A structured result returns: whether it succeeded, which rules matched, and
71
+ the audit entry identifier.
64
72
 
65
- The application stays in control. The executor does not decide what to do with
66
- the result — it decides whether the action was permitted and hands the answer
67
- back.
73
+ The application stays in control. The executor decides whether the action was
74
+ permitted and hands the answer back.
68
75
 
69
76
  ---
70
77
 
@@ -100,32 +107,27 @@ is an agent that can grant itself permission.
100
107
 
101
108
  ---
102
109
 
103
- ## Observer mode — start here
104
-
105
- Not ready to block? Start in observer mode. Every request is fully validated
106
- and logged exactly as it would be in enforcement — but nothing is blocked.
107
-
108
- Watch what the agent is doing before you decide what to deny. Your rules take
109
- effect the moment you switch to enforcement.
110
-
111
- ```bash
112
- npx lbe-exec init # create lbe.policy.json — starts in observer mode
113
- npx lbe-exec status # see mode, rule count, audit entry count
114
- npx lbe-exec enforce # switch to blocking
115
- ```
116
-
117
- ---
118
-
119
110
  ## What this covers
120
111
 
121
112
  | Threat | Gate |
122
113
  |---|---|
123
- | Agent writes outside the project root | Scope — path check |
114
+ | Agent writes outside the project root | Scope — sandbox path check |
124
115
  | Replayed or stale request | Identity — nonce and timestamp |
125
116
  | Tampered or expired key | Identity — key lifecycle |
126
117
  | Excessive requests | Identity — rate limit |
127
118
  | Action not permitted by project policy | Policy — deny-wins evaluation |
128
119
  | Unauthorized shell command | Scope — explicit command allowlist |
120
+ | Injected payload (eval, exec, __proto__) | Content scan before pipeline |
121
+
122
+ ---
123
+
124
+ ## Observer mode — start here
125
+
126
+ Not ready to block? Start in observer mode. Every request is fully validated
127
+ and logged exactly as it would be in enforcement — but nothing is blocked.
128
+
129
+ Watch what the agent is doing before you decide what to deny. Your rules take
130
+ effect the moment you switch to enforcement.
129
131
 
130
132
  ---
131
133
 
@@ -136,13 +138,15 @@ npm install @letterblack/lbe-exec
136
138
  npx lbe-exec init
137
139
  ```
138
140
 
139
- `npx lbe-exec init` scans the project, writes `lbe.policy.json` in observer mode,
140
- generates `CLAUDE.md` and `.github/copilot-instructions.md` so every AI agent
141
- automatically discovers and follows governance without the user explaining it,
142
- and creates `.lbe/AGENT_CONTRACT.md` as a machine-readable contract.
141
+ `npx lbe-exec init` scans the project, writes `lbe.policy.json` in observer
142
+ mode, generates `CLAUDE.md` and `.github/copilot-instructions.md` so every AI
143
+ agent automatically discovers and follows governance, and creates
144
+ `.lbe/AGENT_CONTRACT.md` as a machine-readable contract.
143
145
 
144
146
  Requires Node.js ≥ 20.9.0.
145
147
 
148
+ ---
149
+
146
150
  ## Use in agent code
147
151
 
148
152
  ```js
@@ -150,27 +154,102 @@ import { createLocalExecutor } from '@letterblack/lbe-exec';
150
154
 
151
155
  const lbe = createLocalExecutor({ rootDir: process.cwd() });
152
156
 
157
+ // Every call routes through the full 7-gate pipeline
153
158
  await lbe.writeFile('output/report.md', content);
154
159
  await lbe.readFile('src/config.json');
155
160
  await lbe.patchFile('src/index.js', patch);
156
161
  await lbe.deleteFile('tmp/scratch.txt');
157
162
  await lbe.runShell('node', ['scripts/build.js']);
158
163
 
164
+ // Result shape
159
165
  const result = await lbe.writeFile('output/result.md', data);
160
- // { ok: true, decision: 'allow', executed: true }
161
- // { ok: false, decision: 'deny', error: { message: '...' } }
166
+ // { ok: true, decision: 'allow', executed: true, auditId: '...' }
167
+ // { ok: false, decision: 'deny', executed: false, error: { code, message } }
168
+ ```
169
+
170
+ No knowledge of the pipeline, request format, or policy internals required.
171
+ All signing, validation, and auditing happens automatically.
172
+
173
+ ### Options
174
+
175
+ ```js
176
+ const lbe = createLocalExecutor({
177
+ rootDir: process.cwd(), // sandbox root — no writes escape this path
178
+ mode: 'observe', // 'observe' (log only) or 'enforce' (block)
179
+ shell: {
180
+ allowCommands: ['node', 'npm'], // only these commands may run
181
+ denyCommands: ['rm', 'curl'], // always blocked regardless of policy
182
+ maxRequests: 20 // per-minute shell rate limit
183
+ }
184
+ });
162
185
  ```
163
186
 
164
- No knowledge of the validation pipeline, request format, or policy internals
165
- required. Every method routes through the full gate sequence and returns a
166
- structured result.
187
+ ### Policy management
188
+
189
+ ```js
190
+ // Propose a rule — returns an object for the host to review, writes nothing
191
+ const proposal = lbe.policy.proposeRule({
192
+ effect: 'deny',
193
+ type: 'path',
194
+ pattern: 'secrets/**',
195
+ from: 'agent: these files should not be modified'
196
+ });
197
+
198
+ // Host accepts and writes the rule
199
+ lbe.policy.addRule(proposal);
200
+
201
+ // Read current policy
202
+ const policy = lbe.policy.read();
203
+
204
+ // Verify the audit chain has not been tampered with
205
+ lbe.audit.verify();
206
+ ```
207
+
208
+ ---
209
+
210
+ ## CLI reference
211
+
212
+ ```bash
213
+ npx lbe-exec init # create lbe.policy.json in observer mode
214
+ npx lbe-exec status # show mode, rule count, and audit entry count
215
+ npx lbe-exec enforce # switch to blocking
216
+ npx lbe-exec observe # switch back to advisory
217
+ npx lbe-exec policy # list active rules
218
+ ```
219
+
220
+ | Command | Purpose |
221
+ |---|---|
222
+ | `npx lbe-exec init` | Bootstrap governance — policy, keys, agent files |
223
+ | `npx lbe-exec status` | Show mode, rule count, audit entry count |
224
+ | `npx lbe-exec policy` | List active rules |
225
+ | `npx lbe-exec observe` | Set advisory (log-only) mode |
226
+ | `npx lbe-exec enforce` | Set blocking mode |
227
+ | `npx lbe-exec execute` | Pipe a JSON request from stdin or `--input <file>` |
167
228
 
168
229
  ---
169
230
 
170
231
  ## What ships
171
232
 
172
- This package contains the in-process execution controller and the WASM
173
- validation runtime. It does not contain a hosted service, daemon, or network
174
- dependency.
233
+ ```
234
+ dist/index.js In-process executor createLocalExecutor()
235
+ dist/cli.js Local CLI (npx lbe-exec)
236
+ dist/lbe_engine.wasm Verified WASM runtime binary
237
+ dist/wasm.lock.json Runtime integrity lock (SHA-256 of wasm binary)
238
+ assets/lbe-gates.png Gate sequence diagram
239
+ assets/story-allow.png Approved-request storyboard
240
+ assets/story-deny.png Blocked-request storyboard
241
+ assets/runtime-boundary.svg Runtime boundary diagram
242
+ types.d.ts TypeScript declarations
243
+ ```
244
+
245
+ Source code, tests, keys, and runtime state are not included.
246
+
247
+ ---
248
+
249
+ ## Limits
250
+
251
+ This package governs actions routed through its executor. It does not provide
252
+ kernel-level process isolation, network-egress control, multi-tenant separation,
253
+ or a hosted control plane.
175
254
 
176
- Source code, tests, keys, and runtime state are never included.
255
+ For the raw WASM runtime without a controller, see `@letterblack/lbe-sdk`.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@letterblack/lbe-exec",
3
- "version": "1.2.3",
3
+ "version": "1.2.5",
4
4
  "description": "Local host-signed execution layer for LetterBlack LBE.",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",