genaicode 2.11.0 → 2.13.2
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/CHANGELOG.md +52 -1
- package/README.md +18 -16
- package/dist/agents/cli-agent.d.ts +6 -3
- package/dist/agents/cli-agent.js +57 -35
- package/dist/agents/cli-agent.js.map +1 -1
- package/dist/agents/drivers/antigravity.d.ts +7 -1
- package/dist/agents/drivers/antigravity.js +27 -2
- package/dist/agents/drivers/antigravity.js.map +1 -1
- package/dist/agents/drivers/claude-approvals.d.ts +86 -0
- package/dist/agents/drivers/claude-approvals.js +278 -0
- package/dist/agents/drivers/claude-approvals.js.map +1 -0
- package/dist/agents/drivers/claude.d.ts +12 -2
- package/dist/agents/drivers/claude.js +74 -11
- package/dist/agents/drivers/claude.js.map +1 -1
- package/dist/agents/drivers/codex-approvals.d.ts +11 -0
- package/dist/agents/drivers/codex-approvals.js +118 -0
- package/dist/agents/drivers/codex-approvals.js.map +1 -0
- package/dist/agents/drivers/codex-live.d.ts +12 -1
- package/dist/agents/drivers/codex-live.js +46 -32
- package/dist/agents/drivers/codex-live.js.map +1 -1
- package/dist/agents/drivers/codex.d.ts +10 -1
- package/dist/agents/drivers/codex.js +48 -2
- package/dist/agents/drivers/codex.js.map +1 -1
- package/dist/agents/drivers/copilot.d.ts +9 -1
- package/dist/agents/drivers/copilot.js +31 -1
- package/dist/agents/drivers/copilot.js.map +1 -1
- package/dist/agents/drivers/cursor.d.ts +10 -1
- package/dist/agents/drivers/cursor.js +48 -5
- package/dist/agents/drivers/cursor.js.map +1 -1
- package/dist/agents/drivers/gemini.d.ts +11 -1
- package/dist/agents/drivers/gemini.js +46 -2
- package/dist/agents/drivers/gemini.js.map +1 -1
- package/dist/agents/drivers/muse-approvals.d.ts +19 -0
- package/dist/agents/drivers/muse-approvals.js +157 -0
- package/dist/agents/drivers/muse-approvals.js.map +1 -0
- package/dist/agents/drivers/muse-live.d.ts +5 -1
- package/dist/agents/drivers/muse-live.js +21 -109
- package/dist/agents/drivers/muse-live.js.map +1 -1
- package/dist/agents/drivers/opencode.d.ts +7 -1
- package/dist/agents/drivers/opencode.js +28 -2
- package/dist/agents/drivers/opencode.js.map +1 -1
- package/dist/agents/drivers/permission-args.d.ts +14 -0
- package/dist/agents/drivers/permission-args.js +40 -0
- package/dist/agents/drivers/permission-args.js.map +1 -0
- package/dist/agents/drivers/vibe.d.ts +9 -1
- package/dist/agents/drivers/vibe.js +40 -2
- package/dist/agents/drivers/vibe.js.map +1 -1
- package/dist/agents/hosted.js +9 -0
- package/dist/agents/hosted.js.map +1 -1
- package/dist/agents/live-agent.d.ts +49 -4
- package/dist/agents/live-agent.js +84 -15
- package/dist/agents/live-agent.js.map +1 -1
- package/dist/agents/permissions.d.ts +27 -0
- package/dist/agents/permissions.js +79 -0
- package/dist/agents/permissions.js.map +1 -0
- package/dist/agents/prepare.d.ts +12 -1
- package/dist/agents/prepare.js +18 -3
- package/dist/agents/prepare.js.map +1 -1
- package/dist/agents/rpc.d.ts +13 -2
- package/dist/agents/rpc.js +20 -2
- package/dist/agents/rpc.js.map +1 -1
- package/dist/agents/runtime.d.ts +4 -0
- package/dist/agents/runtime.js +20 -0
- package/dist/agents/runtime.js.map +1 -1
- package/dist/agents/session.d.ts +4 -1
- package/dist/agents/session.js +31 -6
- package/dist/agents/session.js.map +1 -1
- package/dist/agents/types.d.ts +56 -7
- package/dist/agents.d.ts +21 -13
- package/dist/agents.js +14 -9
- package/dist/agents.js.map +1 -1
- package/dist/react/agent-chat.js +10 -2
- package/dist/react/agent-chat.js.map +1 -1
- package/dist/ui/index.js +69 -69
- package/dist/ui/web-client.js +9 -9
- package/docs/agents.md +129 -19
- package/package.json +5 -5
package/docs/agents.md
CHANGED
|
@@ -119,19 +119,19 @@ session.send('Now cover it with a test'); // resumes the same agent session
|
|
|
119
119
|
|
|
120
120
|
## Drivers
|
|
121
121
|
|
|
122
|
-
| Driver | Command | Mode | Notes
|
|
123
|
-
| --------------------- | -------------- | ---------------------------------------- |
|
|
124
|
-
| `claude(options?)` | `claude` | `-p --output-format stream-json` | `permissionMode` defaults to `acceptEdits`; `allowedTools` / `disallowedTools
|
|
125
|
-
| `codex(options?)` | `codex` | `exec --json` | `sandbox` defaults to `workspace-write`; effort via `model_reasoning_effort`
|
|
126
|
-
| `muse(options?)` | `muse` | `exec --json --trust-workspace` | `maxTurns` maps to `--max-model-steps`
|
|
127
|
-
| `codexLive(options?)` | `codex` | `app-server` (JSON-RPC) | `steer()`, approvals, MCP. See [Live sessions](#live-sessions-steering-and-approvals)
|
|
128
|
-
| `museLive(options?)` | `muse` | `serve` (JSON-RPC) | `steer()`, approvals. See [Live sessions](#live-sessions-steering-and-approvals)
|
|
129
|
-
| `gemini(options?)` | `gemini` | `--output-format stream-json --prompt=…` | `approvalMode` defaults to `auto_edit`; `--skip-trust` unless `trustWorkspace: false`
|
|
130
|
-
| `cursor(options?)` | `cursor-agent` | `-p --output-format stream-json` | `--force --approve-mcps` by default (`--trust` if `force: false`); `partialOutput`
|
|
131
|
-
| `opencode(options?)` | `opencode` | `run --format json` | `model` is `provider/model`; `effort` maps to `--variant`; `autoApprove` adds `--auto`
|
|
132
|
-
| `copilot(options?)` | `copilot` | `--output-format json --prompt=…` | `--allow-all-tools --no-ask-user` by default; `allowTools` / `denyTools` patterns
|
|
133
|
-
| `vibe(options?)` | `vibe` | `--output streaming --prompt=…` | `agent` defaults to `accept-edits`; `--trust`; `model` via `VIBE_ACTIVE_MODEL`
|
|
134
|
-
| `antigravity(opts?)` | `agy` | `--output-format stream-json --print` | `mode` defaults to `accept-edits`; `--sandbox` unless `sandbox: false`
|
|
122
|
+
| Driver | Command | Mode | Notes |
|
|
123
|
+
| --------------------- | -------------- | ---------------------------------------- | ----------------------------------------------------------------------------------------- |
|
|
124
|
+
| `claude(options?)` | `claude` | `-p --output-format stream-json` | `permissionMode` defaults to `acceptEdits`; `allowedTools` / `disallowedTools`; approvals |
|
|
125
|
+
| `codex(options?)` | `codex` | `exec --json` | `sandbox` defaults to `workspace-write`; effort via `model_reasoning_effort` |
|
|
126
|
+
| `muse(options?)` | `muse` | `exec --json --trust-workspace` | `maxTurns` maps to `--max-model-steps` |
|
|
127
|
+
| `codexLive(options?)` | `codex` | `app-server` (JSON-RPC) | `steer()`, approvals, MCP. See [Live sessions](#live-sessions-steering-and-approvals) |
|
|
128
|
+
| `museLive(options?)` | `muse` | `serve` (JSON-RPC) | `steer()`, approvals. See [Live sessions](#live-sessions-steering-and-approvals) |
|
|
129
|
+
| `gemini(options?)` | `gemini` | `--output-format stream-json --prompt=…` | `approvalMode` defaults to `auto_edit`; `--skip-trust` unless `trustWorkspace: false` |
|
|
130
|
+
| `cursor(options?)` | `cursor-agent` | `-p --output-format stream-json` | `--force --approve-mcps` by default (`--trust` if `force: false`); `partialOutput` |
|
|
131
|
+
| `opencode(options?)` | `opencode` | `run --format json` | `model` is `provider/model`; `effort` maps to `--variant`; `autoApprove` adds `--auto` |
|
|
132
|
+
| `copilot(options?)` | `copilot` | `--output-format json --prompt=…` | `--allow-all-tools --no-ask-user` by default; `allowTools` / `denyTools` patterns |
|
|
133
|
+
| `vibe(options?)` | `vibe` | `--output streaming --prompt=…` | `agent` defaults to `accept-edits`; `--trust`; `model` via `VIBE_ACTIVE_MODEL` |
|
|
134
|
+
| `antigravity(opts?)` | `agy` | `--output-format stream-json --print` | `mode` defaults to `accept-edits`; `--sandbox` unless `sandbox: false` |
|
|
135
135
|
|
|
136
136
|
Every driver accepts `command` to point at a specific executable. `task.extraArgs` is
|
|
137
137
|
inserted before the prompt for flags that have no portable field.
|
|
@@ -160,15 +160,125 @@ const result = await run.result;
|
|
|
160
160
|
|
|
161
161
|
- `steer(text)` resolves once the agent acknowledges the input. It rejects after the task has
|
|
162
162
|
ended, and when no acknowledgement arrives (the input may or may not have reached the agent).
|
|
163
|
-
- `onApproval`
|
|
164
|
-
`other` request and returns `'approve'` or `'deny'`. If `onApproval` is missing or throws, the
|
|
165
|
-
request is denied. Codex runs with approval policy `never` when no `onApproval` is set.
|
|
166
|
-
- `museLive()` answers each approval with one of the choices Muse offers: the `once`
|
|
167
|
-
approve or deny choice where there is one. A multi-stage approval asks `onApproval` once
|
|
168
|
-
per stage; later stages get ids like `ap-1/2`.
|
|
163
|
+
- `onApproval` answers permission requests; see [Approvals](#approvals).
|
|
169
164
|
- The task ends when the agent reports its turn complete. The server is then stopped. An exit
|
|
170
165
|
before that point is a failure, even with exit code 0.
|
|
171
166
|
|
|
167
|
+
## Approvals
|
|
168
|
+
|
|
169
|
+
`onApproval(request, signal)` answers the agent's permission prompts on drivers with
|
|
170
|
+
`capabilities.approvals`: `claude`, `codexLive`, `museLive`. It returns `'approve'` or
|
|
171
|
+
`'deny'`.
|
|
172
|
+
|
|
173
|
+
```ts
|
|
174
|
+
const run = claude().run({
|
|
175
|
+
prompt: 'Run the tests and fix what fails',
|
|
176
|
+
cwd: '/work/repo',
|
|
177
|
+
onApproval: (request, signal) => askUser(request, signal), // your UI
|
|
178
|
+
});
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
- `request.kind` is `command`, `file-change` or `other`; `summary` is one line to show;
|
|
182
|
+
`detail` is the vendor's whole request (the command with its working directory, the tool
|
|
183
|
+
input, the requested permissions). Show `detail` before asking for a decision.
|
|
184
|
+
- `request.scope` says what approving grants. `once` (or absent): this one call. `turn`: the
|
|
185
|
+
permissions in `detail` until the agent's current turn ends (Codex permission profiles).
|
|
186
|
+
- `signal` aborts when the answer is no longer needed: the agent withdrew the request, the
|
|
187
|
+
turn ended, the process exited, or the task was stopped. Close the question then. A late
|
|
188
|
+
answer counts as `deny`.
|
|
189
|
+
- No handler, a handler that throws, and an aborted signal all deny. Nothing is approved
|
|
190
|
+
automatically unless `permissions.approval` says so (see [Permissions](#permissions)).
|
|
191
|
+
`approval-request` and `approval-resolved` events record each question.
|
|
192
|
+
|
|
193
|
+
Per agent:
|
|
194
|
+
|
|
195
|
+
- `claude()`: with `onApproval`, the driver serves Claude Code's `--permission-prompt-tool`
|
|
196
|
+
from a private MCP endpoint on 127.0.0.1 (random port, random bearer token), next to the
|
|
197
|
+
task's own `mcpServers`, and raises `MCP_TOOL_TIMEOUT` to a day unless `env` sets it. The
|
|
198
|
+
permission mode still applies first (`acceptEdits` by default): only what it does not allow
|
|
199
|
+
is asked. Approving allows exactly the input Claude asked about (`updatedInput` unchanged).
|
|
200
|
+
- `codexLive()`: runs with approval policy `on-request` when `onApproval` is set (`never`
|
|
201
|
+
otherwise). Commands and file changes are answered `accept` / `decline`. A permission
|
|
202
|
+
profile request (`item/permissions/requestApproval`) is asked with `scope: 'turn'`; approving
|
|
203
|
+
grants the requested categories (those that are not null) for the turn, denying grants none.
|
|
204
|
+
Requests from another thread or turn are rejected; `serverRequest/resolved` withdraws one.
|
|
205
|
+
- `museLive()`: answers with one of the choices Muse offers and the stage's requirement id.
|
|
206
|
+
Approving picks the `once` choice; a request that only offers session-wide approval is
|
|
207
|
+
denied. A multi-stage approval asks once per stage (later stages get ids like `ap-1/2`),
|
|
208
|
+
however often a stage is delivered. `approval/resolved` withdraws an open question.
|
|
209
|
+
|
|
210
|
+
The protocol handlers are exported for apps that run their own driver or MCP server:
|
|
211
|
+
|
|
212
|
+
- `codexApprovals(session, ids)` and `museApprovals(session, ids, options?)` take a
|
|
213
|
+
`LiveSession` and a function returning the current `{ session, turn }` ids. Hand them each
|
|
214
|
+
request and notification first (`request()` returns `undefined`, `notification()` false,
|
|
215
|
+
for methods they do not own) and call `close()` when the turn ends.
|
|
216
|
+
- `claudeApprovalTool(onApproval)` is the permission prompt tool as an MCP tool (`name`,
|
|
217
|
+
`description`, `inputSchema`, `call(args, signal)`) to serve from the app's own MCP server;
|
|
218
|
+
pass `claudeApprovalArgs(serverName)` to Claude and `claudeApprovalEnv(env)` in its env.
|
|
219
|
+
Abort `signal` when the MCP caller disconnects. `startClaudeApprovalServer(onApproval)`
|
|
220
|
+
serves the tool on its own endpoint instead.
|
|
221
|
+
|
|
222
|
+
## Permissions
|
|
223
|
+
|
|
224
|
+
`task.permissions` picks the approval policy and the sandbox in one place, and each driver
|
|
225
|
+
translates it into the agent's own options. An omitted field keeps the driver's default (the
|
|
226
|
+
behavior described above); `'yolo'` is `{ approval: 'auto-approve', sandbox: 'unrestricted' }`.
|
|
227
|
+
|
|
228
|
+
```ts
|
|
229
|
+
claude().run({ prompt, cwd, permissions: { approval: 'auto-approve', sandbox: 'workspace-write' } });
|
|
230
|
+
codexLive().run({ prompt, cwd, permissions: 'yolo' });
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
- `approval`: `ask` sends prompts to `onApproval` (required then). `auto-approve` approves each
|
|
234
|
+
prompt without asking, for exactly the scope the agent asked for (one call, or a Codex
|
|
235
|
+
profile for the turn; never a session-wide grant). `deny` refuses whatever would need a
|
|
236
|
+
prompt and does not call `onApproval`.
|
|
237
|
+
- `sandbox`: `workspace-write` turns on the agent's own sandbox (writes limited to `cwd`;
|
|
238
|
+
network rules are the vendor's), `read-only` its read-only mode, `unrestricted` no sandbox,
|
|
239
|
+
even when the agent's settings enable one. `auto-approve` never grants a step outside the
|
|
240
|
+
sandbox. With `ask`, Claude refuses such steps before asking and Codex permission profiles
|
|
241
|
+
(which widen the sandbox) are denied; a Codex command or file-change approval stays the
|
|
242
|
+
person's call, as in Codex itself, so approving it may let that one step leave the sandbox.
|
|
243
|
+
- `capabilities.permissions` lists the values a driver accepts. Anything else, and any
|
|
244
|
+
combination the agent cannot honor, fails the run with `status: 'failed'` and an `error`
|
|
245
|
+
naming the value before the agent starts. Setting both a permissions field and the driver
|
|
246
|
+
option it replaces (`permissionMode`, `sandbox`, `approvalMode`, `force`...) is an error too.
|
|
247
|
+
- Where genaicode sees the prompt (Claude's prompt tool, Muse), `auto-approve` and policy
|
|
248
|
+
denials still emit `approval-request` and `approval-resolved` with `automatic: true`, and
|
|
249
|
+
`createAgentSession` shows them as transcript entries. Agents that approve by themselves
|
|
250
|
+
(Codex with policy `never`, Gemini `yolo`, Cursor `--force`...) report nothing to show.
|
|
251
|
+
|
|
252
|
+
| Driver | approval | sandbox | Translation |
|
|
253
|
+
| --------------- | ----------------------- | ---------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
254
|
+
| `claude()` | ask, auto-approve, deny | workspace-write, read-only, unrestricted | `ask` / `auto-approve`: the prompt tool; `deny`: none. `workspace-write`: Claude's sandbox via `--settings` (required, no per-command escape), `acceptEdits`; `read-only`: `plan`; `unrestricted`: sandbox off |
|
|
255
|
+
| `codex()` | auto-approve, deny | workspace-write, read-only, unrestricted | `approval_policy="never"` (exec never asks); `--sandbox` read-only / workspace-write / danger-full-access |
|
|
256
|
+
| `codexLive()` | ask, auto-approve, deny | workspace-write, read-only, unrestricted | `ask`: policy `on-request`, otherwise `never`; `thread/start` sandbox as above |
|
|
257
|
+
| `museLive()` | ask, auto-approve, deny | unrestricted | `ask` / `auto-approve`: approval mode `onRequest` (the `once` choice); `deny`: `denyUnmatched`. Muse has no sandbox |
|
|
258
|
+
| `gemini()` | auto-approve, deny | workspace-write, read-only, unrestricted | `--approval-mode yolo` / `auto_edit`; `read-only`: `plan` (not with `auto-approve`); `--sandbox` / `--no-sandbox` plus `GEMINI_SANDBOX`, which overrides the flag in Gemini |
|
|
259
|
+
| `cursor()` | auto-approve, deny | workspace-write, read-only, unrestricted | `auto-approve`: `--force`, which runs commands unsandboxed, so only with `unrestricted`; `deny`: `--trust`; `--sandbox enabled` / `disabled`; `read-only`: `--mode ask` |
|
|
260
|
+
| `copilot()` | auto-approve | unrestricted | `--allow-all-tools` (prompt mode needs it); `--allow-all-paths --allow-all-urls`. Copilot's `--sandbox` lets a command opt out of it, so `workspace-write` is not offered |
|
|
261
|
+
| `opencode()` | auto-approve, deny | unrestricted | `--auto`; opencode has no sandbox |
|
|
262
|
+
| `vibe()` | auto-approve, deny | read-only, unrestricted | `--auto-approve`; `read-only`: `--agent plan` (not with `auto-approve`); no sandbox |
|
|
263
|
+
| `antigravity()` | none | workspace-write, unrestricted | `--sandbox` on or off |
|
|
264
|
+
| `muse()` | none | none | |
|
|
265
|
+
|
|
266
|
+
Claude in `read-only` writes nothing in the workspace, but plan mode may still save its plan
|
|
267
|
+
under `~/.claude/plans`. In `workspace-write`, Claude's sandbox covers Bash; edits through its
|
|
268
|
+
file tools are accepted inside `cwd` and denied outside it.
|
|
269
|
+
|
|
270
|
+
For apps that keep their own argument lists (an adapters file, say),
|
|
271
|
+
`applyPermissionArgs(agent, args, permissions)` returns `{ args, env }` with the flags the
|
|
272
|
+
translation owns replaced, using the same per-agent functions (`claudePermissionFlags`,
|
|
273
|
+
`codexPermissionFlags`, `geminiPermissionFlags`, `cursorPermissionFlags`,
|
|
274
|
+
`copilotPermissionFlags`, `opencodePermissionFlags`, `vibePermissionFlags`,
|
|
275
|
+
`antigravityPermissionFlags`; `codexThreadPolicy` for the app server). For Claude, `ask` and
|
|
276
|
+
`auto-approve` also need the prompt tool: `claudeApprovalTool(handler, { sandbox, cwd })`
|
|
277
|
+
denies requests outside the sandbox before asking, and `decideApproval(task, request, signal)`
|
|
278
|
+
applies the approval policy the way the drivers do.
|
|
279
|
+
|
|
280
|
+
## Custom live agents
|
|
281
|
+
|
|
172
282
|
For other JSON-RPC agents, `liveAgent({ name, command, args, drive })` provides the process,
|
|
173
283
|
an `RpcPeer`, event emission, the approval flow, and `setSteer()`. `drive(session)` runs the
|
|
174
284
|
protocol and resolves with `{ ok, error? }` when the turn ends.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "genaicode",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.13.2",
|
|
4
4
|
"description": "A small, provider-neutral TypeScript toolkit for calling LLMs from backend code.",
|
|
5
5
|
"author": "Grzegorz Tańczyk",
|
|
6
6
|
"repository": {
|
|
@@ -86,8 +86,8 @@
|
|
|
86
86
|
"@types/node": "^20.0.0",
|
|
87
87
|
"@types/react": "^19.3.0",
|
|
88
88
|
"@types/react-dom": "^19.3.0",
|
|
89
|
-
"@typescript-eslint/eslint-plugin": "^
|
|
90
|
-
"@typescript-eslint/parser": "^
|
|
89
|
+
"@typescript-eslint/eslint-plugin": "^8.71.1",
|
|
90
|
+
"@typescript-eslint/parser": "^8.71.1",
|
|
91
91
|
"esbuild": "^0.28.2",
|
|
92
92
|
"eslint": "^8.54.0",
|
|
93
93
|
"eslint-config-prettier": "^9.0.0",
|
|
@@ -95,14 +95,14 @@
|
|
|
95
95
|
"husky": "^9.1.1",
|
|
96
96
|
"ink": "^6.8.0",
|
|
97
97
|
"ink-testing-library": "^4.0.0",
|
|
98
|
-
"lint-staged": "^
|
|
98
|
+
"lint-staged": "^16.4.0",
|
|
99
99
|
"playwright": "^1.56.1",
|
|
100
100
|
"prettier": "^3.1.0",
|
|
101
101
|
"react": "^19.3.0",
|
|
102
102
|
"react-dom": "^19.3.0",
|
|
103
103
|
"typescript": "^5.0.0",
|
|
104
104
|
"vite": "^6.4.3",
|
|
105
|
-
"vitest": "^
|
|
105
|
+
"vitest": "^4.1.11"
|
|
106
106
|
},
|
|
107
107
|
"lint-staged": {
|
|
108
108
|
"*.{js,ts,md}": "prettier --write"
|