poe-code 3.0.265 → 3.0.267
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/index.js +14 -5
- package/dist/index.js.map +2 -2
- package/dist/metafile.json +1 -1
- package/dist/providers/poe-agent.js +12 -3
- package/dist/providers/poe-agent.js.map +2 -2
- package/package.json +1 -1
- package/packages/acp-telemetry/dist/redact.js +7 -1
- package/packages/acp-telemetry/dist/trace.js +18 -16
- package/packages/agent-child-process/dist/index.d.ts +1 -1
- package/packages/agent-child-process/dist/index.js +60 -16
- package/packages/superintendent/dist/mcp.js +12 -3
- package/packages/superintendent/dist/mcp.js.map +2 -2
package/package.json
CHANGED
|
@@ -3,6 +3,9 @@ const MAX_JSON_BYTES = 262_144;
|
|
|
3
3
|
const BINARY_SCAN_BYTES = 1_024;
|
|
4
4
|
const REDACTED_SECRET = "[redacted]";
|
|
5
5
|
const BEARER_TOKEN_PATTERN = /\b(Bearer\s+)[A-Za-z0-9._~+/=-]+/gi;
|
|
6
|
+
const AUTH_HEADER_PATTERN = /\b((?:Proxy-)?Authorization\s*:\s*(?:Bearer|Basic|Token)\s+)[^\s"'\r\n]+/gi;
|
|
7
|
+
const COOKIE_HEADER_PATTERN = /\b((?:Set-)?Cookie\s*:\s*)[^\r\n"']+/gi;
|
|
8
|
+
const URL_USERINFO_PATTERN = /\b([A-Za-z][A-Za-z0-9+.-]*:\/\/)([^/?#\s@]+@)/g;
|
|
6
9
|
const ASSIGNED_SECRET_NAME_PATTERN = String.raw `(?:(?:[A-Za-z0-9]+[-_])*api[-_ ]?key|(?:[A-Za-z0-9]+[-_])*(?:token|secret|password|private[-_ ]?key))`;
|
|
7
10
|
const ASSIGNED_SECRET_PATTERN = new RegExp(String.raw `\b(${ASSIGNED_SECRET_NAME_PATTERN}\s*[:=]\s*)(?:"[^"\r\n]*"|'[^'\r\n]*'|[A-Za-z0-9._~+/=-]+)`, "gi");
|
|
8
11
|
export function redact(value) {
|
|
@@ -51,7 +54,7 @@ function redactLeaf(value, ancestors, key) {
|
|
|
51
54
|
configurable: true,
|
|
52
55
|
enumerable: true,
|
|
53
56
|
value: redactLeaf(item, ancestors, key),
|
|
54
|
-
writable: true
|
|
57
|
+
writable: true
|
|
55
58
|
});
|
|
56
59
|
}
|
|
57
60
|
ancestors.delete(value);
|
|
@@ -65,6 +68,9 @@ function redactString(value) {
|
|
|
65
68
|
return `[truncated:${bytes}]`;
|
|
66
69
|
}
|
|
67
70
|
return value
|
|
71
|
+
.replace(URL_USERINFO_PATTERN, `$1${REDACTED_SECRET}@`)
|
|
72
|
+
.replace(AUTH_HEADER_PATTERN, `$1${REDACTED_SECRET}`)
|
|
73
|
+
.replace(COOKIE_HEADER_PATTERN, `$1${REDACTED_SECRET}`)
|
|
68
74
|
.replace(BEARER_TOKEN_PATTERN, `$1${REDACTED_SECRET}`)
|
|
69
75
|
.replace(ASSIGNED_SECRET_PATTERN, redactAssignedSecretValue);
|
|
70
76
|
}
|
|
@@ -8,17 +8,17 @@ export function acpToTrace(ctx) {
|
|
|
8
8
|
input: redact({
|
|
9
9
|
prompt: ctx.prompt,
|
|
10
10
|
mode: ctx.mode,
|
|
11
|
-
cwd: ctx.cwd
|
|
11
|
+
cwd: ctx.cwd
|
|
12
12
|
}),
|
|
13
13
|
output: redact(accumulateAgentOutput(ctx.events)),
|
|
14
14
|
metadata: redactRecord({
|
|
15
15
|
...spawnCtx.metadata,
|
|
16
16
|
sessionId: ctx.sessionId,
|
|
17
|
-
threadId: ctx.threadId
|
|
17
|
+
threadId: ctx.threadId
|
|
18
18
|
}),
|
|
19
19
|
metrics: buildMetrics(ctx),
|
|
20
|
-
children: logToolSpans(ctx.events)
|
|
21
|
-
}
|
|
20
|
+
children: logToolSpans(ctx.events)
|
|
21
|
+
}
|
|
22
22
|
};
|
|
23
23
|
}
|
|
24
24
|
function logToolSpans(events) {
|
|
@@ -37,14 +37,14 @@ function logToolSpans(events) {
|
|
|
37
37
|
output: redact(assembleToolOutput(events, index, toolCallId)),
|
|
38
38
|
...(metadata ? { metadata } : {}),
|
|
39
39
|
...readSpanTimestamps(metadata),
|
|
40
|
-
children: []
|
|
40
|
+
children: []
|
|
41
41
|
});
|
|
42
42
|
}
|
|
43
43
|
return spans;
|
|
44
44
|
}
|
|
45
45
|
function collectToolMeta(events, toolCallIndex, toolCallId) {
|
|
46
46
|
const merged = {
|
|
47
|
-
...(toolCallId !== undefined ? { toolCallId } : {})
|
|
47
|
+
...(toolCallId !== undefined ? { toolCallId } : {})
|
|
48
48
|
};
|
|
49
49
|
const startMeta = asRecord(asRecord(events[toolCallIndex])?._meta);
|
|
50
50
|
if (startMeta) {
|
|
@@ -53,6 +53,9 @@ function collectToolMeta(events, toolCallIndex, toolCallId) {
|
|
|
53
53
|
}
|
|
54
54
|
}
|
|
55
55
|
for (const event of events.slice(toolCallIndex + 1)) {
|
|
56
|
+
if (toolCallId === undefined && asToolCall(event) !== undefined) {
|
|
57
|
+
break;
|
|
58
|
+
}
|
|
56
59
|
const update = asToolCallUpdate(event);
|
|
57
60
|
if (update === undefined)
|
|
58
61
|
continue;
|
|
@@ -91,6 +94,9 @@ function assembleToolOutput(events, toolCallIndex, toolCallId) {
|
|
|
91
94
|
const outputs = [];
|
|
92
95
|
let text = "";
|
|
93
96
|
for (const event of events.slice(toolCallIndex + 1)) {
|
|
97
|
+
if (toolCallId === undefined && asToolCall(event) !== undefined) {
|
|
98
|
+
break;
|
|
99
|
+
}
|
|
94
100
|
const update = asToolCallUpdate(event);
|
|
95
101
|
if (update === undefined) {
|
|
96
102
|
continue;
|
|
@@ -169,7 +175,7 @@ function readSpanTimestamps(metadata) {
|
|
|
169
175
|
const endTs = readNumber(metadata.endTs);
|
|
170
176
|
return {
|
|
171
177
|
...(startTs !== undefined ? { startTs } : {}),
|
|
172
|
-
...(endTs !== undefined ? { endTs } : {})
|
|
178
|
+
...(endTs !== undefined ? { endTs } : {})
|
|
173
179
|
};
|
|
174
180
|
}
|
|
175
181
|
function redactRecord(record) {
|
|
@@ -177,25 +183,21 @@ function redactRecord(record) {
|
|
|
177
183
|
return asRecord(redacted) ?? { redacted };
|
|
178
184
|
}
|
|
179
185
|
function asRecord(value) {
|
|
180
|
-
return typeof value === "object" && value !== null
|
|
181
|
-
? value
|
|
182
|
-
: undefined;
|
|
186
|
+
return typeof value === "object" && value !== null ? value : undefined;
|
|
183
187
|
}
|
|
184
188
|
function readString(value) {
|
|
185
189
|
return typeof value === "string" ? value : undefined;
|
|
186
190
|
}
|
|
187
191
|
function readNumber(value) {
|
|
188
|
-
return typeof value === "number" && Number.isFinite(value)
|
|
189
|
-
? value
|
|
190
|
-
: undefined;
|
|
192
|
+
return typeof value === "number" && Number.isFinite(value) ? value : undefined;
|
|
191
193
|
}
|
|
192
194
|
function addMetric(metrics, key, value) {
|
|
193
|
-
if (value !== undefined) {
|
|
195
|
+
if (value !== undefined && value >= 0) {
|
|
194
196
|
metrics[key] = value;
|
|
195
197
|
}
|
|
196
198
|
}
|
|
197
199
|
function sumIfPresent(left, right) {
|
|
198
|
-
if (left === undefined || right === undefined) {
|
|
200
|
+
if (left === undefined || right === undefined || left < 0 || right < 0) {
|
|
199
201
|
return undefined;
|
|
200
202
|
}
|
|
201
203
|
return readNumber(left + right);
|
|
@@ -205,6 +207,6 @@ function setOwnProperty(target, key, value) {
|
|
|
205
207
|
configurable: true,
|
|
206
208
|
enumerable: true,
|
|
207
209
|
value,
|
|
208
|
-
writable: true
|
|
210
|
+
writable: true
|
|
209
211
|
});
|
|
210
212
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import { type Readable, type Writable } from "node:stream";
|
|
2
2
|
import type { SpawnResult, SpawnUsage } from "../../agent-spawn/dist/index.js";
|
|
3
3
|
export type SpawnProcess = typeof import("node:child_process").spawn;
|
|
4
4
|
export type AgentChildProcessKind = "exec" | "execFile" | "spawn";
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { spawn as defaultSpawn } from "node:child_process";
|
|
2
|
+
import { PassThrough } from "node:stream";
|
|
2
3
|
import { StringDecoder } from "node:string_decoder";
|
|
3
4
|
export class AgentChildProcessError extends Error {
|
|
4
5
|
result;
|
|
@@ -9,7 +10,10 @@ export class AgentChildProcessError extends Error {
|
|
|
9
10
|
}
|
|
10
11
|
}
|
|
11
12
|
export async function exec(command, options) {
|
|
12
|
-
|
|
13
|
+
assertNonBlank(command, "command");
|
|
14
|
+
const shell = process.platform === "win32"
|
|
15
|
+
? (options?.env?.ComSpec ?? process.env.ComSpec ?? "cmd.exe")
|
|
16
|
+
: (options?.env?.SHELL ?? process.env.SHELL ?? "sh");
|
|
13
17
|
const shellArgs = process.platform === "win32" ? ["/d", "/s", "/c", command] : ["-c", command];
|
|
14
18
|
return runExecution({
|
|
15
19
|
kind: "exec",
|
|
@@ -21,6 +25,7 @@ export async function exec(command, options) {
|
|
|
21
25
|
});
|
|
22
26
|
}
|
|
23
27
|
export async function execFile(file, argsOrOptions = [], maybeOptions) {
|
|
28
|
+
assertNonBlank(file, "file");
|
|
24
29
|
const args = Array.isArray(argsOrOptions) ? argsOrOptions : [];
|
|
25
30
|
const options = Array.isArray(argsOrOptions) ? maybeOptions : argsOrOptions;
|
|
26
31
|
return runExecution({
|
|
@@ -33,10 +38,11 @@ export async function execFile(file, argsOrOptions = [], maybeOptions) {
|
|
|
33
38
|
});
|
|
34
39
|
}
|
|
35
40
|
export function spawn(file, argsOrOptions = [], maybeOptions) {
|
|
36
|
-
const args = Array.isArray(argsOrOptions) ? argsOrOptions : [];
|
|
37
|
-
const options = Array.isArray(argsOrOptions) ? maybeOptions : argsOrOptions;
|
|
38
41
|
let child;
|
|
39
42
|
try {
|
|
43
|
+
assertNonBlank(file, "file");
|
|
44
|
+
const args = Array.isArray(argsOrOptions) ? argsOrOptions : [];
|
|
45
|
+
const options = Array.isArray(argsOrOptions) ? maybeOptions : argsOrOptions;
|
|
40
46
|
child = startChildProcess({
|
|
41
47
|
kind: "spawn",
|
|
42
48
|
file,
|
|
@@ -59,8 +65,8 @@ export function spawn(file, argsOrOptions = [], maybeOptions) {
|
|
|
59
65
|
return {
|
|
60
66
|
pid: child.process.pid,
|
|
61
67
|
stdin: child.process.stdin,
|
|
62
|
-
stdout: child.
|
|
63
|
-
stderr: child.
|
|
68
|
+
stdout: child.stdout,
|
|
69
|
+
stderr: child.stderr,
|
|
64
70
|
kill(signal) {
|
|
65
71
|
return child.process.kill(signal);
|
|
66
72
|
},
|
|
@@ -72,8 +78,13 @@ async function runExecution(spec) {
|
|
|
72
78
|
}
|
|
73
79
|
function startChildProcess(spec) {
|
|
74
80
|
const child = spawnChild(spec);
|
|
75
|
-
const
|
|
76
|
-
|
|
81
|
+
const stdout = createOutputPipes(child.stdout, spec.kind === "spawn");
|
|
82
|
+
const stderr = createOutputPipes(child.stderr, spec.kind === "spawn");
|
|
83
|
+
const result = collectResult(child, spec, {
|
|
84
|
+
stdout: stdout.result,
|
|
85
|
+
stderr: stderr.result
|
|
86
|
+
}).then((commandResult) => applyExitPolicy(commandResult, spec.options));
|
|
87
|
+
return { process: child, stdout: stdout.user, stderr: stderr.user, result };
|
|
77
88
|
}
|
|
78
89
|
function spawnChild(spec) {
|
|
79
90
|
const options = spec.options;
|
|
@@ -89,22 +100,22 @@ function spawnChild(spec) {
|
|
|
89
100
|
function getStdio(kind) {
|
|
90
101
|
return kind === "spawn" ? ["pipe", "pipe", "pipe"] : ["ignore", "pipe", "pipe"];
|
|
91
102
|
}
|
|
92
|
-
function collectResult(child, spec) {
|
|
103
|
+
function collectResult(child, spec, streams) {
|
|
93
104
|
const stdoutDecoder = new StringDecoder("utf8");
|
|
94
105
|
const stderrDecoder = new StringDecoder("utf8");
|
|
95
106
|
let stdout = "";
|
|
96
107
|
let stderr = "";
|
|
97
108
|
let childClosed = false;
|
|
98
|
-
let stdoutFinished =
|
|
99
|
-
let stderrFinished =
|
|
109
|
+
let stdoutFinished = streams.stdout === null;
|
|
110
|
+
let stderrFinished = streams.stderr === null;
|
|
100
111
|
let exitCode = 1;
|
|
101
112
|
let exitSignal = null;
|
|
102
113
|
let processError;
|
|
103
114
|
let outputError;
|
|
104
|
-
|
|
115
|
+
streams.stdout?.on("data", (chunk) => {
|
|
105
116
|
stdout += typeof chunk === "string" ? chunk : stdoutDecoder.write(chunk);
|
|
106
117
|
});
|
|
107
|
-
|
|
118
|
+
streams.stderr?.on("data", (chunk) => {
|
|
108
119
|
stderr += typeof chunk === "string" ? chunk : stderrDecoder.write(chunk);
|
|
109
120
|
});
|
|
110
121
|
return new Promise((resolve) => {
|
|
@@ -127,20 +138,20 @@ function collectResult(child, spec) {
|
|
|
127
138
|
});
|
|
128
139
|
resolve({ ...attempt, attempts: [attempt] });
|
|
129
140
|
};
|
|
130
|
-
|
|
141
|
+
streams.stdout?.once("end", () => {
|
|
131
142
|
stdoutFinished = true;
|
|
132
143
|
finish();
|
|
133
144
|
});
|
|
134
|
-
|
|
145
|
+
streams.stderr?.once("end", () => {
|
|
135
146
|
stderrFinished = true;
|
|
136
147
|
finish();
|
|
137
148
|
});
|
|
138
|
-
|
|
149
|
+
streams.stdout?.once("error", (error) => {
|
|
139
150
|
outputError = error;
|
|
140
151
|
stdoutFinished = true;
|
|
141
152
|
finish();
|
|
142
153
|
});
|
|
143
|
-
|
|
154
|
+
streams.stderr?.once("error", (error) => {
|
|
144
155
|
outputError = error;
|
|
145
156
|
stderrFinished = true;
|
|
146
157
|
finish();
|
|
@@ -161,6 +172,22 @@ function collectResult(child, spec) {
|
|
|
161
172
|
});
|
|
162
173
|
});
|
|
163
174
|
}
|
|
175
|
+
function createOutputPipes(source, exposeUserStream) {
|
|
176
|
+
if (source === null) {
|
|
177
|
+
return { result: null, user: null };
|
|
178
|
+
}
|
|
179
|
+
const result = new PassThrough();
|
|
180
|
+
const user = exposeUserStream ? new PassThrough() : null;
|
|
181
|
+
source.once("error", (error) => {
|
|
182
|
+
result.destroy(error);
|
|
183
|
+
user?.destroy();
|
|
184
|
+
});
|
|
185
|
+
source.pipe(result);
|
|
186
|
+
if (user !== null) {
|
|
187
|
+
source.pipe(user);
|
|
188
|
+
}
|
|
189
|
+
return { result, user };
|
|
190
|
+
}
|
|
164
191
|
function createAttempt(spec, output) {
|
|
165
192
|
return {
|
|
166
193
|
kind: spec.kind,
|
|
@@ -195,6 +222,14 @@ async function maybeRunAgent(result, options) {
|
|
|
195
222
|
cause: error
|
|
196
223
|
});
|
|
197
224
|
}
|
|
225
|
+
try {
|
|
226
|
+
validateExitPolicy(policy);
|
|
227
|
+
}
|
|
228
|
+
catch (error) {
|
|
229
|
+
throw new AgentChildProcessError("Agent exit policy is invalid", result, {
|
|
230
|
+
cause: error
|
|
231
|
+
});
|
|
232
|
+
}
|
|
198
233
|
const runAgent = options.runAgent ?? defaultRunAgent;
|
|
199
234
|
let agentResult;
|
|
200
235
|
try {
|
|
@@ -225,6 +260,15 @@ async function maybeRunAgent(result, options) {
|
|
|
225
260
|
}
|
|
226
261
|
};
|
|
227
262
|
}
|
|
263
|
+
function validateExitPolicy(policy) {
|
|
264
|
+
assertNonBlank(policy.agent, "onExit.agent");
|
|
265
|
+
assertNonBlank(policy.prompt, "onExit.prompt");
|
|
266
|
+
}
|
|
267
|
+
function assertNonBlank(value, field) {
|
|
268
|
+
if (value.trim().length === 0) {
|
|
269
|
+
throw new TypeError(`${field} must not be empty`);
|
|
270
|
+
}
|
|
271
|
+
}
|
|
228
272
|
async function defaultRunAgent(input) {
|
|
229
273
|
const { spawn: spawnAgent } = await import("@poe-code/agent-spawn");
|
|
230
274
|
return spawnAgent(input.agent, {
|
|
@@ -41850,6 +41850,9 @@ var MAX_JSON_BYTES = 262144;
|
|
|
41850
41850
|
var BINARY_SCAN_BYTES = 1024;
|
|
41851
41851
|
var REDACTED_SECRET = "[redacted]";
|
|
41852
41852
|
var BEARER_TOKEN_PATTERN = /\b(Bearer\s+)[A-Za-z0-9._~+/=-]+/gi;
|
|
41853
|
+
var AUTH_HEADER_PATTERN = /\b((?:Proxy-)?Authorization\s*:\s*(?:Bearer|Basic|Token)\s+)[^\s"'\r\n]+/gi;
|
|
41854
|
+
var COOKIE_HEADER_PATTERN = /\b((?:Set-)?Cookie\s*:\s*)[^\r\n"']+/gi;
|
|
41855
|
+
var URL_USERINFO_PATTERN = /\b([A-Za-z][A-Za-z0-9+.-]*:\/\/)([^/?#\s@]+@)/g;
|
|
41853
41856
|
var ASSIGNED_SECRET_NAME_PATTERN = String.raw`(?:(?:[A-Za-z0-9]+[-_])*api[-_ ]?key|(?:[A-Za-z0-9]+[-_])*(?:token|secret|password|private[-_ ]?key))`;
|
|
41854
41857
|
var ASSIGNED_SECRET_PATTERN = new RegExp(
|
|
41855
41858
|
String.raw`\b(${ASSIGNED_SECRET_NAME_PATTERN}\s*[:=]\s*)(?:"[^"\r\n]*"|'[^'\r\n]*'|[A-Za-z0-9._~+/=-]+)`,
|
|
@@ -41914,7 +41917,7 @@ function redactString(value) {
|
|
|
41914
41917
|
if (bytes > MAX_STRING_BYTES) {
|
|
41915
41918
|
return `[truncated:${bytes}]`;
|
|
41916
41919
|
}
|
|
41917
|
-
return value.replace(BEARER_TOKEN_PATTERN, `$1${REDACTED_SECRET}`).replace(ASSIGNED_SECRET_PATTERN, redactAssignedSecretValue);
|
|
41920
|
+
return value.replace(URL_USERINFO_PATTERN, `$1${REDACTED_SECRET}@`).replace(AUTH_HEADER_PATTERN, `$1${REDACTED_SECRET}`).replace(COOKIE_HEADER_PATTERN, `$1${REDACTED_SECRET}`).replace(BEARER_TOKEN_PATTERN, `$1${REDACTED_SECRET}`).replace(ASSIGNED_SECRET_PATTERN, redactAssignedSecretValue);
|
|
41918
41921
|
}
|
|
41919
41922
|
function redactAssignedSecretValue(match, prefix) {
|
|
41920
41923
|
const secret = match.slice(prefix.length);
|
|
@@ -42000,6 +42003,9 @@ function collectToolMeta(events, toolCallIndex, toolCallId) {
|
|
|
42000
42003
|
}
|
|
42001
42004
|
}
|
|
42002
42005
|
for (const event of events.slice(toolCallIndex + 1)) {
|
|
42006
|
+
if (toolCallId === void 0 && asToolCall(event) !== void 0) {
|
|
42007
|
+
break;
|
|
42008
|
+
}
|
|
42003
42009
|
const update = asToolCallUpdate(event);
|
|
42004
42010
|
if (update === void 0) continue;
|
|
42005
42011
|
if (readToolCallId(update) !== toolCallId) continue;
|
|
@@ -42035,6 +42041,9 @@ function assembleToolOutput(events, toolCallIndex, toolCallId) {
|
|
|
42035
42041
|
const outputs = [];
|
|
42036
42042
|
let text4 = "";
|
|
42037
42043
|
for (const event of events.slice(toolCallIndex + 1)) {
|
|
42044
|
+
if (toolCallId === void 0 && asToolCall(event) !== void 0) {
|
|
42045
|
+
break;
|
|
42046
|
+
}
|
|
42038
42047
|
const update = asToolCallUpdate(event);
|
|
42039
42048
|
if (update === void 0) {
|
|
42040
42049
|
continue;
|
|
@@ -42138,12 +42147,12 @@ function readNumber(value) {
|
|
|
42138
42147
|
return typeof value === "number" && Number.isFinite(value) ? value : void 0;
|
|
42139
42148
|
}
|
|
42140
42149
|
function addMetric(metrics, key2, value) {
|
|
42141
|
-
if (value !== void 0) {
|
|
42150
|
+
if (value !== void 0 && value >= 0) {
|
|
42142
42151
|
metrics[key2] = value;
|
|
42143
42152
|
}
|
|
42144
42153
|
}
|
|
42145
42154
|
function sumIfPresent(left, right) {
|
|
42146
|
-
if (left === void 0 || right === void 0) {
|
|
42155
|
+
if (left === void 0 || right === void 0 || left < 0 || right < 0) {
|
|
42147
42156
|
return void 0;
|
|
42148
42157
|
}
|
|
42149
42158
|
return readNumber(left + right);
|