theokit 0.24.0 → 0.25.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/{agent-7474NDZD.js → agent-GXJNFW6N.js} +2 -2
- package/dist/{build-CVWAK4UE.js → build-WD2PT5TA.js} +2 -2
- package/dist/{chunk-FARW5PH6.js → chunk-2JNG3P4Y.js} +267 -21
- package/dist/chunk-2JNG3P4Y.js.map +1 -0
- package/dist/{chunk-IEA4O6ZN.js → chunk-GG6H76GC.js} +5 -3
- package/dist/chunk-GG6H76GC.js.map +1 -0
- package/dist/{chunk-ZGKGXXZG.js → chunk-LVGDYTU2.js} +2 -2
- package/dist/{chunk-VK553I55.js → chunk-S7L6H3KP.js} +264 -20
- package/dist/chunk-S7L6H3KP.js.map +1 -0
- package/dist/cli/index.js +5 -5
- package/dist/{dev-FSTYMPPF.js → dev-63UNEUF6.js} +3 -3
- package/dist/index.js +1 -1
- package/dist/{mcp-TOYHKCB6.js → mcp-MIZFVNCL.js} +2 -2
- package/dist/{start-LEDGWJF2.js → start-IFTLTEPZ.js} +5 -3
- package/dist/{start-LEDGWJF2.js.map → start-IFTLTEPZ.js.map} +1 -1
- package/dist/vite-plugin/index.js +1 -1
- package/dist/{vite-plugin-HSOWPMK4.js → vite-plugin-ST4JZQRJ.js} +3 -3
- package/package.json +1 -1
- package/dist/chunk-FARW5PH6.js.map +0 -1
- package/dist/chunk-IEA4O6ZN.js.map +0 -1
- package/dist/chunk-VK553I55.js.map +0 -1
- /package/dist/{agent-7474NDZD.js.map → agent-GXJNFW6N.js.map} +0 -0
- /package/dist/{build-CVWAK4UE.js.map → build-WD2PT5TA.js.map} +0 -0
- /package/dist/{chunk-ZGKGXXZG.js.map → chunk-LVGDYTU2.js.map} +0 -0
- /package/dist/{dev-FSTYMPPF.js.map → dev-63UNEUF6.js.map} +0 -0
- /package/dist/{mcp-TOYHKCB6.js.map → mcp-MIZFVNCL.js.map} +0 -0
- /package/dist/{vite-plugin-HSOWPMK4.js.map → vite-plugin-ST4JZQRJ.js.map} +0 -0
|
@@ -3,7 +3,7 @@ import "tsx/esm";
|
|
|
3
3
|
import {
|
|
4
4
|
agentCommand,
|
|
5
5
|
createAgentSsrLoader
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-LVGDYTU2.js";
|
|
7
7
|
import "./chunk-M6NMS5LR.js";
|
|
8
8
|
import "./chunk-GDN3PXFH.js";
|
|
9
9
|
import "./chunk-TERFLG67.js";
|
|
@@ -12,4 +12,4 @@ export {
|
|
|
12
12
|
agentCommand,
|
|
13
13
|
createAgentSsrLoader
|
|
14
14
|
};
|
|
15
|
-
//# sourceMappingURL=agent-
|
|
15
|
+
//# sourceMappingURL=agent-GXJNFW6N.js.map
|
|
@@ -531,7 +531,7 @@ async function buildCommand(options) {
|
|
|
531
531
|
`);
|
|
532
532
|
}
|
|
533
533
|
async function runAdapterBuild(target, config, cwd) {
|
|
534
|
-
const { theoPluginAsync } = await import("./vite-plugin-
|
|
534
|
+
const { theoPluginAsync } = await import("./vite-plugin-ST4JZQRJ.js");
|
|
535
535
|
const { default: react } = await import("@vitejs/plugin-react");
|
|
536
536
|
const ctx = {
|
|
537
537
|
// `react()` may return Plugin or Plugin[] depending on version; spread the
|
|
@@ -616,4 +616,4 @@ function relativize3(absPath, root) {
|
|
|
616
616
|
export {
|
|
617
617
|
buildCommand
|
|
618
618
|
};
|
|
619
|
-
//# sourceMappingURL=build-
|
|
619
|
+
//# sourceMappingURL=build-WD2PT5TA.js.map
|
|
@@ -1155,11 +1155,43 @@ function handleListApprovals(registry2) {
|
|
|
1155
1155
|
}
|
|
1156
1156
|
|
|
1157
1157
|
// src/server/agent/mount-agent.ts
|
|
1158
|
+
import { compileAgentModule as compileAgentModule3, resolveEnabledSkills as resolveEnabledSkills2, streamAgentUIMessages as streamAgentUIMessages2 } from "@theokit/agents";
|
|
1159
|
+
|
|
1160
|
+
// src/server/agent/build-agent-streamer.ts
|
|
1158
1161
|
import {
|
|
1159
1162
|
compileAgentModule as compileAgentModule2,
|
|
1160
1163
|
resolveEnabledSkills,
|
|
1161
1164
|
streamAgentUIMessages
|
|
1162
1165
|
} from "@theokit/agents";
|
|
1166
|
+
function buildAgentHitl(compiled) {
|
|
1167
|
+
const gated = compiled.hitl;
|
|
1168
|
+
if (gated === void 0 || gated.size === 0) return void 0;
|
|
1169
|
+
const registry2 = getApprovalRegistry();
|
|
1170
|
+
return {
|
|
1171
|
+
gated,
|
|
1172
|
+
awaitApproval: (approvalId, opts, toolName) => registry2.register(approvalId, {
|
|
1173
|
+
timeoutMs: opts.timeout ?? 3e5,
|
|
1174
|
+
onTimeout: opts.onTimeout ?? "abort",
|
|
1175
|
+
toolName,
|
|
1176
|
+
question: opts.question,
|
|
1177
|
+
...opts.payloadSchema !== void 0 ? { payloadSchema: opts.payloadSchema } : {}
|
|
1178
|
+
})
|
|
1179
|
+
};
|
|
1180
|
+
}
|
|
1181
|
+
function makeThreadStartRun(mod, apiKey, source) {
|
|
1182
|
+
return (sessionId, message) => (async function* () {
|
|
1183
|
+
const compiled = compileAgentModule2(mod, source);
|
|
1184
|
+
if (compiled.skillsResolver) {
|
|
1185
|
+
const enabled = await resolveEnabledSkills(
|
|
1186
|
+
compiled.skillsResolver,
|
|
1187
|
+
compiled.runContext ?? {}
|
|
1188
|
+
);
|
|
1189
|
+
if (enabled !== void 0) compiled.skills = { enabled, autoInject: true };
|
|
1190
|
+
}
|
|
1191
|
+
const hitl = buildAgentHitl(compiled);
|
|
1192
|
+
yield* streamAgentUIMessages(compiled, apiKey, { message, sessionId, hitl });
|
|
1193
|
+
})();
|
|
1194
|
+
}
|
|
1163
1195
|
|
|
1164
1196
|
// src/server/agent/durable-ui-message-stream-response.ts
|
|
1165
1197
|
var SSE_BASE_HEADERS = {
|
|
@@ -1216,6 +1248,9 @@ function createInMemoryRunEventCache(opts = {}) {
|
|
|
1216
1248
|
return buf;
|
|
1217
1249
|
}
|
|
1218
1250
|
return {
|
|
1251
|
+
begin(runId) {
|
|
1252
|
+
getOrCreate(runId);
|
|
1253
|
+
},
|
|
1219
1254
|
append(runId, data) {
|
|
1220
1255
|
const buf = getOrCreate(runId);
|
|
1221
1256
|
const seq = buf.frames.length;
|
|
@@ -1313,9 +1348,9 @@ async function mountAgent(mod, request, apiKey, source = "agent module", csrfMod
|
|
|
1313
1348
|
return jsonError2(403, "CSRF_FAILED", `CSRF check failed: ${csrf.reason}`);
|
|
1314
1349
|
}
|
|
1315
1350
|
}
|
|
1316
|
-
const compiled =
|
|
1351
|
+
const compiled = compileAgentModule3(mod, source);
|
|
1317
1352
|
if (compiled.skillsResolver) {
|
|
1318
|
-
const enabled = await
|
|
1353
|
+
const enabled = await resolveEnabledSkills2(compiled.skillsResolver, compiled.runContext ?? {});
|
|
1319
1354
|
if (enabled !== void 0) compiled.skills = { enabled, autoInject: true };
|
|
1320
1355
|
}
|
|
1321
1356
|
let body = null;
|
|
@@ -1327,23 +1362,10 @@ async function mountAgent(mod, request, apiKey, source = "agent module", csrfMod
|
|
|
1327
1362
|
if (input === null) {
|
|
1328
1363
|
return jsonError2(400, "BAD_REQUEST", "Request must contain a non-empty message or messages[].");
|
|
1329
1364
|
}
|
|
1330
|
-
const
|
|
1331
|
-
const registry2 = getApprovalRegistry();
|
|
1332
|
-
const hitl = gated && gated.size > 0 ? {
|
|
1333
|
-
gated,
|
|
1334
|
-
awaitApproval: (approvalId, opts, toolName) => registry2.register(approvalId, {
|
|
1335
|
-
timeoutMs: opts.timeout ?? 3e5,
|
|
1336
|
-
onTimeout: opts.onTimeout ?? "abort",
|
|
1337
|
-
// M14 — surface toolName + question in GET /approvals (the plugin forwards c.name).
|
|
1338
|
-
toolName,
|
|
1339
|
-
question: opts.question,
|
|
1340
|
-
// M20 — carry the declared custom-payload schema into GET /approvals.
|
|
1341
|
-
...opts.payloadSchema !== void 0 ? { payloadSchema: opts.payloadSchema } : {}
|
|
1342
|
-
})
|
|
1343
|
-
} : void 0;
|
|
1365
|
+
const hitl = buildAgentHitl(compiled);
|
|
1344
1366
|
const runId = mintRunId();
|
|
1345
1367
|
return durableUiMessageStreamResponse(
|
|
1346
|
-
|
|
1368
|
+
streamAgentUIMessages2(compiled, apiKey, { ...input, hitl, signal: request.signal }),
|
|
1347
1369
|
{ runId, cache: getRunEventCache() }
|
|
1348
1370
|
);
|
|
1349
1371
|
}
|
|
@@ -1459,13 +1481,202 @@ function handleAgentRunReconnect(runId, request, cache) {
|
|
|
1459
1481
|
return new Response(stream, { headers: { ...SSE_BASE_HEADERS, [RUN_ID_HEADER]: runId } });
|
|
1460
1482
|
}
|
|
1461
1483
|
|
|
1462
|
-
// src/server/agent/
|
|
1484
|
+
// src/server/agent/thread-dispatcher.ts
|
|
1485
|
+
function postThreadFollowUp(deps, sessionId, message) {
|
|
1486
|
+
if (deps.registry.getActive(sessionId) !== null) {
|
|
1487
|
+
deps.registry.queue(sessionId, { message });
|
|
1488
|
+
return { queued: true };
|
|
1489
|
+
}
|
|
1490
|
+
return { runId: startAndPump(deps, sessionId, message) };
|
|
1491
|
+
}
|
|
1492
|
+
function startAndPump(deps, sessionId, message) {
|
|
1493
|
+
const runId = mintRunId();
|
|
1494
|
+
deps.cache.begin(runId);
|
|
1495
|
+
deps.registry.startRun(sessionId, runId);
|
|
1496
|
+
pumpIntoCache(deps, sessionId, runId, deps.startRun(sessionId, message));
|
|
1497
|
+
return runId;
|
|
1498
|
+
}
|
|
1499
|
+
function pumpIntoCache(deps, sessionId, runId, chunks) {
|
|
1500
|
+
void (async () => {
|
|
1501
|
+
try {
|
|
1502
|
+
for await (const chunk of chunks) {
|
|
1503
|
+
deps.cache.append(runId, JSON.stringify(chunk));
|
|
1504
|
+
}
|
|
1505
|
+
} catch {
|
|
1506
|
+
} finally {
|
|
1507
|
+
deps.cache.end(runId);
|
|
1508
|
+
const next = deps.registry.endRun(sessionId, runId);
|
|
1509
|
+
if (next !== void 0) startAndPump(deps, sessionId, next.message);
|
|
1510
|
+
}
|
|
1511
|
+
})();
|
|
1512
|
+
}
|
|
1513
|
+
|
|
1514
|
+
// src/server/agent/thread-run-registry.ts
|
|
1515
|
+
function createInProcessThreadRunRegistry() {
|
|
1516
|
+
const threads = /* @__PURE__ */ new Map();
|
|
1517
|
+
const ensure = (sessionId) => {
|
|
1518
|
+
let s = threads.get(sessionId);
|
|
1519
|
+
if (s === void 0) {
|
|
1520
|
+
s = { activeRunId: null, queue: [], waiters: /* @__PURE__ */ new Set() };
|
|
1521
|
+
threads.set(sessionId, s);
|
|
1522
|
+
}
|
|
1523
|
+
return s;
|
|
1524
|
+
};
|
|
1525
|
+
return {
|
|
1526
|
+
getActive(sessionId) {
|
|
1527
|
+
return threads.get(sessionId)?.activeRunId ?? null;
|
|
1528
|
+
},
|
|
1529
|
+
startRun(sessionId, runId) {
|
|
1530
|
+
const s = ensure(sessionId);
|
|
1531
|
+
s.activeRunId = runId;
|
|
1532
|
+
const waiters = [...s.waiters];
|
|
1533
|
+
s.waiters.clear();
|
|
1534
|
+
for (const cb of waiters) cb(runId);
|
|
1535
|
+
},
|
|
1536
|
+
endRun(sessionId, runId) {
|
|
1537
|
+
const s = threads.get(sessionId);
|
|
1538
|
+
if (s?.activeRunId !== runId) return void 0;
|
|
1539
|
+
s.activeRunId = null;
|
|
1540
|
+
return s.queue.shift();
|
|
1541
|
+
},
|
|
1542
|
+
queue(sessionId, followUp) {
|
|
1543
|
+
ensure(sessionId).queue.push(followUp);
|
|
1544
|
+
},
|
|
1545
|
+
onNextRun(sessionId, cb) {
|
|
1546
|
+
const s = ensure(sessionId);
|
|
1547
|
+
s.waiters.add(cb);
|
|
1548
|
+
return () => {
|
|
1549
|
+
s.waiters.delete(cb);
|
|
1550
|
+
};
|
|
1551
|
+
}
|
|
1552
|
+
};
|
|
1553
|
+
}
|
|
1554
|
+
var serverRegistry2;
|
|
1555
|
+
function getThreadRunRegistry() {
|
|
1556
|
+
serverRegistry2 ??= createInProcessThreadRunRegistry();
|
|
1557
|
+
return serverRegistry2;
|
|
1558
|
+
}
|
|
1559
|
+
|
|
1560
|
+
// src/server/agent/handle-thread-routes.ts
|
|
1561
|
+
var THREAD_MESSAGE_PATH = /^\/api\/agents\/([^/]+)\/threads\/([^/]+)\/message$/;
|
|
1562
|
+
var THREAD_STREAM_PATH = /^\/api\/agents\/([^/]+)\/threads\/([^/]+)\/stream$/;
|
|
1563
|
+
var DEFAULT_IDLE_WAIT_MS = 3e4;
|
|
1564
|
+
function matchThread(re, urlPath) {
|
|
1565
|
+
const m = re.exec(urlPath);
|
|
1566
|
+
return m ? { name: decodeURIComponent(m[1]), sessionId: decodeURIComponent(m[2]) } : null;
|
|
1567
|
+
}
|
|
1568
|
+
var isThreadMessagePath = (urlPath) => matchThread(THREAD_MESSAGE_PATH, urlPath);
|
|
1569
|
+
var isThreadStreamPath = (urlPath) => matchThread(THREAD_STREAM_PATH, urlPath);
|
|
1463
1570
|
function jsonError3(status, code, message) {
|
|
1464
1571
|
return new Response(JSON.stringify({ error: { code, message } }), {
|
|
1465
1572
|
status,
|
|
1466
1573
|
headers: { "content-type": "application/json; charset=utf-8" }
|
|
1467
1574
|
});
|
|
1468
1575
|
}
|
|
1576
|
+
async function handleThreadMessage(args) {
|
|
1577
|
+
const { mod, apiKey, sessionId, request, source, csrfMode = "strict" } = args;
|
|
1578
|
+
if (csrfMode === "strict") {
|
|
1579
|
+
const csrf = validateCsrfRequest(request);
|
|
1580
|
+
if (!csrf.valid) return jsonError3(403, "CSRF_FAILED", `CSRF check failed: ${csrf.reason}`);
|
|
1581
|
+
}
|
|
1582
|
+
let body = null;
|
|
1583
|
+
try {
|
|
1584
|
+
body = await request.json();
|
|
1585
|
+
} catch {
|
|
1586
|
+
}
|
|
1587
|
+
const input = parseAgentRequestBody(body);
|
|
1588
|
+
if (input === null) {
|
|
1589
|
+
return jsonError3(400, "BAD_REQUEST", "Request must contain a non-empty message.");
|
|
1590
|
+
}
|
|
1591
|
+
const result = postThreadFollowUp(
|
|
1592
|
+
{
|
|
1593
|
+
registry: getThreadRunRegistry(),
|
|
1594
|
+
cache: getRunEventCache(),
|
|
1595
|
+
startRun: makeThreadStartRun(mod, apiKey, source)
|
|
1596
|
+
},
|
|
1597
|
+
sessionId,
|
|
1598
|
+
input.message
|
|
1599
|
+
);
|
|
1600
|
+
const headers = { "content-type": "application/json; charset=utf-8" };
|
|
1601
|
+
if ("runId" in result) headers[RUN_ID_HEADER] = result.runId;
|
|
1602
|
+
return new Response(JSON.stringify(result), { status: 202, headers });
|
|
1603
|
+
}
|
|
1604
|
+
function handleThreadStream(sessionId, request, registry2 = getThreadRunRegistry(), cache = getRunEventCache(), idleWaitMs = DEFAULT_IDLE_WAIT_MS) {
|
|
1605
|
+
const active = registry2.getActive(sessionId);
|
|
1606
|
+
if (active !== null && cache.has(active)) {
|
|
1607
|
+
return handleAgentRunReconnect(active, request, cache);
|
|
1608
|
+
}
|
|
1609
|
+
return waitThenAttachStream(sessionId, request, registry2, cache, idleWaitMs);
|
|
1610
|
+
}
|
|
1611
|
+
function waitThenAttachStream(sessionId, request, registry2, cache, idleWaitMs) {
|
|
1612
|
+
const stream = new ReadableStream({
|
|
1613
|
+
start(controller) {
|
|
1614
|
+
let closed = false;
|
|
1615
|
+
const send = (text) => {
|
|
1616
|
+
if (closed) return;
|
|
1617
|
+
try {
|
|
1618
|
+
controller.enqueue(encodeSse(text));
|
|
1619
|
+
} catch {
|
|
1620
|
+
}
|
|
1621
|
+
};
|
|
1622
|
+
let detachAttach;
|
|
1623
|
+
const close = () => {
|
|
1624
|
+
if (closed) return;
|
|
1625
|
+
send(SSE_DONE_FRAME);
|
|
1626
|
+
closed = true;
|
|
1627
|
+
try {
|
|
1628
|
+
controller.close();
|
|
1629
|
+
} catch {
|
|
1630
|
+
}
|
|
1631
|
+
};
|
|
1632
|
+
const offNext = registry2.onNextRun(sessionId, (runId) => {
|
|
1633
|
+
const res = cache.attach(
|
|
1634
|
+
runId,
|
|
1635
|
+
-1,
|
|
1636
|
+
(frame) => {
|
|
1637
|
+
send(formatSseFrame(frame.seq, frame.data));
|
|
1638
|
+
},
|
|
1639
|
+
() => {
|
|
1640
|
+
close();
|
|
1641
|
+
}
|
|
1642
|
+
);
|
|
1643
|
+
if (!res.known) {
|
|
1644
|
+
close();
|
|
1645
|
+
return;
|
|
1646
|
+
}
|
|
1647
|
+
for (const frame of res.replay) send(formatSseFrame(frame.seq, frame.data));
|
|
1648
|
+
if (res.ended) {
|
|
1649
|
+
close();
|
|
1650
|
+
return;
|
|
1651
|
+
}
|
|
1652
|
+
detachAttach = res.unsubscribe;
|
|
1653
|
+
});
|
|
1654
|
+
const teardownWaiter = () => {
|
|
1655
|
+
offNext();
|
|
1656
|
+
detachAttach?.();
|
|
1657
|
+
};
|
|
1658
|
+
const timer = setTimeout(() => {
|
|
1659
|
+
teardownWaiter();
|
|
1660
|
+
close();
|
|
1661
|
+
}, idleWaitMs);
|
|
1662
|
+
timer.unref();
|
|
1663
|
+
request.signal.addEventListener("abort", () => {
|
|
1664
|
+
teardownWaiter();
|
|
1665
|
+
clearTimeout(timer);
|
|
1666
|
+
close();
|
|
1667
|
+
});
|
|
1668
|
+
}
|
|
1669
|
+
});
|
|
1670
|
+
return new Response(stream, { headers: { ...SSE_BASE_HEADERS } });
|
|
1671
|
+
}
|
|
1672
|
+
|
|
1673
|
+
// src/server/agent/serve-aux-routes.ts
|
|
1674
|
+
function jsonError4(status, code, message) {
|
|
1675
|
+
return new Response(JSON.stringify({ error: { code, message } }), {
|
|
1676
|
+
status,
|
|
1677
|
+
headers: { "content-type": "application/json; charset=utf-8" }
|
|
1678
|
+
});
|
|
1679
|
+
}
|
|
1469
1680
|
async function serveAgentAuxRoute(request, urlPath, deps) {
|
|
1470
1681
|
const method = request.method.toUpperCase();
|
|
1471
1682
|
const cardName = isAgentCardPath(urlPath);
|
|
@@ -1486,12 +1697,45 @@ async function serveAgentAuxRoute(request, urlPath, deps) {
|
|
|
1486
1697
|
if (!deps.agents.some((a) => a.name === runStream.name)) return null;
|
|
1487
1698
|
return handleAgentRunReconnect(runStream.runId, request, getRunEventCache());
|
|
1488
1699
|
}
|
|
1700
|
+
const threadResponse = await serveThreadRoute(request, method, urlPath, deps);
|
|
1701
|
+
if (threadResponse !== null) return threadResponse;
|
|
1489
1702
|
const mcpName = isMcpPath(urlPath);
|
|
1490
1703
|
if (mcpName !== null) {
|
|
1491
1704
|
return serveMcpRoute(request, method, mcpName, deps);
|
|
1492
1705
|
}
|
|
1493
1706
|
return null;
|
|
1494
1707
|
}
|
|
1708
|
+
async function serveThreadRoute(request, method, urlPath, deps) {
|
|
1709
|
+
const stream = isThreadStreamPath(urlPath);
|
|
1710
|
+
if (stream !== null) {
|
|
1711
|
+
if (method !== "GET") return null;
|
|
1712
|
+
if (!deps.agents.some((a) => a.name === stream.name)) return null;
|
|
1713
|
+
return handleThreadStream(stream.sessionId, request);
|
|
1714
|
+
}
|
|
1715
|
+
const msg = isThreadMessagePath(urlPath);
|
|
1716
|
+
if (msg !== null) {
|
|
1717
|
+
if (method !== "POST") return null;
|
|
1718
|
+
const agent = deps.agents.find((a) => a.name === msg.name);
|
|
1719
|
+
if (!agent) return null;
|
|
1720
|
+
if (deps.resolveApiKey === void 0) {
|
|
1721
|
+
return jsonError4(
|
|
1722
|
+
501,
|
|
1723
|
+
"NOT_CONFIGURED",
|
|
1724
|
+
"Thread follow-up requires a provider API key (resolveApiKey was not provided to serveAgentAuxRoute)."
|
|
1725
|
+
);
|
|
1726
|
+
}
|
|
1727
|
+
const mod = await deps.loadModule(agent.filePath);
|
|
1728
|
+
return handleThreadMessage({
|
|
1729
|
+
mod,
|
|
1730
|
+
apiKey: deps.resolveApiKey(),
|
|
1731
|
+
sessionId: msg.sessionId,
|
|
1732
|
+
request,
|
|
1733
|
+
source: `agent "${msg.name}"`,
|
|
1734
|
+
csrfMode: deps.csrfMode ?? "strict"
|
|
1735
|
+
});
|
|
1736
|
+
}
|
|
1737
|
+
return null;
|
|
1738
|
+
}
|
|
1495
1739
|
async function serveMcpRoute(request, method, mcpName, deps) {
|
|
1496
1740
|
if (method !== "POST") return null;
|
|
1497
1741
|
const agent = deps.agents.find((a) => a.name === mcpName);
|
|
@@ -1501,7 +1745,7 @@ async function serveMcpRoute(request, method, mcpName, deps) {
|
|
|
1501
1745
|
const csrfMode = deps.csrfMode ?? "strict";
|
|
1502
1746
|
if (csrfMode === "strict") {
|
|
1503
1747
|
const csrf = validateCsrfRequest(request);
|
|
1504
|
-
if (!csrf.valid) return
|
|
1748
|
+
if (!csrf.valid) return jsonError4(403, "CSRF_FAILED", `CSRF check failed: ${csrf.reason}`);
|
|
1505
1749
|
}
|
|
1506
1750
|
let body = null;
|
|
1507
1751
|
try {
|
|
@@ -1635,7 +1879,9 @@ async function serveAux(req, res, next, urlPath, deps) {
|
|
|
1635
1879
|
agents: scanAgents(deps.projectRoot, deps.agentsDir),
|
|
1636
1880
|
loadModule: deps.loadModule,
|
|
1637
1881
|
baseUrl: `http://${req.headers.host ?? "localhost"}`,
|
|
1638
|
-
csrfMode: deps.csrfMode
|
|
1882
|
+
csrfMode: deps.csrfMode,
|
|
1883
|
+
// M39 — the thread follow-up route drives the agent; resolve the key on demand.
|
|
1884
|
+
resolveApiKey: () => resolveProvider().apiKey
|
|
1639
1885
|
});
|
|
1640
1886
|
if (response === null) {
|
|
1641
1887
|
next();
|
|
@@ -3291,4 +3537,4 @@ export {
|
|
|
3291
3537
|
theoPluginAsync,
|
|
3292
3538
|
theoPlugin
|
|
3293
3539
|
};
|
|
3294
|
-
//# sourceMappingURL=chunk-
|
|
3540
|
+
//# sourceMappingURL=chunk-2JNG3P4Y.js.map
|