@corenel/tools-web 0.11.4 → 0.12.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/dist/composerPicks.d.ts +30 -0
- package/dist/composerPicks.d.ts.map +1 -0
- package/dist/composerPicks.js +123 -0
- package/dist/composerPicks.js.map +1 -0
- package/dist/core/protocol.d.ts +36 -1
- package/dist/core/protocol.d.ts.map +1 -1
- package/dist/injectionCheck.d.ts +44 -0
- package/dist/injectionCheck.d.ts.map +1 -0
- package/dist/injectionCheck.js +73 -0
- package/dist/injectionCheck.js.map +1 -0
- package/dist/liveFold.d.ts +4 -0
- package/dist/liveFold.d.ts.map +1 -1
- package/dist/liveFold.js +15 -0
- package/dist/liveFold.js.map +1 -1
- package/dist/mutationHook.d.ts +32 -0
- package/dist/mutationHook.d.ts.map +1 -0
- package/dist/mutationHook.js +108 -0
- package/dist/mutationHook.js.map +1 -0
- package/dist/runtime.d.ts +145 -41
- package/dist/runtime.d.ts.map +1 -1
- package/dist/runtime.js +1045 -975
- package/dist/runtime.js.map +1 -1
- package/dist/sessionTools.d.ts +5 -3
- package/dist/sessionTools.d.ts.map +1 -1
- package/dist/sessionTools.js +12 -7
- package/dist/sessionTools.js.map +1 -1
- package/dist/systemOneGate/gate.d.ts +45 -0
- package/dist/systemOneGate/gate.d.ts.map +1 -0
- package/dist/systemOneGate/gate.js +380 -0
- package/dist/systemOneGate/gate.js.map +1 -0
- package/dist/systemOneGate/requests.d.ts +67 -0
- package/dist/systemOneGate/requests.d.ts.map +1 -0
- package/dist/systemOneGate/requests.js +201 -0
- package/dist/systemOneGate/requests.js.map +1 -0
- package/dist/workerClient.d.ts +39 -1
- package/dist/workerClient.d.ts.map +1 -1
- package/dist/workerClient.js +96 -7
- package/dist/workerClient.js.map +1 -1
- package/dist/workerHandler.d.ts.map +1 -1
- package/dist/workerHandler.js +118 -20
- package/dist/workerHandler.js.map +1 -1
- package/dist/workspaceBlock.d.ts +5 -0
- package/dist/workspaceBlock.d.ts.map +1 -0
- package/dist/workspaceBlock.js +18 -0
- package/dist/workspaceBlock.js.map +1 -0
- package/package.json +4 -4
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
import { CHECK_STATE_BYTES, INJECTION_QUESTION } from '../injectionCheck';
|
|
2
|
+
const MAX_QUESTIONS = 16;
|
|
3
|
+
/** Characters of JSON-stringified args kept before the output gets what is left. */
|
|
4
|
+
const ARGS_CHARS = 8 * 1024;
|
|
5
|
+
const ROUTE_STATE_BYTES = 30 * 1024;
|
|
6
|
+
const LABEL_CHARS = 200;
|
|
7
|
+
const CRITERION_CHARS = 500;
|
|
8
|
+
/** The one tool a `before-commit` hook applies to. */
|
|
9
|
+
const COMMIT_TOOL = 'sidecar_git_commit';
|
|
10
|
+
const bytesOf = (v) => new TextEncoder().encode(JSON.stringify(v)).length;
|
|
11
|
+
const isObject = (v) => v !== null && typeof v === 'object' && !Array.isArray(v);
|
|
12
|
+
const unit = (n) => typeof n === 'number' && n >= 0 && n <= 1;
|
|
13
|
+
/** `text` cut to at most `max` characters, never inside a surrogate pair. */
|
|
14
|
+
function head(text, max) {
|
|
15
|
+
if (text.length <= max)
|
|
16
|
+
return text;
|
|
17
|
+
const t = text.slice(0, Math.max(0, max));
|
|
18
|
+
return /[\uD800-\uDBFF]$/.test(t) ? t.slice(0, -1) : t;
|
|
19
|
+
}
|
|
20
|
+
/** The longest start of `text` for which `size(start)` is within `budget`. The
|
|
21
|
+
* measure drives the loop: JSON escaping and UTF-8 both make bytes run ahead of
|
|
22
|
+
* characters. Returns the cut text and whether any was left out. */
|
|
23
|
+
function fitText(text, budget, size) {
|
|
24
|
+
if (size(text) <= budget)
|
|
25
|
+
return { text, cut: false };
|
|
26
|
+
let end = Math.min(text.length, budget);
|
|
27
|
+
for (;;) {
|
|
28
|
+
const t = head(text, end);
|
|
29
|
+
const s = size(t);
|
|
30
|
+
if (s <= budget)
|
|
31
|
+
return { text: t, cut: true };
|
|
32
|
+
if (t.length === 0)
|
|
33
|
+
return { text: '', cut: true };
|
|
34
|
+
end = Math.max(0, Math.floor(t.length * (budget / s)) - 16);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
/** The enabled hooks that apply to this event and tool, in list order. A
|
|
38
|
+
* `before-commit` hook applies on `before-tool` to sidecar_git_commit only. */
|
|
39
|
+
export function hooksFor(rules, event, toolName) {
|
|
40
|
+
return rules.hooks.filter((h) => {
|
|
41
|
+
if (!h.enabled)
|
|
42
|
+
return false;
|
|
43
|
+
if (h.event === 'before-commit')
|
|
44
|
+
return event === 'before-tool' && toolName === COMMIT_TOOL;
|
|
45
|
+
if (h.event !== event)
|
|
46
|
+
return false;
|
|
47
|
+
return h.tools.length === 0 || h.tools.includes(toolName);
|
|
48
|
+
});
|
|
49
|
+
}
|
|
50
|
+
function hookPrefix(tail) {
|
|
51
|
+
const what = tail === undefined || tail.text === '' ? ''
|
|
52
|
+
: tail.key === 'output' ? ', and `output` what it returned'
|
|
53
|
+
: ', and `changes` the unified diff of every change the commit would take';
|
|
54
|
+
return '`tool` is the name of a tool an AI assistant is using, `args` its arguments' + what + '. ';
|
|
55
|
+
}
|
|
56
|
+
/** `{ tool, args, output? | changes? }` under CHECK_STATE_BYTES. Args are
|
|
57
|
+
* JSON-stringified and cut first (ARGS_CHARS), then the tail takes whatever
|
|
58
|
+
* room is left. */
|
|
59
|
+
function eventState(toolName, args, tail) {
|
|
60
|
+
let argsText;
|
|
61
|
+
try {
|
|
62
|
+
argsText = JSON.stringify(args) ?? '';
|
|
63
|
+
}
|
|
64
|
+
catch {
|
|
65
|
+
argsText = '';
|
|
66
|
+
}
|
|
67
|
+
const shortArgs = head(argsText, ARGS_CHARS);
|
|
68
|
+
const argsCut = shortArgs.length < argsText.length;
|
|
69
|
+
const build = (a, t) => ({ tool: toolName, args: a, ...(t === undefined || tail === undefined ? {} : { [tail.key]: t }) });
|
|
70
|
+
// Args alone must fit first, whatever the tail is.
|
|
71
|
+
const a = fitText(shortArgs, CHECK_STATE_BYTES, (t) => bytesOf(build(t, tail === undefined ? undefined : '')));
|
|
72
|
+
const cutArgs = argsCut || a.cut;
|
|
73
|
+
if (tail === undefined)
|
|
74
|
+
return { state: build(a.text), cut: cutArgs };
|
|
75
|
+
// Characters before bytes: slicing to the byte budget first loses nothing
|
|
76
|
+
// that would fit, and a multi-MB tail is never stringified whole.
|
|
77
|
+
const pre = head(tail.text, CHECK_STATE_BYTES);
|
|
78
|
+
const o = fitText(pre, CHECK_STATE_BYTES, (t) => bytesOf(build(a.text, t)));
|
|
79
|
+
return { state: build(a.text, o.text), cut: cutArgs || o.cut || pre.length < tail.text.length };
|
|
80
|
+
}
|
|
81
|
+
/** True when a commit's arguments (its message) and `changes` fit the state
|
|
82
|
+
* whole. A before-commit hook is sent only then: System One never judges a
|
|
83
|
+
* commit from part of its changes. */
|
|
84
|
+
export function commitStateFits(toolName, args, changes) {
|
|
85
|
+
return !eventState(toolName, args, { key: 'changes', text: changes }).cut;
|
|
86
|
+
}
|
|
87
|
+
/** The decisions requests for one tool event: at most 16 questions each, the
|
|
88
|
+
* injection check (key `injection`) first, hooks as `h0..hN`. Every request
|
|
89
|
+
* carries the same state. No requests when there is nothing to ask. */
|
|
90
|
+
export function buildEventRequests(args) {
|
|
91
|
+
const tail = args.output !== undefined ? { key: 'output', text: args.output }
|
|
92
|
+
: args.changes !== undefined ? { key: 'changes', text: args.changes } : undefined;
|
|
93
|
+
const { state, cut } = eventState(args.toolName, args.args, tail);
|
|
94
|
+
const prefix = hookPrefix(tail);
|
|
95
|
+
const out = [];
|
|
96
|
+
const open = () => ({ body: { state, questions: {} }, keys: { hook: new Map(), injection: false }, cut });
|
|
97
|
+
let current = open();
|
|
98
|
+
let count = 0;
|
|
99
|
+
if (args.injection) {
|
|
100
|
+
current.body.questions.injection = INJECTION_QUESTION;
|
|
101
|
+
current.keys.injection = true;
|
|
102
|
+
count += 1;
|
|
103
|
+
}
|
|
104
|
+
args.hooks.forEach((hook, i) => {
|
|
105
|
+
if (count >= MAX_QUESTIONS) {
|
|
106
|
+
out.push(current);
|
|
107
|
+
current = open();
|
|
108
|
+
count = 0;
|
|
109
|
+
}
|
|
110
|
+
const key = `h${i}`;
|
|
111
|
+
current.body.questions[key] = { type: 'noul', instructions: prefix + hook.question };
|
|
112
|
+
current.keys.hook.set(key, hook);
|
|
113
|
+
count += 1;
|
|
114
|
+
});
|
|
115
|
+
if (count > 0)
|
|
116
|
+
out.push(current);
|
|
117
|
+
return out;
|
|
118
|
+
}
|
|
119
|
+
/** The scores for one request: hook scores by hook id, and the injection score
|
|
120
|
+
* when it was asked. Null when any asked key is missing or is not a noul in [0,1]. */
|
|
121
|
+
export function readEventAnswers(body, keys) {
|
|
122
|
+
const answers = isObject(body) && isObject(body.answers) ? body.answers : null;
|
|
123
|
+
if (!answers)
|
|
124
|
+
return null;
|
|
125
|
+
const noul = (key) => {
|
|
126
|
+
const a = answers[key];
|
|
127
|
+
return isObject(a) && a.type === 'noul' && unit(a.noul) ? a.noul : null;
|
|
128
|
+
};
|
|
129
|
+
const hooks = new Map();
|
|
130
|
+
for (const [key, hook] of keys.hook) {
|
|
131
|
+
const n = noul(key);
|
|
132
|
+
if (n === null)
|
|
133
|
+
return null;
|
|
134
|
+
hooks.set(hook.id, n);
|
|
135
|
+
}
|
|
136
|
+
if (!keys.injection)
|
|
137
|
+
return { hooks };
|
|
138
|
+
const inj = noul('injection');
|
|
139
|
+
if (inj === null)
|
|
140
|
+
return null;
|
|
141
|
+
return { hooks, injection: inj };
|
|
142
|
+
}
|
|
143
|
+
/** Batches of at most 16 items. Task text is cut to share the state budget; an
|
|
144
|
+
* item is never dropped. Categories are the criteria c0..cN of every question. */
|
|
145
|
+
export function buildRouteRequests(items, categories) {
|
|
146
|
+
// A choice question needs at least two options.
|
|
147
|
+
if (categories.length < 2)
|
|
148
|
+
return [];
|
|
149
|
+
const criteria = {};
|
|
150
|
+
categories.forEach((c, i) => { criteria[`c${i}`] = head(`${c.name}: ${c.explanation}`, CRITERION_CHARS); });
|
|
151
|
+
const out = [];
|
|
152
|
+
for (let from = 0; from < items.length; from += MAX_QUESTIONS) {
|
|
153
|
+
const batch = items.slice(from, from + MAX_QUESTIONS);
|
|
154
|
+
const ids = new Map();
|
|
155
|
+
const questions = {};
|
|
156
|
+
batch.forEach((item, i) => {
|
|
157
|
+
ids.set(`q${i}`, item.id);
|
|
158
|
+
questions[`q${i}`] = {
|
|
159
|
+
type: 'choice',
|
|
160
|
+
instructions: `Which category best describes the work in \`items.q${i}\`?`,
|
|
161
|
+
criteria,
|
|
162
|
+
};
|
|
163
|
+
});
|
|
164
|
+
const build = (cap) => {
|
|
165
|
+
const o = {};
|
|
166
|
+
batch.forEach((item, i) => { o[`q${i}`] = { label: head(item.label, LABEL_CHARS), task: head(item.task, cap) }; });
|
|
167
|
+
return { items: o };
|
|
168
|
+
};
|
|
169
|
+
// One cap for every task in the batch, shrunk by the measured overshoot.
|
|
170
|
+
let cap = Math.max(0, ...batch.map((b) => b.task.length));
|
|
171
|
+
let state = build(cap);
|
|
172
|
+
while (bytesOf(state) > ROUTE_STATE_BYTES && cap > 0) {
|
|
173
|
+
const size = bytesOf(state);
|
|
174
|
+
cap = Math.max(0, Math.min(cap - 1, Math.floor(cap * (ROUTE_STATE_BYTES / size)) - 8));
|
|
175
|
+
state = build(cap);
|
|
176
|
+
}
|
|
177
|
+
out.push({ body: { state, questions }, ids });
|
|
178
|
+
}
|
|
179
|
+
return out;
|
|
180
|
+
}
|
|
181
|
+
/** Category name and confidence per item id. An answer with no confidence reads
|
|
182
|
+
* as 0, so the caller's confidence floor sends it to the fallback model. Null
|
|
183
|
+
* when any asked item has no valid choice answer. */
|
|
184
|
+
export function readRouteAnswers(body, ids, categories) {
|
|
185
|
+
const answers = isObject(body) && isObject(body.answers) ? body.answers : null;
|
|
186
|
+
if (!answers)
|
|
187
|
+
return null;
|
|
188
|
+
const out = new Map();
|
|
189
|
+
for (const [key, id] of ids) {
|
|
190
|
+
const a = answers[key];
|
|
191
|
+
if (!isObject(a) || a.type !== 'choice' || typeof a.choice !== 'string')
|
|
192
|
+
return null;
|
|
193
|
+
const m = /^c(0|[1-9]\d*)$/.exec(a.choice);
|
|
194
|
+
const category = m ? categories[Number(m[1])] : undefined;
|
|
195
|
+
if (!category)
|
|
196
|
+
return null;
|
|
197
|
+
out.set(id, { category: category.name, confidence: unit(a.confidence) ? a.confidence : 0 });
|
|
198
|
+
}
|
|
199
|
+
return out;
|
|
200
|
+
}
|
|
201
|
+
//# sourceMappingURL=requests.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"requests.js","sourceRoot":"","sources":["../../systemOneGate/requests.ts"],"names":[],"mappings":"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"}
|
package/dist/workerClient.d.ts
CHANGED
|
@@ -4,7 +4,7 @@ import type { SkillEntry } from '@corenel/harness/tools/skillTool';
|
|
|
4
4
|
import type { WorkerToMain, GraphConfigWire } from './core/protocol';
|
|
5
5
|
import type { RunNodeResult, NodeSpec } from '@corenel/harness/dag/executeNode';
|
|
6
6
|
import type { NodeOutput, NodeEvent } from '@corenel/protocol';
|
|
7
|
-
import type { AgentEvent, AskQuestion, AskAnswers, EditReviewOutcome, HealRecord, Usage, DecisionEvent, RecordContext, ApprovalSuggestion, ApprovalSubject } from '@corenel/protocol';
|
|
7
|
+
import type { AgentEvent, AskQuestion, AskAnswers, EditReviewOutcome, HealRecord, Usage, DecisionEvent, RecordContext, ApprovalSuggestion, ApprovalSubject, SystemOneRules } from '@corenel/protocol';
|
|
8
8
|
import type { Policy, PermissionCeiling } from '@corenel/harness/guardrail';
|
|
9
9
|
import type { CompressionConfig } from '@corenel/harness/compression';
|
|
10
10
|
import type { FileService } from '@corenel/protocol';
|
|
@@ -14,15 +14,42 @@ import type { CrewDelegate, OrchestrationLimits, WorkspaceLockRef } from '@coren
|
|
|
14
14
|
import type { RunConstraints, Breach, BudgetState } from '@corenel/harness/core/budget';
|
|
15
15
|
import type { ModelRouting } from '@corenel/harness/providers/gateway';
|
|
16
16
|
import { type AuditBridgeHost } from '@corenel/harness/audit/runAudit';
|
|
17
|
+
import { type MutationHook } from './mutationHook';
|
|
17
18
|
/** Options for runNode — like RunOpts but the node's internal turns arrive via
|
|
18
19
|
* onNodeEvent (the node-tagged stream); onEvent only ever sees a terminal error. */
|
|
19
20
|
/** One permission ask as the host sees it. `agent` names a delegated callee
|
|
20
21
|
* (call_agent) that raised it; absent for the run's own agent. */
|
|
22
|
+
/** What an ask is about, for the approval card: the command, path and folder
|
|
23
|
+
* only, each clipped. Never the whole tool input (a 5,000-line write's content
|
|
24
|
+
* has no business in UI state). */
|
|
25
|
+
export type PermDetail = {
|
|
26
|
+
command?: string;
|
|
27
|
+
path?: string;
|
|
28
|
+
cwd?: string;
|
|
29
|
+
root?: string;
|
|
30
|
+
};
|
|
31
|
+
/** The PermDetail of a tool input; undefined when it names none of them. */
|
|
32
|
+
export declare function permDetail(input: unknown): PermDetail | undefined;
|
|
33
|
+
/** What a System One ask is about (tool `HOOK_ASK_TOOL`): the tool the
|
|
34
|
+
* check or hook fired on, every reason, and for an after-tool ask the tool's
|
|
35
|
+
* output, so the card can show the result before the person decides. */
|
|
36
|
+
export type HookAskDetail = {
|
|
37
|
+
tool: string;
|
|
38
|
+
reasons: string[];
|
|
39
|
+
result?: string;
|
|
40
|
+
};
|
|
21
41
|
export interface PermissionRequest {
|
|
22
42
|
tool: string;
|
|
23
43
|
summary: string;
|
|
24
44
|
agent?: string;
|
|
45
|
+
input?: PermDetail | HookAskDetail;
|
|
25
46
|
}
|
|
47
|
+
/** A System One ask's answer from the run's permission handler. Only an
|
|
48
|
+
* explicit Allow (`true` or `{ allow: true }`) allows; no handler, no answer
|
|
49
|
+
* (null: nobody to ask), a throw, or a stopped run is a Block. Unlike a
|
|
50
|
+
* permission ask, an unattended run is never allowed here: the spec's rule is
|
|
51
|
+
* that a run with nobody to answer never continues past a check on its own. */
|
|
52
|
+
export declare function answerHookAsk(onPermission: ((req: PermissionRequest) => Promise<PermissionAnswer>) | undefined, req: PermissionRequest, signal: AbortSignal | undefined): Promise<boolean>;
|
|
26
53
|
/** What a host's permission handler answers: a bare boolean (a person
|
|
27
54
|
* clicked), or who answered, and for a deny the person's reason. */
|
|
28
55
|
export type PermissionAnswer = boolean | {
|
|
@@ -197,6 +224,12 @@ export interface WorkerAgentOpts {
|
|
|
197
224
|
* read). A getter so a Settings change applies to the next run without
|
|
198
225
|
* recreating the worker. Mirrors getGraphConfig. */
|
|
199
226
|
getModelRouting?: () => ModelRouting | undefined;
|
|
227
|
+
/** The user's System One rules to carry to the worker per run (they are
|
|
228
|
+
* read from the API on the main thread, which the worker cannot do with
|
|
229
|
+
* the user's session). A getter so a save applies to the next run; the run
|
|
230
|
+
* message holds a copy, so a run keeps the rules it started with.
|
|
231
|
+
* Absent or undefined = the worker uses DEFAULT_RULES. */
|
|
232
|
+
getSystemOneRules?: () => SystemOneRules | undefined;
|
|
200
233
|
/** The approvals service, which owns the config workspace (the worker's file
|
|
201
234
|
* proxy cannot reach it). A getter, like the others above, so the host can
|
|
202
235
|
* construct it lazily/reactively. Absent or returning null answers every
|
|
@@ -233,6 +266,11 @@ export interface WorkerAgentOpts {
|
|
|
233
266
|
* re-reads the env var itself. The host supplies the number here instead;
|
|
234
267
|
* absent that, the sampler falls back to its own built-in default. */
|
|
235
268
|
getTelemetrySampleRate?: () => number;
|
|
269
|
+
/** Sees every file change the agent asks for -- a kernel file tool's
|
|
270
|
+
* `file-request` or a sidecar file tool's `tool-request` -- before it runs,
|
|
271
|
+
* and may refuse it (mutationHook.ts). Absent: requests are answered as
|
|
272
|
+
* they always were. */
|
|
273
|
+
mutations?: MutationHook;
|
|
236
274
|
}
|
|
237
275
|
/** The usage to meter from a worker message: the root run's own turns and
|
|
238
276
|
* every sub-agent's (node-event). Sub-agent usage was never metered, so a
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"workerClient.d.ts","sourceRoot":"","sources":["../workerClient.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAC;AACpF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAC;AACjE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kCAAkC,CAAC;AACnE,OAAO,KAAK,EAAgB,YAAY,EAAY,eAAe,EAAE,MAAM,iBAAiB,CAAC;AAC7F,OAAO,KAAK,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,kCAAkC,CAAC;AAChF,OAAO,KAAK,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,mBAAmB,CAAC;AAE/D,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,UAAU,EAAE,iBAAiB,EAAE,UAAU,EAAE,KAAK,EAAE,aAAa,EAAE,aAAa,EAAE,kBAAkB,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;
|
|
1
|
+
{"version":3,"file":"workerClient.d.ts","sourceRoot":"","sources":["../workerClient.ts"],"names":[],"mappings":"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"}
|
package/dist/workerClient.js
CHANGED
|
@@ -2,10 +2,54 @@ import { nodeUsageOf } from './nodeUsage';
|
|
|
2
2
|
import { isAgentLogging, alog } from '@corenel/harness/log';
|
|
3
3
|
import { makeBudgetGate } from './budgetGate';
|
|
4
4
|
import { createRunRecorder } from './runSpans';
|
|
5
|
-
import { createRunSampler, captureSpan } from '@corenel/telemetry';
|
|
5
|
+
import { createRunSampler, captureSpan, trackEvent } from '@corenel/telemetry';
|
|
6
|
+
import { checkTelemetry } from './injectionCheck';
|
|
6
7
|
import { startRunAudit } from '@corenel/harness/audit/runAudit';
|
|
7
8
|
import { newTraceId } from '@corenel/harness/audit/ids';
|
|
8
|
-
import { denialNote } from '@corenel/protocol';
|
|
9
|
+
import { denialNote, HOOK_ASK_TOOL } from '@corenel/protocol';
|
|
10
|
+
import { guardMutation, fileRequestMutation, toolRequestMutation } from './mutationHook';
|
|
11
|
+
const PERM_DETAIL_MAX = 280;
|
|
12
|
+
const PERM_DETAIL_KEYS = ['command', 'path', 'cwd', 'root'];
|
|
13
|
+
/** The PermDetail of a tool input; undefined when it names none of them. */
|
|
14
|
+
export function permDetail(input) {
|
|
15
|
+
if (input === null || typeof input !== 'object' || Array.isArray(input))
|
|
16
|
+
return undefined;
|
|
17
|
+
const src = input;
|
|
18
|
+
const out = {};
|
|
19
|
+
for (const k of PERM_DETAIL_KEYS) {
|
|
20
|
+
const v = src[k];
|
|
21
|
+
if (typeof v !== 'string' || !v.trim())
|
|
22
|
+
continue;
|
|
23
|
+
const t = v.trim();
|
|
24
|
+
out[k] = t.length > PERM_DETAIL_MAX ? `${t.slice(0, PERM_DETAIL_MAX - 1)}…` : t;
|
|
25
|
+
}
|
|
26
|
+
return Object.keys(out).length ? out : undefined;
|
|
27
|
+
}
|
|
28
|
+
/** A System One ask's answer from the run's permission handler. Only an
|
|
29
|
+
* explicit Allow (`true` or `{ allow: true }`) allows; no handler, no answer
|
|
30
|
+
* (null: nobody to ask), a throw, or a stopped run is a Block. Unlike a
|
|
31
|
+
* permission ask, an unattended run is never allowed here: the spec's rule is
|
|
32
|
+
* that a run with nobody to answer never continues past a check on its own. */
|
|
33
|
+
export async function answerHookAsk(onPermission, req, signal) {
|
|
34
|
+
if (!onPermission || signal?.aborted)
|
|
35
|
+
return false;
|
|
36
|
+
let onAbort;
|
|
37
|
+
const stopped = new Promise((resolve) => {
|
|
38
|
+
onAbort = () => resolve(false);
|
|
39
|
+
signal?.addEventListener('abort', onAbort, { once: true });
|
|
40
|
+
});
|
|
41
|
+
try {
|
|
42
|
+
const res = await Promise.race([onPermission(req), stopped]);
|
|
43
|
+
return res === true || (typeof res === 'object' && res !== null && res.allow === true);
|
|
44
|
+
}
|
|
45
|
+
catch {
|
|
46
|
+
return false;
|
|
47
|
+
}
|
|
48
|
+
finally {
|
|
49
|
+
if (onAbort)
|
|
50
|
+
signal?.removeEventListener('abort', onAbort);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
9
53
|
/** Re-phrase a file-mutation permission prompt from the live workspace, so the
|
|
10
54
|
* stated risk reflects the CURRENT source. Returns null for non-file tools. */
|
|
11
55
|
function fileWriteSummary(tool, input, svc) {
|
|
@@ -73,6 +117,10 @@ export function createWorkerAgent(clientOpts) {
|
|
|
73
117
|
// Per-run audits (approvals-request is client-level, so a decision finds its
|
|
74
118
|
// run's recorder here). Removed when the run settles.
|
|
75
119
|
const auditRuns = new Map();
|
|
120
|
+
// Per-run chat id, for the mutation hook (file-request and tool-request are
|
|
121
|
+
// client-level). Set for a run started with a sessionId; removed when it settles.
|
|
122
|
+
const mutationSessions = new Map();
|
|
123
|
+
const sessionOf = (runId) => (runId === undefined ? null : mutationSessions.get(runId) ?? null);
|
|
76
124
|
/** Start a run's audit, or null when the host audits nothing. A `getAudit`
|
|
77
125
|
* that throws means no audit (nothing says auditing is on); everything
|
|
78
126
|
* after that -- buffering, baseline, bounded finish -- is @corenel/harness/audit/runAudit.
|
|
@@ -129,7 +177,9 @@ export function createWorkerAgent(clientOpts) {
|
|
|
129
177
|
const fn = svc[m.op];
|
|
130
178
|
if (typeof fn !== 'function')
|
|
131
179
|
throw new Error(`Unsupported file op: ${m.op}`);
|
|
132
|
-
|
|
180
|
+
// Only the agent's own requests carry a runId; the worker's store writes never reach the hook.
|
|
181
|
+
const mutation = m.runId === undefined ? null : fileRequestMutation(m.op, m.args, sessionOf(m.runId));
|
|
182
|
+
const data = await guardMutation(clientOpts.mutations, mutation, () => fn.apply(svc, m.args));
|
|
133
183
|
send({ kind: 'file-response', id: m.id, ok: true, data });
|
|
134
184
|
}
|
|
135
185
|
catch (e) {
|
|
@@ -178,13 +228,19 @@ export function createWorkerAgent(clientOpts) {
|
|
|
178
228
|
return;
|
|
179
229
|
}
|
|
180
230
|
try {
|
|
181
|
-
const
|
|
231
|
+
const mutation = toolRequestMutation(m.name, m.args, sessionOf(m.runId));
|
|
232
|
+
const result = await guardMutation(clientOpts.mutations, mutation, () => exec(m.name, m.args, remoteAborts.get(m.runId)?.signal, { ask: remoteAsk.get(m.runId), runState: remoteRunState.get(m.runId) }));
|
|
182
233
|
send({ kind: 'tool-response', id: m.id, ok: true, result });
|
|
183
234
|
}
|
|
184
235
|
catch (e) {
|
|
185
236
|
send({ kind: 'tool-response', id: m.id, ok: false, error: String(e?.message || e) });
|
|
186
237
|
}
|
|
187
238
|
}
|
|
239
|
+
else if (m.kind === 'tool-check') {
|
|
240
|
+
// Here, not in the run's listener: a check can finish after its run.
|
|
241
|
+
// Carries what the check led to (outcome) with the score.
|
|
242
|
+
trackEvent('injection_check', checkTelemetry(m.name, m.check));
|
|
243
|
+
}
|
|
188
244
|
else if (m.kind === 'approvals-request') {
|
|
189
245
|
// Audit every decision, whether or not an approvals service exists.
|
|
190
246
|
if (m.op === 'record')
|
|
@@ -228,6 +284,12 @@ export function createWorkerAgent(clientOpts) {
|
|
|
228
284
|
return worker;
|
|
229
285
|
}
|
|
230
286
|
let runSeq = 0;
|
|
287
|
+
/** The System One rules for one run message: a copy, so editing or
|
|
288
|
+
* replacing the host's rules after the run was sent changes nothing in it. */
|
|
289
|
+
function systemOneRulesField() {
|
|
290
|
+
const rules = clientOpts.getSystemOneRules?.();
|
|
291
|
+
return rules ? { systemOneRules: structuredClone(rules) } : {};
|
|
292
|
+
}
|
|
231
293
|
/** Snapshot the LIVE workspace's risk metadata for a run/permission prompt. */
|
|
232
294
|
function currentFileMeta() {
|
|
233
295
|
const svc = clientOpts.getFileService?.() || null;
|
|
@@ -249,6 +311,8 @@ export function createWorkerAgent(clientOpts) {
|
|
|
249
311
|
remoteAsk.set(runId, opts.onAsk);
|
|
250
312
|
remoteRunState.set(runId, {});
|
|
251
313
|
approvalRuns.set(runId, { context: opts.approvalContext, onSuggestion: opts.onApprovalSuggestion });
|
|
314
|
+
if (opts.sessionId)
|
|
315
|
+
mutationSessions.set(runId, opts.sessionId);
|
|
252
316
|
const audit = opts.audit ? startAudit(opts.audit, opts.model) : null;
|
|
253
317
|
if (audit)
|
|
254
318
|
auditRuns.set(runId, audit);
|
|
@@ -277,6 +341,7 @@ export function createWorkerAgent(clientOpts) {
|
|
|
277
341
|
remoteRunState.delete(runId);
|
|
278
342
|
approvalRuns.delete(runId);
|
|
279
343
|
auditRuns.delete(runId);
|
|
344
|
+
mutationSessions.delete(runId);
|
|
280
345
|
remoteAbort.abort(); // cancel any still-pending remote tool work
|
|
281
346
|
w.removeEventListener('message', onMessage);
|
|
282
347
|
opts.signal?.removeEventListener('abort', onAbort);
|
|
@@ -370,7 +435,8 @@ export function createWorkerAgent(clientOpts) {
|
|
|
370
435
|
// so the risk (LOCAL DISK vs virtual) is current, not frozen at run start.
|
|
371
436
|
const svc = clientOpts.getFileService?.() || null;
|
|
372
437
|
const summary = fileWriteSummary(m.tool, m.input, svc) ?? m.summary;
|
|
373
|
-
const
|
|
438
|
+
const input = permDetail(m.input);
|
|
439
|
+
const res = opts.onPermission ? await opts.onPermission({ tool: m.tool, summary, ...(m.callee ? { agent: m.callee } : {}), ...(input ? { input } : {}) }) : null;
|
|
374
440
|
/* Nobody to ask. The run itself answers as it always has (allow); a
|
|
375
441
|
* delegated callee is capped by the stricter of that and its OWN
|
|
376
442
|
* unattended mode, and with nobody to wait for, park is a deny. */
|
|
@@ -383,6 +449,22 @@ export function createWorkerAgent(clientOpts) {
|
|
|
383
449
|
send({ kind: 'permission-response', id: m.id, allow: answer.allow, by: answer.by, ...(note ? { note } : {}) });
|
|
384
450
|
return;
|
|
385
451
|
}
|
|
452
|
+
if (m.kind === 'hook-ask') {
|
|
453
|
+
// A System One check or hook asks the person, through the same
|
|
454
|
+
// handler as a permission ask (callees included), but with no
|
|
455
|
+
// unattended allow: see answerHookAsk.
|
|
456
|
+
const allow = await answerHookAsk(opts.onPermission, {
|
|
457
|
+
tool: HOOK_ASK_TOOL,
|
|
458
|
+
summary: m.reasons.join('\n'),
|
|
459
|
+
input: { tool: m.tool, reasons: m.reasons, ...(m.result === undefined ? {} : { result: m.result }) },
|
|
460
|
+
}, opts.signal);
|
|
461
|
+
send({ kind: 'hook-ask-response', id: m.id, allow });
|
|
462
|
+
return;
|
|
463
|
+
}
|
|
464
|
+
if (m.kind === 'tool-hooks') {
|
|
465
|
+
opts.onEvent?.({ type: 'tool-hooks', id: m.id, mark: m.mark, ...(m.blockedText === undefined ? {} : { blockedText: m.blockedText }) });
|
|
466
|
+
return;
|
|
467
|
+
}
|
|
386
468
|
if (m.kind === 'ask-request') {
|
|
387
469
|
const answers = opts.onAsk ? await opts.onAsk(m.questions) : null;
|
|
388
470
|
send({ kind: 'ask-response', id: m.id, answers });
|
|
@@ -392,6 +474,10 @@ export function createWorkerAgent(clientOpts) {
|
|
|
392
474
|
opts.onInjected?.(m.ids);
|
|
393
475
|
return;
|
|
394
476
|
}
|
|
477
|
+
if (m.kind === 'tool-check') {
|
|
478
|
+
opts.onEvent?.({ type: 'tool-check', id: m.id, name: m.name, check: m.check });
|
|
479
|
+
return;
|
|
480
|
+
}
|
|
395
481
|
if (m.kind === 'edit-review-request') {
|
|
396
482
|
// Without a reviewer wired, answer null immediately — the tool then
|
|
397
483
|
// reports "not reviewed" instead of suspending the run forever.
|
|
@@ -429,6 +515,9 @@ export function createWorkerAgent(clientOpts) {
|
|
|
429
515
|
w.addEventListener('message', onMessage);
|
|
430
516
|
opts.signal?.addEventListener('abort', onAbort, { once: true });
|
|
431
517
|
start(runId, send);
|
|
518
|
+
// An already-aborted signal never fires 'abort'.
|
|
519
|
+
if (opts.signal?.aborted)
|
|
520
|
+
onAbort();
|
|
432
521
|
});
|
|
433
522
|
}
|
|
434
523
|
return {
|
|
@@ -436,7 +525,7 @@ export function createWorkerAgent(clientOpts) {
|
|
|
436
525
|
return begin({ ...opts, audit: opts.auditContext ?? {} }, (runId, send) => {
|
|
437
526
|
alog('client:post-run', runId, { debug: isAgentLogging() });
|
|
438
527
|
const routing = clientOpts.getModelRouting?.();
|
|
439
|
-
send({ kind: 'run', runId, messages, model: opts.model, system: opts.system, policy: opts.policy, ceiling: opts.ceiling, compression: opts.compression, temperature: opts.temperature, debug: isAgentLogging(), fileMeta: currentFileMeta(), scope: getScope(), graphConfig: clientOpts.getGraphConfig?.(), reviewEdits: !!opts.onEditReview, editorFile: opts.editorFile, remoteTools: clientOpts.getRemoteTools?.() ?? [], sessionId: opts.sessionId, toolNames: opts.toolNames, toolDeny: opts.toolDeny, loadedTools: opts.loadedTools, skills: opts.skills, crewDelegates: opts.crewDelegates, crewOrchestration: opts.crewOrchestration, ...(opts.crewTraceRoot ? { crewTraceRoot: opts.crewTraceRoot } : {}), agentMemory: !!clientOpts.getMemoryProvider?.(), ...(opts.sessionsRoot !== undefined ? { sessionsRoot: opts.sessionsRoot } : {}), ...(opts.forceFold ? { forceFold: true } : {}), canMoveSession: !!opts.onMoveSession, ...(routing ? { routing } : {}) });
|
|
528
|
+
send({ kind: 'run', runId, messages, model: opts.model, system: opts.system, policy: opts.policy, ceiling: opts.ceiling, compression: opts.compression, temperature: opts.temperature, debug: isAgentLogging(), fileMeta: currentFileMeta(), scope: getScope(), graphConfig: clientOpts.getGraphConfig?.(), reviewEdits: !!opts.onEditReview, editorFile: opts.editorFile, remoteTools: clientOpts.getRemoteTools?.() ?? [], sessionId: opts.sessionId, toolNames: opts.toolNames, toolDeny: opts.toolDeny, loadedTools: opts.loadedTools, skills: opts.skills, crewDelegates: opts.crewDelegates, crewOrchestration: opts.crewOrchestration, ...(opts.crewTraceRoot ? { crewTraceRoot: opts.crewTraceRoot } : {}), agentMemory: !!clientOpts.getMemoryProvider?.(), ...(opts.sessionsRoot !== undefined ? { sessionsRoot: opts.sessionsRoot } : {}), ...(opts.forceFold ? { forceFold: true } : {}), canMoveSession: !!opts.onMoveSession, ...(routing ? { routing } : {}), ...systemOneRulesField() });
|
|
440
529
|
// WorkerAgentOpts/RunOpts have no `surface` concept yet -- every run
|
|
441
530
|
// through this client is the agent surface for now.
|
|
442
531
|
recorder.start(String(runId), { surface: 'agent', model: opts.model ?? '' });
|
|
@@ -447,7 +536,7 @@ export function createWorkerAgent(clientOpts) {
|
|
|
447
536
|
return begin(opts, (runId, send) => {
|
|
448
537
|
alog('client:post-run-node', runId, node.id, { debug: isAgentLogging() });
|
|
449
538
|
const routing = clientOpts.getModelRouting?.();
|
|
450
|
-
send({ kind: 'run-node', runId, node, inputs, model: opts.model, policy: opts.policy, ceiling: opts.ceiling, compression: opts.compression, debug: isAgentLogging(), fileMeta: currentFileMeta(), scope: getScope(), graphConfig: clientOpts.getGraphConfig?.(), remoteTools: clientOpts.getRemoteTools?.() ?? [], toolDeny: opts.toolDeny, agentMemory: !!clientOpts.getMemoryProvider?.(), ...(routing ? { routing } : {}) });
|
|
539
|
+
send({ kind: 'run-node', runId, node, inputs, model: opts.model, policy: opts.policy, ceiling: opts.ceiling, compression: opts.compression, debug: isAgentLogging(), fileMeta: currentFileMeta(), scope: getScope(), graphConfig: clientOpts.getGraphConfig?.(), remoteTools: clientOpts.getRemoteTools?.() ?? [], toolDeny: opts.toolDeny, agentMemory: !!clientOpts.getMemoryProvider?.(), ...(routing ? { routing } : {}), ...systemOneRulesField() });
|
|
451
540
|
}, (m, done) => { if (m.kind === 'node-result')
|
|
452
541
|
done(m.result); });
|
|
453
542
|
},
|