@alexkroman1/aai 0.7.11 → 0.8.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/README.md +1 -1
- package/dist/aai.js +1 -1
- package/dist/cli.js +693 -349
- package/dist/sdk/_internal_types.d.ts +0 -1
- package/dist/sdk/_internal_types.d.ts.map +1 -1
- package/dist/sdk/_internal_types.js.map +1 -1
- package/dist/sdk/_render_check.d.ts +7 -0
- package/dist/sdk/_render_check.d.ts.map +1 -0
- package/dist/sdk/_render_check.js +38 -0
- package/dist/sdk/_render_check.js.map +1 -0
- package/dist/sdk/builtin_tools.d.ts.map +1 -1
- package/dist/sdk/builtin_tools.js +21 -0
- package/dist/sdk/builtin_tools.js.map +1 -1
- package/dist/sdk/define_agent.d.ts.map +1 -1
- package/dist/sdk/define_agent.js +0 -1
- package/dist/sdk/define_agent.js.map +1 -1
- package/dist/sdk/direct_executor.d.ts.map +1 -1
- package/dist/sdk/direct_executor.js +0 -1
- package/dist/sdk/direct_executor.js.map +1 -1
- package/dist/sdk/memory_tools.d.ts +38 -0
- package/dist/sdk/memory_tools.d.ts.map +1 -0
- package/dist/sdk/memory_tools.js +77 -0
- package/dist/sdk/memory_tools.js.map +1 -0
- package/dist/sdk/mod.d.ts +3 -1
- package/dist/sdk/mod.d.ts.map +1 -1
- package/dist/sdk/mod.js +2 -0
- package/dist/sdk/mod.js.map +1 -1
- package/dist/sdk/protocol.d.ts +9 -3
- package/dist/sdk/protocol.d.ts.map +1 -1
- package/dist/sdk/protocol.js +2 -1
- package/dist/sdk/protocol.js.map +1 -1
- package/dist/sdk/s2s.d.ts.map +1 -1
- package/dist/sdk/s2s.js +9 -3
- package/dist/sdk/s2s.js.map +1 -1
- package/dist/sdk/session.d.ts.map +1 -1
- package/dist/sdk/session.js +5 -0
- package/dist/sdk/session.js.map +1 -1
- package/dist/sdk/types.d.ts +23 -14
- package/dist/sdk/types.d.ts.map +1 -1
- package/dist/sdk/types.js +29 -0
- package/dist/sdk/types.js.map +1 -1
- package/dist/ui/_components/app.d.ts.map +1 -1
- package/dist/ui/_components/app.js +6 -7
- package/dist/ui/_components/app.js.map +1 -1
- package/dist/ui/_components/message_list.d.ts.map +1 -1
- package/dist/ui/_components/message_list.js +2 -1
- package/dist/ui/_components/message_list.js.map +1 -1
- package/dist/ui/_components/sidebar_layout.d.ts +19 -0
- package/dist/ui/_components/sidebar_layout.d.ts.map +1 -0
- package/dist/ui/_components/sidebar_layout.js +21 -0
- package/dist/ui/_components/sidebar_layout.js.map +1 -0
- package/dist/ui/_components/start_screen.d.ts +24 -0
- package/dist/ui/_components/start_screen.d.ts.map +1 -0
- package/dist/ui/_components/start_screen.js +25 -0
- package/dist/ui/_components/start_screen.js.map +1 -0
- package/dist/ui/_hooks.d.ts +21 -0
- package/dist/ui/_hooks.d.ts.map +1 -0
- package/dist/ui/_hooks.js +35 -0
- package/dist/ui/_hooks.js.map +1 -0
- package/dist/ui/components.d.ts +20 -0
- package/dist/ui/components.d.ts.map +1 -1
- package/dist/ui/components.js +12 -0
- package/dist/ui/components.js.map +1 -1
- package/dist/ui/components_mod.d.ts +3 -2
- package/dist/ui/components_mod.d.ts.map +1 -1
- package/dist/ui/components_mod.js +3 -2
- package/dist/ui/components_mod.js.map +1 -1
- package/dist/ui/mod.d.ts +4 -3
- package/dist/ui/mod.d.ts.map +1 -1
- package/dist/ui/mod.js +3 -2
- package/dist/ui/mod.js.map +1 -1
- package/dist/ui/session.d.ts +7 -0
- package/dist/ui/session.d.ts.map +1 -1
- package/dist/ui/session.js +21 -3
- package/dist/ui/session.js.map +1 -1
- package/dist/ui/signals.d.ts +14 -0
- package/dist/ui/signals.d.ts.map +1 -1
- package/dist/ui/signals.js +55 -3
- package/dist/ui/signals.js.map +1 -1
- package/package.json +19 -2
- package/templates/_shared/CLAUDE.md +305 -116
- package/templates/_shared/package.json +4 -1
- package/templates/dispatch-center/agent.ts +43 -72
- package/templates/embedded-assets/agent.ts +4 -5
- package/templates/health-assistant/agent.ts +7 -7
- package/templates/infocom-adventure/agent.ts +20 -20
- package/templates/memory-agent/agent.ts +1 -55
- package/templates/night-owl/agent.ts +4 -4
- package/templates/night-owl/client.tsx +6 -23
- package/templates/pizza-ordering/agent.ts +214 -0
- package/templates/pizza-ordering/client.tsx +264 -0
- package/templates/smart-research/agent.ts +10 -10
package/dist/cli.js
CHANGED
|
@@ -21,6 +21,16 @@ var COLORS;
|
|
|
21
21
|
var init_colors = __esm({
|
|
22
22
|
"cli/_colors.ts"() {
|
|
23
23
|
"use strict";
|
|
24
|
+
if (chalk.level === 0 && !process.env.NO_COLOR) {
|
|
25
|
+
const ct = process.env.COLORTERM;
|
|
26
|
+
if (ct === "truecolor" || ct === "24bit") {
|
|
27
|
+
chalk.level = 3;
|
|
28
|
+
} else if (ct || /-256(color)?$/i.test(process.env.TERM ?? "")) {
|
|
29
|
+
chalk.level = 2;
|
|
30
|
+
} else if (process.env.TERM_PROGRAM) {
|
|
31
|
+
chalk.level = 1;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
24
34
|
COLORS = {
|
|
25
35
|
primary: "#fab283",
|
|
26
36
|
interactive: "#56b6c2",
|
|
@@ -52,10 +62,11 @@ function rootHelp(version) {
|
|
|
52
62
|
const cmds = [
|
|
53
63
|
["init", "[dir]", "Scaffold a new agent project"],
|
|
54
64
|
["dev", "", "Start a local development server"],
|
|
65
|
+
["build", "", "Bundle and validate (no server or deploy)"],
|
|
55
66
|
["deploy", "", "Bundle and deploy to production"],
|
|
56
67
|
["start", "", "Start production server from build"],
|
|
57
68
|
["secret", "<cmd>", "Manage secrets"],
|
|
58
|
-
["rag", "<url>", "Ingest a site
|
|
69
|
+
["rag", "<url>", "Ingest a site into the vector store"]
|
|
59
70
|
];
|
|
60
71
|
for (const [name, args, desc] of cmds) {
|
|
61
72
|
const nameStr = interactive(name.padEnd(8));
|
|
@@ -78,15 +89,9 @@ function rootHelp(version) {
|
|
|
78
89
|
lines.push("");
|
|
79
90
|
lines.push(` ${chalk2.bold(interactive("Getting started"))}`);
|
|
80
91
|
lines.push("");
|
|
81
|
-
lines.push(
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
)}`
|
|
85
|
-
);
|
|
86
|
-
lines.push(` ${chalk2.dim("$")} ${primary("cd my-agent")}`);
|
|
87
|
-
lines.push(
|
|
88
|
-
` ${chalk2.dim("$")} ${primary("aai deploy")} ${chalk2.dim("Deploy to production")}`
|
|
89
|
-
);
|
|
92
|
+
lines.push(` ${chalk2.dim("$")} ${primary("aai init")} ${interactive("my-agent")}`);
|
|
93
|
+
lines.push(` ${chalk2.dim("$")} ${primary("cd")} ${interactive("my-agent")}`);
|
|
94
|
+
lines.push(` ${chalk2.dim("$")} ${primary("aai dev")}`);
|
|
90
95
|
lines.push("");
|
|
91
96
|
return lines.join("\n");
|
|
92
97
|
}
|
|
@@ -273,6 +278,7 @@ async function askText(message, defaultValue) {
|
|
|
273
278
|
onSubmit: (value) => {
|
|
274
279
|
resolve(value || defaultValue);
|
|
275
280
|
app.unmount();
|
|
281
|
+
app.clear();
|
|
276
282
|
}
|
|
277
283
|
}
|
|
278
284
|
)
|
|
@@ -415,57 +421,6 @@ var init_discover = __esm({
|
|
|
415
421
|
}
|
|
416
422
|
});
|
|
417
423
|
|
|
418
|
-
// cli/_deploy.ts
|
|
419
|
-
async function attemptDeploy(url, slug, apiKey, env, worker, clientFiles) {
|
|
420
|
-
return await _internals.fetch(`${url}/${slug}/deploy`, {
|
|
421
|
-
method: "POST",
|
|
422
|
-
headers: {
|
|
423
|
-
"Content-Type": "application/json",
|
|
424
|
-
Authorization: `Bearer ${apiKey}`
|
|
425
|
-
},
|
|
426
|
-
body: JSON.stringify({
|
|
427
|
-
env,
|
|
428
|
-
worker,
|
|
429
|
-
clientFiles
|
|
430
|
-
})
|
|
431
|
-
});
|
|
432
|
-
}
|
|
433
|
-
async function runDeploy(opts) {
|
|
434
|
-
const worker = opts.bundle.worker;
|
|
435
|
-
const clientFiles = opts.bundle.clientFiles;
|
|
436
|
-
let slug = opts.slug;
|
|
437
|
-
if (opts.dryRun) {
|
|
438
|
-
return { slug };
|
|
439
|
-
}
|
|
440
|
-
for (let i = 0; i < MAX_RETRIES; i++) {
|
|
441
|
-
const resp = await attemptDeploy(opts.url, slug, opts.apiKey, opts.env, worker, clientFiles);
|
|
442
|
-
if (resp.ok) {
|
|
443
|
-
return { slug };
|
|
444
|
-
}
|
|
445
|
-
if (resp.status === 403) {
|
|
446
|
-
const text2 = await resp.text();
|
|
447
|
-
if (text2.includes("Slug")) {
|
|
448
|
-
slug = generateSlug();
|
|
449
|
-
continue;
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
const text = await resp.text();
|
|
453
|
-
throw new Error(`deploy failed (${resp.status}): ${text}`);
|
|
454
|
-
}
|
|
455
|
-
throw new Error(`deploy failed: could not find available slug after ${MAX_RETRIES} attempts`);
|
|
456
|
-
}
|
|
457
|
-
var _internals, MAX_RETRIES;
|
|
458
|
-
var init_deploy = __esm({
|
|
459
|
-
"cli/_deploy.ts"() {
|
|
460
|
-
"use strict";
|
|
461
|
-
init_discover();
|
|
462
|
-
_internals = {
|
|
463
|
-
fetch: globalThis.fetch.bind(globalThis)
|
|
464
|
-
};
|
|
465
|
-
MAX_RETRIES = 20;
|
|
466
|
-
}
|
|
467
|
-
});
|
|
468
|
-
|
|
469
424
|
// cli/_ink.tsx
|
|
470
425
|
import { Spinner } from "@inkjs/ui";
|
|
471
426
|
import { Box as Box2, render as render2, Static, Text as Text2, useApp } from "ink";
|
|
@@ -490,14 +445,20 @@ function StepInfo({ action, msg }) {
|
|
|
490
445
|
] });
|
|
491
446
|
}
|
|
492
447
|
function Info({ msg }) {
|
|
493
|
-
return /* @__PURE__ */
|
|
448
|
+
return /* @__PURE__ */ jsxs2(Text2, { dimColor: true, children: [
|
|
449
|
+
" ",
|
|
450
|
+
msg
|
|
451
|
+
] });
|
|
494
452
|
}
|
|
495
453
|
function Detail({ msg }) {
|
|
496
|
-
return /* @__PURE__ */
|
|
454
|
+
return /* @__PURE__ */ jsxs2(Text2, { children: [
|
|
455
|
+
" ",
|
|
456
|
+
msg
|
|
457
|
+
] });
|
|
497
458
|
}
|
|
498
459
|
function Warn({ msg }) {
|
|
499
460
|
return /* @__PURE__ */ jsxs2(Text2, { children: [
|
|
500
|
-
/* @__PURE__ */ jsx2(Text2, { bold: true, color: COLORS.warning, children: "
|
|
461
|
+
/* @__PURE__ */ jsx2(Text2, { bold: true, color: COLORS.warning, children: "\u25B2" }),
|
|
501
462
|
/* @__PURE__ */ jsxs2(Text2, { children: [
|
|
502
463
|
" ",
|
|
503
464
|
msg
|
|
@@ -506,9 +467,9 @@ function Warn({ msg }) {
|
|
|
506
467
|
}
|
|
507
468
|
function ErrorLine({ msg }) {
|
|
508
469
|
return /* @__PURE__ */ jsxs2(Text2, { children: [
|
|
509
|
-
/* @__PURE__ */ jsx2(Text2, { bold: true, color: COLORS.error, children: "
|
|
470
|
+
/* @__PURE__ */ jsx2(Text2, { bold: true, color: COLORS.error, children: "\u2717" }),
|
|
510
471
|
/* @__PURE__ */ jsxs2(Text2, { children: [
|
|
511
|
-
"
|
|
472
|
+
" ",
|
|
512
473
|
msg
|
|
513
474
|
] })
|
|
514
475
|
] });
|
|
@@ -587,7 +548,7 @@ async function runWithInk(fn) {
|
|
|
587
548
|
)
|
|
588
549
|
);
|
|
589
550
|
await app.waitUntilExit();
|
|
590
|
-
if (thrownError)
|
|
551
|
+
if (thrownError) process.exit(1);
|
|
591
552
|
}
|
|
592
553
|
var init_ink = __esm({
|
|
593
554
|
"cli/_ink.tsx"() {
|
|
@@ -596,6 +557,244 @@ var init_ink = __esm({
|
|
|
596
557
|
}
|
|
597
558
|
});
|
|
598
559
|
|
|
560
|
+
// ui/_dom_shim.ts
|
|
561
|
+
import { DOMParser } from "linkedom";
|
|
562
|
+
function installDomShim() {
|
|
563
|
+
if (installed) return;
|
|
564
|
+
installed = true;
|
|
565
|
+
const doc = new DOMParser().parseFromString(
|
|
566
|
+
"<!DOCTYPE html><html><head></head><body></body></html>",
|
|
567
|
+
"text/html"
|
|
568
|
+
);
|
|
569
|
+
const g2 = globalThis;
|
|
570
|
+
g2.document = doc;
|
|
571
|
+
g2.HTMLElement = doc.documentElement.constructor;
|
|
572
|
+
if (!Object.getOwnPropertyDescriptor(
|
|
573
|
+
g2.HTMLElement.prototype,
|
|
574
|
+
"scrollIntoView"
|
|
575
|
+
)) {
|
|
576
|
+
g2.HTMLElement.prototype.scrollIntoView = () => {
|
|
577
|
+
};
|
|
578
|
+
}
|
|
579
|
+
}
|
|
580
|
+
var installed;
|
|
581
|
+
var init_dom_shim = __esm({
|
|
582
|
+
"ui/_dom_shim.ts"() {
|
|
583
|
+
"use strict";
|
|
584
|
+
installed = false;
|
|
585
|
+
}
|
|
586
|
+
});
|
|
587
|
+
|
|
588
|
+
// sdk/_mock_ws.ts
|
|
589
|
+
function installMockWebSocket() {
|
|
590
|
+
const saved = globalThis.WebSocket;
|
|
591
|
+
const created = [];
|
|
592
|
+
g.WebSocket = class extends MockWebSocket {
|
|
593
|
+
constructor(url, protocols) {
|
|
594
|
+
super(url, protocols);
|
|
595
|
+
created.push(this);
|
|
596
|
+
}
|
|
597
|
+
};
|
|
598
|
+
return {
|
|
599
|
+
created,
|
|
600
|
+
get lastWs() {
|
|
601
|
+
return created.at(-1) ?? null;
|
|
602
|
+
},
|
|
603
|
+
restore() {
|
|
604
|
+
globalThis.WebSocket = saved;
|
|
605
|
+
},
|
|
606
|
+
[Symbol.dispose]() {
|
|
607
|
+
globalThis.WebSocket = saved;
|
|
608
|
+
}
|
|
609
|
+
};
|
|
610
|
+
}
|
|
611
|
+
var MockWebSocket, g;
|
|
612
|
+
var init_mock_ws = __esm({
|
|
613
|
+
"sdk/_mock_ws.ts"() {
|
|
614
|
+
"use strict";
|
|
615
|
+
MockWebSocket = class _MockWebSocket extends EventTarget {
|
|
616
|
+
// mirrors the WebSocket API
|
|
617
|
+
static CONNECTING = 0;
|
|
618
|
+
// mirrors the WebSocket API
|
|
619
|
+
static OPEN = 1;
|
|
620
|
+
// mirrors the WebSocket API
|
|
621
|
+
static CLOSING = 2;
|
|
622
|
+
// mirrors the WebSocket API
|
|
623
|
+
static CLOSED = 3;
|
|
624
|
+
readyState = _MockWebSocket.CONNECTING;
|
|
625
|
+
binaryType = "arraybuffer";
|
|
626
|
+
/** All messages passed to {@linkcode send}, in order. */
|
|
627
|
+
sent = [];
|
|
628
|
+
url;
|
|
629
|
+
/**
|
|
630
|
+
* Create a new MockWebSocket.
|
|
631
|
+
*
|
|
632
|
+
* Automatically transitions to `OPEN` state on the next microtask,
|
|
633
|
+
* dispatching an `"open"` event.
|
|
634
|
+
*
|
|
635
|
+
* @param url - The WebSocket URL.
|
|
636
|
+
* @param _protocols - Ignored; accepted for API compatibility.
|
|
637
|
+
*/
|
|
638
|
+
constructor(url, _protocols) {
|
|
639
|
+
super();
|
|
640
|
+
this.url = typeof url === "string" ? url : url.toString();
|
|
641
|
+
queueMicrotask(() => {
|
|
642
|
+
if (this.readyState === _MockWebSocket.CONNECTING) {
|
|
643
|
+
this.readyState = _MockWebSocket.OPEN;
|
|
644
|
+
this.dispatchEvent(new Event("open"));
|
|
645
|
+
}
|
|
646
|
+
});
|
|
647
|
+
}
|
|
648
|
+
/**
|
|
649
|
+
* Record a sent message without transmitting it.
|
|
650
|
+
*
|
|
651
|
+
* @param data - The message data to record.
|
|
652
|
+
*/
|
|
653
|
+
send(data) {
|
|
654
|
+
this.sent.push(data);
|
|
655
|
+
}
|
|
656
|
+
/**
|
|
657
|
+
* Transition to `CLOSED` state and dispatch a `"close"` event.
|
|
658
|
+
*
|
|
659
|
+
* @param code - The close code (defaults to 1000).
|
|
660
|
+
* @param _reason - Ignored; accepted for API compatibility.
|
|
661
|
+
*/
|
|
662
|
+
close(code, _reason) {
|
|
663
|
+
this.readyState = _MockWebSocket.CLOSED;
|
|
664
|
+
this.dispatchEvent(new CloseEvent("close", { code: code ?? 1e3 }));
|
|
665
|
+
}
|
|
666
|
+
/**
|
|
667
|
+
* Simulate receiving a message from the server.
|
|
668
|
+
*
|
|
669
|
+
* @param data - The message data (string or binary).
|
|
670
|
+
*/
|
|
671
|
+
simulateMessage(data) {
|
|
672
|
+
this.dispatchEvent(new MessageEvent("message", { data }));
|
|
673
|
+
}
|
|
674
|
+
/** Transition to `OPEN` state and dispatch an `"open"` event. */
|
|
675
|
+
open() {
|
|
676
|
+
this.readyState = _MockWebSocket.OPEN;
|
|
677
|
+
this.dispatchEvent(new Event("open"));
|
|
678
|
+
}
|
|
679
|
+
/**
|
|
680
|
+
* Shorthand for {@linkcode simulateMessage}.
|
|
681
|
+
*
|
|
682
|
+
* @param data - The message data to dispatch.
|
|
683
|
+
*/
|
|
684
|
+
msg(data) {
|
|
685
|
+
this.dispatchEvent(new MessageEvent("message", { data }));
|
|
686
|
+
}
|
|
687
|
+
/**
|
|
688
|
+
* Simulate a connection close from the server.
|
|
689
|
+
*
|
|
690
|
+
* @param code - The close code (defaults to 1000).
|
|
691
|
+
*/
|
|
692
|
+
disconnect(code = 1e3) {
|
|
693
|
+
this.dispatchEvent(new CloseEvent("close", { code }));
|
|
694
|
+
}
|
|
695
|
+
/** Dispatch an `"error"` event on this socket. */
|
|
696
|
+
error() {
|
|
697
|
+
this.dispatchEvent(new Event("error"));
|
|
698
|
+
}
|
|
699
|
+
/**
|
|
700
|
+
* Return all sent string messages parsed as JSON objects.
|
|
701
|
+
*
|
|
702
|
+
* Binary messages are filtered out.
|
|
703
|
+
*
|
|
704
|
+
* @returns An array of parsed JSON objects from sent string messages.
|
|
705
|
+
*/
|
|
706
|
+
sentJson() {
|
|
707
|
+
return this.sent.filter((d) => typeof d === "string").map((s) => JSON.parse(s));
|
|
708
|
+
}
|
|
709
|
+
};
|
|
710
|
+
g = globalThis;
|
|
711
|
+
}
|
|
712
|
+
});
|
|
713
|
+
|
|
714
|
+
// sdk/_render_check.ts
|
|
715
|
+
var render_check_exports = {};
|
|
716
|
+
__export(render_check_exports, {
|
|
717
|
+
renderCheck: () => renderCheck
|
|
718
|
+
});
|
|
719
|
+
import { createServer as createViteServer } from "vite";
|
|
720
|
+
async function renderCheck(clientEntry, cwd) {
|
|
721
|
+
installDomShim();
|
|
722
|
+
const g2 = globalThis;
|
|
723
|
+
const doc = new DOMParser().parseFromString(
|
|
724
|
+
'<!DOCTYPE html><html><head></head><body><main id="app"></main></body></html>',
|
|
725
|
+
"text/html"
|
|
726
|
+
);
|
|
727
|
+
const prevDoc = g2.document;
|
|
728
|
+
const prevLocation = g2.location;
|
|
729
|
+
g2.document = doc;
|
|
730
|
+
g2.location = { origin: "http://localhost:3000", pathname: "/", href: "http://localhost:3000/" };
|
|
731
|
+
const mock = installMockWebSocket();
|
|
732
|
+
const vite = await createViteServer({
|
|
733
|
+
root: cwd,
|
|
734
|
+
logLevel: "silent",
|
|
735
|
+
server: { middlewareMode: true }
|
|
736
|
+
});
|
|
737
|
+
try {
|
|
738
|
+
await vite.ssrLoadModule(clientEntry);
|
|
739
|
+
const app = doc.querySelector("#app");
|
|
740
|
+
if (!app?.innerHTML) {
|
|
741
|
+
throw new Error("client.tsx render check failed: #app is empty after mount()");
|
|
742
|
+
}
|
|
743
|
+
} finally {
|
|
744
|
+
await vite.close();
|
|
745
|
+
mock.restore();
|
|
746
|
+
g2.document = prevDoc;
|
|
747
|
+
g2.location = prevLocation;
|
|
748
|
+
}
|
|
749
|
+
}
|
|
750
|
+
var init_render_check = __esm({
|
|
751
|
+
"sdk/_render_check.ts"() {
|
|
752
|
+
"use strict";
|
|
753
|
+
init_dom_shim();
|
|
754
|
+
init_mock_ws();
|
|
755
|
+
}
|
|
756
|
+
});
|
|
757
|
+
|
|
758
|
+
// cli/_build.ts
|
|
759
|
+
import React2 from "react";
|
|
760
|
+
async function buildAgentBundle(cwd, log) {
|
|
761
|
+
const agent = await loadAgent(cwd);
|
|
762
|
+
if (!agent) {
|
|
763
|
+
throw new Error("No agent found \u2014 run `aai init` first");
|
|
764
|
+
}
|
|
765
|
+
log(React2.createElement(Step, { action: "Bundle", msg: agent.slug }));
|
|
766
|
+
let bundle;
|
|
767
|
+
try {
|
|
768
|
+
bundle = await bundleAgent(agent);
|
|
769
|
+
} catch (err) {
|
|
770
|
+
if (err instanceof BundleError) {
|
|
771
|
+
throw new Error(`Bundle failed: ${err.message}`);
|
|
772
|
+
}
|
|
773
|
+
throw err;
|
|
774
|
+
}
|
|
775
|
+
const kb = (bundle.workerBytes / 1024).toFixed(1);
|
|
776
|
+
const clientCount = Object.keys(bundle.clientFiles).length;
|
|
777
|
+
log(React2.createElement(Info, { msg: `worker: ${kb} KB, client: ${clientCount} file(s)` }));
|
|
778
|
+
if (agent.clientEntry) {
|
|
779
|
+
log(React2.createElement(Step, { action: "Render", msg: "check" }));
|
|
780
|
+
try {
|
|
781
|
+
const { renderCheck: renderCheck2 } = await Promise.resolve().then(() => (init_render_check(), render_check_exports));
|
|
782
|
+
await renderCheck2(agent.clientEntry, cwd);
|
|
783
|
+
} catch (err) {
|
|
784
|
+
throw new Error(`Render check failed: ${err instanceof Error ? err.message : String(err)}`);
|
|
785
|
+
}
|
|
786
|
+
}
|
|
787
|
+
return bundle;
|
|
788
|
+
}
|
|
789
|
+
var init_build = __esm({
|
|
790
|
+
"cli/_build.ts"() {
|
|
791
|
+
"use strict";
|
|
792
|
+
init_bundler();
|
|
793
|
+
init_discover();
|
|
794
|
+
init_ink();
|
|
795
|
+
}
|
|
796
|
+
});
|
|
797
|
+
|
|
599
798
|
// cli/_init.ts
|
|
600
799
|
var init_exports = {};
|
|
601
800
|
__export(init_exports, {
|
|
@@ -684,19 +883,163 @@ var init_init = __esm({
|
|
|
684
883
|
}
|
|
685
884
|
});
|
|
686
885
|
|
|
886
|
+
// cli/_deploy.ts
|
|
887
|
+
async function attemptDeploy(url, slug, apiKey, env, worker, clientFiles) {
|
|
888
|
+
try {
|
|
889
|
+
return await _internals.fetch(`${url}/${slug}/deploy`, {
|
|
890
|
+
method: "POST",
|
|
891
|
+
headers: {
|
|
892
|
+
"Content-Type": "application/json",
|
|
893
|
+
Authorization: `Bearer ${apiKey}`
|
|
894
|
+
},
|
|
895
|
+
body: JSON.stringify({
|
|
896
|
+
env,
|
|
897
|
+
worker,
|
|
898
|
+
clientFiles
|
|
899
|
+
})
|
|
900
|
+
});
|
|
901
|
+
} catch {
|
|
902
|
+
throw new Error(`deployment failed: could not reach ${url}`);
|
|
903
|
+
}
|
|
904
|
+
}
|
|
905
|
+
async function runDeploy(opts) {
|
|
906
|
+
const worker = opts.bundle.worker;
|
|
907
|
+
const clientFiles = opts.bundle.clientFiles;
|
|
908
|
+
let slug = opts.slug;
|
|
909
|
+
if (opts.dryRun) {
|
|
910
|
+
return { slug };
|
|
911
|
+
}
|
|
912
|
+
for (let i = 0; i < MAX_RETRIES; i++) {
|
|
913
|
+
const resp = await attemptDeploy(opts.url, slug, opts.apiKey, opts.env, worker, clientFiles);
|
|
914
|
+
if (resp.ok) {
|
|
915
|
+
return { slug };
|
|
916
|
+
}
|
|
917
|
+
if (resp.status === 403) {
|
|
918
|
+
const text2 = await resp.text();
|
|
919
|
+
if (text2.includes("Slug")) {
|
|
920
|
+
slug = generateSlug();
|
|
921
|
+
continue;
|
|
922
|
+
}
|
|
923
|
+
}
|
|
924
|
+
const text = await resp.text();
|
|
925
|
+
throw new Error(`deploy failed (${resp.status}): ${text}`);
|
|
926
|
+
}
|
|
927
|
+
throw new Error(`deploy failed: could not find available slug after ${MAX_RETRIES} attempts`);
|
|
928
|
+
}
|
|
929
|
+
var _internals, MAX_RETRIES;
|
|
930
|
+
var init_deploy = __esm({
|
|
931
|
+
"cli/_deploy.ts"() {
|
|
932
|
+
"use strict";
|
|
933
|
+
init_discover();
|
|
934
|
+
_internals = {
|
|
935
|
+
fetch: globalThis.fetch.bind(globalThis)
|
|
936
|
+
};
|
|
937
|
+
MAX_RETRIES = 20;
|
|
938
|
+
}
|
|
939
|
+
});
|
|
940
|
+
|
|
941
|
+
// cli/deploy.tsx
|
|
942
|
+
var deploy_exports = {};
|
|
943
|
+
__export(deploy_exports, {
|
|
944
|
+
runDeployCommand: () => runDeployCommand
|
|
945
|
+
});
|
|
946
|
+
import path4 from "node:path";
|
|
947
|
+
import minimist from "minimist";
|
|
948
|
+
import { jsx as jsx3 } from "react/jsx-runtime";
|
|
949
|
+
function resolveServerUrl(parsed) {
|
|
950
|
+
return parsed.server || (isDevMode() ? "http://localhost:3100" : DEFAULT_SERVER);
|
|
951
|
+
}
|
|
952
|
+
async function deployBundle(opts) {
|
|
953
|
+
const { bundle, serverUrl, apiKey, cwd, log } = opts;
|
|
954
|
+
let { slug } = opts;
|
|
955
|
+
log(/* @__PURE__ */ jsx3(Step, { action: "Deploy", msg: slug }));
|
|
956
|
+
const deployed = await runDeploy({
|
|
957
|
+
url: serverUrl,
|
|
958
|
+
bundle,
|
|
959
|
+
env: { ASSEMBLYAI_API_KEY: apiKey },
|
|
960
|
+
slug,
|
|
961
|
+
dryRun: false,
|
|
962
|
+
apiKey
|
|
963
|
+
});
|
|
964
|
+
slug = deployed.slug;
|
|
965
|
+
await writeProjectConfig(cwd, { slug, serverUrl });
|
|
966
|
+
const agentUrl = `${serverUrl}/${slug}`;
|
|
967
|
+
log(/* @__PURE__ */ jsx3(Step, { action: "Ready", msg: agentUrl }));
|
|
968
|
+
return agentUrl;
|
|
969
|
+
}
|
|
970
|
+
async function runDeployCommand(args, version) {
|
|
971
|
+
const parsed = minimist(args, {
|
|
972
|
+
string: ["server"],
|
|
973
|
+
boolean: ["dry-run", "help", "yes"],
|
|
974
|
+
alias: { s: "server", h: "help", y: "yes" }
|
|
975
|
+
});
|
|
976
|
+
if (parsed.help) {
|
|
977
|
+
console.log(subcommandHelp(deployCommandDef, version));
|
|
978
|
+
return;
|
|
979
|
+
}
|
|
980
|
+
const cwd = process.env.INIT_CWD || process.cwd();
|
|
981
|
+
if (!await fileExists(path4.join(cwd, "agent.ts"))) {
|
|
982
|
+
await runInitCommand(parsed.yes ? ["-y"] : [], version, { quiet: true });
|
|
983
|
+
}
|
|
984
|
+
const serverUrl = resolveServerUrl(parsed);
|
|
985
|
+
const dryRun = parsed["dry-run"] ?? false;
|
|
986
|
+
const apiKey = dryRun ? "" : await getApiKey();
|
|
987
|
+
const projectConfig = await readProjectConfig(cwd);
|
|
988
|
+
const slug = projectConfig?.slug ?? generateSlug();
|
|
989
|
+
let agentUrl = "";
|
|
990
|
+
await runWithInk(async (log) => {
|
|
991
|
+
const bundle = await buildAgentBundle(cwd, log);
|
|
992
|
+
if (dryRun) {
|
|
993
|
+
log(/* @__PURE__ */ jsx3(StepInfo, { action: "Dry run", msg: `would deploy as ${slug}` }));
|
|
994
|
+
return;
|
|
995
|
+
}
|
|
996
|
+
agentUrl = await deployBundle({ bundle, serverUrl, apiKey, slug, cwd, log });
|
|
997
|
+
});
|
|
998
|
+
if (agentUrl && !dryRun) {
|
|
999
|
+
await askEnter("Press enter to open in browser");
|
|
1000
|
+
const { exec } = await import("node:child_process");
|
|
1001
|
+
exec(`open "${agentUrl}"`);
|
|
1002
|
+
}
|
|
1003
|
+
}
|
|
1004
|
+
var deployCommandDef;
|
|
1005
|
+
var init_deploy2 = __esm({
|
|
1006
|
+
"cli/deploy.tsx"() {
|
|
1007
|
+
"use strict";
|
|
1008
|
+
init_build();
|
|
1009
|
+
init_deploy();
|
|
1010
|
+
init_discover();
|
|
1011
|
+
init_help();
|
|
1012
|
+
init_ink();
|
|
1013
|
+
init_prompts();
|
|
1014
|
+
init_init2();
|
|
1015
|
+
deployCommandDef = {
|
|
1016
|
+
name: "deploy",
|
|
1017
|
+
description: "Bundle and deploy to production",
|
|
1018
|
+
options: [
|
|
1019
|
+
{ flags: "-s, --server <url>", description: "Server URL" },
|
|
1020
|
+
{
|
|
1021
|
+
flags: "--dry-run",
|
|
1022
|
+
description: "Validate and bundle without deploying"
|
|
1023
|
+
},
|
|
1024
|
+
{ flags: "-y, --yes", description: "Accept defaults (no prompts)" }
|
|
1025
|
+
]
|
|
1026
|
+
};
|
|
1027
|
+
}
|
|
1028
|
+
});
|
|
1029
|
+
|
|
687
1030
|
// cli/init.tsx
|
|
688
1031
|
import { execFile } from "node:child_process";
|
|
689
1032
|
import fs4 from "node:fs/promises";
|
|
690
|
-
import
|
|
1033
|
+
import path5 from "node:path";
|
|
691
1034
|
import { fileURLToPath } from "node:url";
|
|
692
1035
|
import { promisify } from "node:util";
|
|
693
|
-
import
|
|
694
|
-
import { jsx as
|
|
1036
|
+
import minimist2 from "minimist";
|
|
1037
|
+
import { jsx as jsx4 } from "react/jsx-runtime";
|
|
695
1038
|
async function rewriteDevDeps(cwd, cliDir2) {
|
|
696
|
-
const monorepoRoot =
|
|
697
|
-
const pkgJsonPath2 =
|
|
1039
|
+
const monorepoRoot = path5.join(cliDir2, "..");
|
|
1040
|
+
const pkgJsonPath2 = path5.join(cwd, "package.json");
|
|
698
1041
|
const pkgJson2 = JSON.parse(await fs4.readFile(pkgJsonPath2, "utf-8"));
|
|
699
|
-
const rootPkg = JSON.parse(await fs4.readFile(
|
|
1042
|
+
const rootPkg = JSON.parse(await fs4.readFile(path5.join(monorepoRoot, "package.json"), "utf-8"));
|
|
700
1043
|
const rootPkgName = rootPkg.name;
|
|
701
1044
|
if (pkgJson2.dependencies[rootPkgName]) {
|
|
702
1045
|
pkgJson2.dependencies[rootPkgName] = `file:${monorepoRoot}`;
|
|
@@ -705,29 +1048,29 @@ async function rewriteDevDeps(cwd, cliDir2) {
|
|
|
705
1048
|
`);
|
|
706
1049
|
}
|
|
707
1050
|
async function installDeps(cwd, log) {
|
|
708
|
-
if (await fileExists(
|
|
1051
|
+
if (await fileExists(path5.join(cwd, "node_modules"))) return;
|
|
709
1052
|
let pkgJson2;
|
|
710
1053
|
try {
|
|
711
|
-
pkgJson2 = JSON.parse(await fs4.readFile(
|
|
1054
|
+
pkgJson2 = JSON.parse(await fs4.readFile(path5.join(cwd, "package.json"), "utf-8"));
|
|
712
1055
|
} catch {
|
|
713
1056
|
pkgJson2 = {};
|
|
714
1057
|
}
|
|
715
1058
|
const deps = Object.keys(pkgJson2.dependencies ?? {});
|
|
716
1059
|
const devDeps = Object.keys(pkgJson2.devDependencies ?? {});
|
|
717
1060
|
if (deps.length > 0) {
|
|
718
|
-
log(/* @__PURE__ */
|
|
1061
|
+
log(/* @__PURE__ */ jsx4(Step, { action: "Install", msg: deps.join(", ") }));
|
|
719
1062
|
}
|
|
720
1063
|
if (devDeps.length > 0) {
|
|
721
|
-
log(/* @__PURE__ */
|
|
1064
|
+
log(/* @__PURE__ */ jsx4(Step, { action: "Install", msg: `dev: ${devDeps.join(", ")}` }));
|
|
722
1065
|
}
|
|
723
1066
|
try {
|
|
724
1067
|
await execFileAsync("npm", ["install"], { cwd });
|
|
725
1068
|
} catch {
|
|
726
|
-
log(/* @__PURE__ */
|
|
1069
|
+
log(/* @__PURE__ */ jsx4(Warn, { msg: "npm install failed" }));
|
|
727
1070
|
}
|
|
728
1071
|
}
|
|
729
1072
|
async function runInitCommand(args, version, opts) {
|
|
730
|
-
const parsed =
|
|
1073
|
+
const parsed = minimist2(args, {
|
|
731
1074
|
string: ["template"],
|
|
732
1075
|
boolean: ["force", "help"],
|
|
733
1076
|
alias: { t: "template", f: "force", h: "help" }
|
|
@@ -742,19 +1085,19 @@ async function runInitCommand(args, version, opts) {
|
|
|
742
1085
|
if (!dir) {
|
|
743
1086
|
dir = await askText("What is your project named?", "my-voice-agent");
|
|
744
1087
|
}
|
|
745
|
-
const cwd =
|
|
746
|
-
if (!parsed.force && await fileExists(
|
|
1088
|
+
const cwd = path5.resolve(process.env.INIT_CWD || process.cwd(), dir);
|
|
1089
|
+
if (!parsed.force && await fileExists(path5.join(cwd, "agent.ts"))) {
|
|
747
1090
|
console.log(
|
|
748
1091
|
`agent.ts already exists in this directory. Use ${interactive("--force")} to overwrite.`
|
|
749
1092
|
);
|
|
750
1093
|
process.exit(1);
|
|
751
1094
|
}
|
|
752
|
-
const cliDir2 =
|
|
753
|
-
const templatesDir =
|
|
1095
|
+
const cliDir2 = path5.dirname(fileURLToPath(import.meta.url));
|
|
1096
|
+
const templatesDir = path5.join(cliDir2, "..", "templates");
|
|
754
1097
|
const { runInit: runInit2 } = await Promise.resolve().then(() => (init_init(), init_exports));
|
|
755
1098
|
const template = parsed.template || "simple";
|
|
756
1099
|
await runWithInk(async (log) => {
|
|
757
|
-
log(/* @__PURE__ */
|
|
1100
|
+
log(/* @__PURE__ */ jsx4(Step, { action: "Create", msg: dir }));
|
|
758
1101
|
await runInit2({ targetDir: cwd, template, templatesDir });
|
|
759
1102
|
if (isDevMode()) {
|
|
760
1103
|
await rewriteDevDeps(cwd, cliDir2);
|
|
@@ -794,112 +1137,6 @@ var init_init2 = __esm({
|
|
|
794
1137
|
}
|
|
795
1138
|
});
|
|
796
1139
|
|
|
797
|
-
// cli/deploy.tsx
|
|
798
|
-
var deploy_exports = {};
|
|
799
|
-
__export(deploy_exports, {
|
|
800
|
-
runDeployCommand: () => runDeployCommand
|
|
801
|
-
});
|
|
802
|
-
import path5 from "node:path";
|
|
803
|
-
import minimist2 from "minimist";
|
|
804
|
-
import { jsx as jsx4 } from "react/jsx-runtime";
|
|
805
|
-
function resolveServerUrl(parsed) {
|
|
806
|
-
return parsed.server || (isDevMode() ? "http://localhost:3100" : DEFAULT_SERVER);
|
|
807
|
-
}
|
|
808
|
-
async function buildAgent(cwd, log) {
|
|
809
|
-
log(/* @__PURE__ */ jsx4(Step, { action: "Build", msg: "bundling agent" }));
|
|
810
|
-
const agent = await loadAgent(cwd);
|
|
811
|
-
if (!agent) {
|
|
812
|
-
throw new Error("No agent found \u2014 run `aai init` first");
|
|
813
|
-
}
|
|
814
|
-
let bundle;
|
|
815
|
-
try {
|
|
816
|
-
bundle = await bundleAgent(agent);
|
|
817
|
-
} catch (err) {
|
|
818
|
-
if (err instanceof BundleError) {
|
|
819
|
-
throw new Error(`Bundle failed: ${err.message}`);
|
|
820
|
-
}
|
|
821
|
-
throw err;
|
|
822
|
-
}
|
|
823
|
-
return bundle;
|
|
824
|
-
}
|
|
825
|
-
async function deployBundle(opts) {
|
|
826
|
-
const { bundle, serverUrl, apiKey, cwd, log } = opts;
|
|
827
|
-
let { slug } = opts;
|
|
828
|
-
log(/* @__PURE__ */ jsx4(Step, { action: "Deploy", msg: slug }));
|
|
829
|
-
const deployed = await runDeploy({
|
|
830
|
-
url: serverUrl,
|
|
831
|
-
bundle,
|
|
832
|
-
env: { ASSEMBLYAI_API_KEY: apiKey },
|
|
833
|
-
slug,
|
|
834
|
-
dryRun: false,
|
|
835
|
-
apiKey
|
|
836
|
-
});
|
|
837
|
-
slug = deployed.slug;
|
|
838
|
-
await writeProjectConfig(cwd, { slug, serverUrl });
|
|
839
|
-
const agentUrl = `${serverUrl}/${slug}`;
|
|
840
|
-
log(/* @__PURE__ */ jsx4(Step, { action: "Ready", msg: agentUrl }));
|
|
841
|
-
return agentUrl;
|
|
842
|
-
}
|
|
843
|
-
async function runDeployCommand(args, version) {
|
|
844
|
-
const parsed = minimist2(args, {
|
|
845
|
-
string: ["server"],
|
|
846
|
-
boolean: ["dry-run", "help", "yes"],
|
|
847
|
-
alias: { s: "server", h: "help", y: "yes" }
|
|
848
|
-
});
|
|
849
|
-
if (parsed.help) {
|
|
850
|
-
console.log(subcommandHelp(deployCommandDef, version));
|
|
851
|
-
return;
|
|
852
|
-
}
|
|
853
|
-
const cwd = process.env.INIT_CWD || process.cwd();
|
|
854
|
-
if (!await fileExists(path5.join(cwd, "agent.ts"))) {
|
|
855
|
-
await runInitCommand(parsed.yes ? ["-y"] : [], version, { quiet: true });
|
|
856
|
-
}
|
|
857
|
-
const serverUrl = resolveServerUrl(parsed);
|
|
858
|
-
const dryRun = parsed["dry-run"] ?? false;
|
|
859
|
-
const apiKey = dryRun ? "" : await getApiKey();
|
|
860
|
-
const projectConfig = await readProjectConfig(cwd);
|
|
861
|
-
const slug = projectConfig?.slug ?? generateSlug();
|
|
862
|
-
let agentUrl = "";
|
|
863
|
-
await runWithInk(async (log) => {
|
|
864
|
-
const bundle = await buildAgent(cwd, log);
|
|
865
|
-
if (dryRun) {
|
|
866
|
-
log(/* @__PURE__ */ jsx4(StepInfo, { action: "Dry run", msg: `would deploy as ${slug}` }));
|
|
867
|
-
return;
|
|
868
|
-
}
|
|
869
|
-
agentUrl = await deployBundle({ bundle, serverUrl, apiKey, slug, cwd, log });
|
|
870
|
-
});
|
|
871
|
-
if (agentUrl && !dryRun) {
|
|
872
|
-
await askEnter("Press enter to open in browser");
|
|
873
|
-
const { exec } = await import("node:child_process");
|
|
874
|
-
exec(`open "${agentUrl}"`);
|
|
875
|
-
}
|
|
876
|
-
}
|
|
877
|
-
var deployCommandDef;
|
|
878
|
-
var init_deploy2 = __esm({
|
|
879
|
-
"cli/deploy.tsx"() {
|
|
880
|
-
"use strict";
|
|
881
|
-
init_bundler();
|
|
882
|
-
init_deploy();
|
|
883
|
-
init_discover();
|
|
884
|
-
init_help();
|
|
885
|
-
init_ink();
|
|
886
|
-
init_prompts();
|
|
887
|
-
init_init2();
|
|
888
|
-
deployCommandDef = {
|
|
889
|
-
name: "deploy",
|
|
890
|
-
description: "Bundle and deploy to production",
|
|
891
|
-
options: [
|
|
892
|
-
{ flags: "-s, --server <url>", description: "Server URL" },
|
|
893
|
-
{
|
|
894
|
-
flags: "--dry-run",
|
|
895
|
-
description: "Validate and bundle without deploying"
|
|
896
|
-
},
|
|
897
|
-
{ flags: "-y, --yes", description: "Accept defaults (no prompts)" }
|
|
898
|
-
]
|
|
899
|
-
};
|
|
900
|
-
}
|
|
901
|
-
});
|
|
902
|
-
|
|
903
1140
|
// sdk/protocol.ts
|
|
904
1141
|
import { z } from "zod";
|
|
905
1142
|
var DEFAULT_TTS_SAMPLE_RATE, AUDIO_FORMAT, _bitsPerSample, _channels, AudioFrameSpec, KvRequestBaseSchema, HOOK_TIMEOUT_MS, SessionErrorCodeSchema, TranscriptEventSchema, ClientEventSchema, ClientMessageSchema;
|
|
@@ -965,6 +1202,7 @@ var init_protocol = __esm({
|
|
|
965
1202
|
turnOrder: z.number().int().nonnegative().optional()
|
|
966
1203
|
}),
|
|
967
1204
|
z.object({ type: z.literal("chat"), text: z.string() }),
|
|
1205
|
+
z.object({ type: z.literal("chat_delta"), text: z.string() }),
|
|
968
1206
|
z.object({
|
|
969
1207
|
type: z.literal("tool_call_start"),
|
|
970
1208
|
toolCallId: z.string(),
|
|
@@ -1058,9 +1296,86 @@ var init_internal_types = __esm({
|
|
|
1058
1296
|
}
|
|
1059
1297
|
});
|
|
1060
1298
|
|
|
1299
|
+
// sdk/types.ts
|
|
1300
|
+
function tool(def) {
|
|
1301
|
+
return def;
|
|
1302
|
+
}
|
|
1303
|
+
var DEFAULT_INSTRUCTIONS;
|
|
1304
|
+
var init_types = __esm({
|
|
1305
|
+
"sdk/types.ts"() {
|
|
1306
|
+
"use strict";
|
|
1307
|
+
DEFAULT_INSTRUCTIONS = `You are AAI, a helpful AI assistant.
|
|
1308
|
+
|
|
1309
|
+
Voice-First Rules:
|
|
1310
|
+
- Optimize for natural speech. Avoid jargon unless central to the answer. Use short, punchy sentences.
|
|
1311
|
+
- Never mention "search results," "sources," or "the provided text." Speak as if the knowledge is your own.
|
|
1312
|
+
- No visual formatting. Do not say "bullet point," "bold," or "bracketed one." If you need to list items, say "First," "Next," and "Finally."
|
|
1313
|
+
- Start with the most important information. No introductory filler.
|
|
1314
|
+
- Be concise. Keep answers to 1-3 sentences. For complex topics, provide a high-level summary.
|
|
1315
|
+
- Be confident. Avoid hedging phrases like "It seems that" or "I believe."
|
|
1316
|
+
- If you don't have enough information, say so directly rather than guessing.
|
|
1317
|
+
- Never use exclamation points. Keep your tone calm and conversational.`;
|
|
1318
|
+
}
|
|
1319
|
+
});
|
|
1320
|
+
|
|
1321
|
+
// sdk/memory_tools.ts
|
|
1322
|
+
import { z as z3 } from "zod";
|
|
1323
|
+
function memoryTools() {
|
|
1324
|
+
return {
|
|
1325
|
+
save_memory: tool({
|
|
1326
|
+
description: "Save a piece of information to persistent memory. Use a descriptive key like 'user:name' or 'project:status'.",
|
|
1327
|
+
parameters: z3.object({
|
|
1328
|
+
key: z3.string().describe("A descriptive key for this memory (e.g. 'user:name', 'preference:color')"),
|
|
1329
|
+
value: z3.string().describe("The information to remember")
|
|
1330
|
+
}),
|
|
1331
|
+
execute: async ({ key, value }, ctx) => {
|
|
1332
|
+
await ctx.kv.set(key, value);
|
|
1333
|
+
return { saved: key };
|
|
1334
|
+
}
|
|
1335
|
+
}),
|
|
1336
|
+
recall_memory: tool({
|
|
1337
|
+
description: "Retrieve a previously saved memory by its key.",
|
|
1338
|
+
parameters: z3.object({
|
|
1339
|
+
key: z3.string().describe("The key to look up")
|
|
1340
|
+
}),
|
|
1341
|
+
execute: async ({ key }, ctx) => {
|
|
1342
|
+
const value = await ctx.kv.get(key);
|
|
1343
|
+
if (value === null) return { found: false, key };
|
|
1344
|
+
return { found: true, key, value };
|
|
1345
|
+
}
|
|
1346
|
+
}),
|
|
1347
|
+
list_memories: tool({
|
|
1348
|
+
description: "List all saved memory keys, optionally filtered by a prefix (e.g. 'user:').",
|
|
1349
|
+
parameters: z3.object({
|
|
1350
|
+
prefix: z3.string().describe("Prefix to filter keys (e.g. 'user:'). Use empty string for all.").optional()
|
|
1351
|
+
}),
|
|
1352
|
+
execute: async ({ prefix }, ctx) => {
|
|
1353
|
+
const entries = await ctx.kv.list(prefix ?? "");
|
|
1354
|
+
return { count: entries.length, keys: entries.map((e) => e.key) };
|
|
1355
|
+
}
|
|
1356
|
+
}),
|
|
1357
|
+
forget_memory: tool({
|
|
1358
|
+
description: "Delete a previously saved memory by its key.",
|
|
1359
|
+
parameters: z3.object({
|
|
1360
|
+
key: z3.string().describe("The key to delete")
|
|
1361
|
+
}),
|
|
1362
|
+
execute: async ({ key }, ctx) => {
|
|
1363
|
+
await ctx.kv.delete(key);
|
|
1364
|
+
return { deleted: key };
|
|
1365
|
+
}
|
|
1366
|
+
})
|
|
1367
|
+
};
|
|
1368
|
+
}
|
|
1369
|
+
var init_memory_tools = __esm({
|
|
1370
|
+
"sdk/memory_tools.ts"() {
|
|
1371
|
+
"use strict";
|
|
1372
|
+
init_types();
|
|
1373
|
+
}
|
|
1374
|
+
});
|
|
1375
|
+
|
|
1061
1376
|
// sdk/builtin_tools.ts
|
|
1062
1377
|
import { convert } from "html-to-text";
|
|
1063
|
-
import { z as
|
|
1378
|
+
import { z as z4 } from "zod";
|
|
1064
1379
|
function htmlToText(html) {
|
|
1065
1380
|
return convert(html, { wordwrap: false });
|
|
1066
1381
|
}
|
|
@@ -1213,12 +1528,27 @@ function getBuiltinToolDefs(names, opts) {
|
|
|
1213
1528
|
defs[name] = createVectorSearch(opts.vectorSearch);
|
|
1214
1529
|
}
|
|
1215
1530
|
break;
|
|
1531
|
+
case "memory": {
|
|
1532
|
+
const mt = memoryTools();
|
|
1533
|
+
for (const [toolName, toolDef] of Object.entries(mt)) {
|
|
1534
|
+
defs[toolName] = toolDef;
|
|
1535
|
+
}
|
|
1536
|
+
break;
|
|
1537
|
+
}
|
|
1216
1538
|
}
|
|
1217
1539
|
}
|
|
1218
1540
|
return defs;
|
|
1219
1541
|
}
|
|
1220
1542
|
function getBuiltinToolSchemas(names) {
|
|
1221
1543
|
return names.flatMap((name) => {
|
|
1544
|
+
const multiCreator = MULTI_TOOL_BUILTINS[name];
|
|
1545
|
+
if (multiCreator) {
|
|
1546
|
+
return Object.entries(multiCreator()).map(([toolName, def2]) => ({
|
|
1547
|
+
name: toolName,
|
|
1548
|
+
description: def2.description,
|
|
1549
|
+
parameters: z4.toJSONSchema(def2.parameters ?? EMPTY_PARAMS)
|
|
1550
|
+
}));
|
|
1551
|
+
}
|
|
1222
1552
|
const creator = TOOL_CREATORS[name];
|
|
1223
1553
|
if (!creator) return [];
|
|
1224
1554
|
const def = creator();
|
|
@@ -1226,49 +1556,50 @@ function getBuiltinToolSchemas(names) {
|
|
|
1226
1556
|
{
|
|
1227
1557
|
name,
|
|
1228
1558
|
description: def.description,
|
|
1229
|
-
parameters:
|
|
1559
|
+
parameters: z4.toJSONSchema(def.parameters ?? EMPTY_PARAMS)
|
|
1230
1560
|
}
|
|
1231
1561
|
];
|
|
1232
1562
|
});
|
|
1233
1563
|
}
|
|
1234
|
-
var webSearchParams, BRAVE_SEARCH_URL, BraveSearchResponseSchema, MAX_PAGE_CHARS, MAX_HTML_BYTES, visitWebpageParams, fetchJsonParams, runCodeParams, vectorSearchParams, TOOL_CREATORS;
|
|
1564
|
+
var webSearchParams, BRAVE_SEARCH_URL, BraveSearchResponseSchema, MAX_PAGE_CHARS, MAX_HTML_BYTES, visitWebpageParams, fetchJsonParams, runCodeParams, vectorSearchParams, TOOL_CREATORS, MULTI_TOOL_BUILTINS;
|
|
1235
1565
|
var init_builtin_tools = __esm({
|
|
1236
1566
|
"sdk/builtin_tools.ts"() {
|
|
1237
1567
|
"use strict";
|
|
1238
1568
|
init_internal_types();
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1569
|
+
init_memory_tools();
|
|
1570
|
+
webSearchParams = z4.object({
|
|
1571
|
+
query: z4.string().describe("The search query"),
|
|
1572
|
+
max_results: z4.number().describe("Maximum number of results to return (default 5)").optional()
|
|
1242
1573
|
});
|
|
1243
1574
|
BRAVE_SEARCH_URL = "https://api.search.brave.com/res/v1/web/search";
|
|
1244
|
-
BraveSearchResponseSchema =
|
|
1245
|
-
web:
|
|
1246
|
-
results:
|
|
1247
|
-
|
|
1248
|
-
title:
|
|
1249
|
-
url:
|
|
1250
|
-
description:
|
|
1575
|
+
BraveSearchResponseSchema = z4.object({
|
|
1576
|
+
web: z4.object({
|
|
1577
|
+
results: z4.array(
|
|
1578
|
+
z4.object({
|
|
1579
|
+
title: z4.string(),
|
|
1580
|
+
url: z4.string(),
|
|
1581
|
+
description: z4.string()
|
|
1251
1582
|
})
|
|
1252
1583
|
)
|
|
1253
1584
|
}).optional()
|
|
1254
1585
|
});
|
|
1255
1586
|
MAX_PAGE_CHARS = 1e4;
|
|
1256
1587
|
MAX_HTML_BYTES = 2e5;
|
|
1257
|
-
visitWebpageParams =
|
|
1258
|
-
url:
|
|
1588
|
+
visitWebpageParams = z4.object({
|
|
1589
|
+
url: z4.string().describe("The full URL to fetch (e.g., 'https://example.com/page')")
|
|
1259
1590
|
});
|
|
1260
|
-
fetchJsonParams =
|
|
1261
|
-
url:
|
|
1262
|
-
headers:
|
|
1591
|
+
fetchJsonParams = z4.object({
|
|
1592
|
+
url: z4.string().describe("The URL to fetch JSON from"),
|
|
1593
|
+
headers: z4.record(z4.string(), z4.string()).describe("Optional HTTP headers to include in the request").optional()
|
|
1263
1594
|
});
|
|
1264
|
-
runCodeParams =
|
|
1265
|
-
code:
|
|
1595
|
+
runCodeParams = z4.object({
|
|
1596
|
+
code: z4.string().describe("JavaScript code to execute. Use console.log() for output.")
|
|
1266
1597
|
});
|
|
1267
|
-
vectorSearchParams =
|
|
1268
|
-
query:
|
|
1598
|
+
vectorSearchParams = z4.object({
|
|
1599
|
+
query: z4.string().describe(
|
|
1269
1600
|
'Short keyword query to search the knowledge base. Use specific topic terms, not full sentences. Do NOT include the company or product name since all documents are from the same source. For example, if the user asks "how much does Acme cost", search for "pricing plans rates".'
|
|
1270
1601
|
),
|
|
1271
|
-
topK:
|
|
1602
|
+
topK: z4.number().describe("Maximum results to return (default: 5)").optional()
|
|
1272
1603
|
});
|
|
1273
1604
|
TOOL_CREATORS = {
|
|
1274
1605
|
web_search: createWebSearch,
|
|
@@ -1278,6 +1609,9 @@ var init_builtin_tools = __esm({
|
|
|
1278
1609
|
// vector_search uses a stub for schema generation
|
|
1279
1610
|
vector_search: () => createVectorSearch(async () => "")
|
|
1280
1611
|
};
|
|
1612
|
+
MULTI_TOOL_BUILTINS = {
|
|
1613
|
+
memory: memoryTools
|
|
1614
|
+
};
|
|
1281
1615
|
}
|
|
1282
1616
|
});
|
|
1283
1617
|
|
|
@@ -1348,7 +1682,7 @@ var init_kv = __esm({
|
|
|
1348
1682
|
});
|
|
1349
1683
|
|
|
1350
1684
|
// sdk/s2s.ts
|
|
1351
|
-
import { z as
|
|
1685
|
+
import { z as z5 } from "zod";
|
|
1352
1686
|
function uint8ToBase64(bytes) {
|
|
1353
1687
|
return Buffer.from(bytes.buffer, bytes.byteOffset, bytes.byteLength).toString("base64");
|
|
1354
1688
|
}
|
|
@@ -1486,7 +1820,9 @@ function connectS2s(opts) {
|
|
|
1486
1820
|
}
|
|
1487
1821
|
},
|
|
1488
1822
|
sendToolResult(callId, result) {
|
|
1489
|
-
|
|
1823
|
+
const msg = { type: "tool.result", call_id: callId, result };
|
|
1824
|
+
log.debug("S2S >> tool.result", { call_id: callId, resultLength: result.length });
|
|
1825
|
+
send(msg);
|
|
1490
1826
|
},
|
|
1491
1827
|
updateSession(sessionConfig) {
|
|
1492
1828
|
send({ type: "session.update", session: sessionConfig });
|
|
@@ -1516,6 +1852,9 @@ function connectS2s(opts) {
|
|
|
1516
1852
|
return;
|
|
1517
1853
|
}
|
|
1518
1854
|
const obj = raw;
|
|
1855
|
+
if (obj.type !== "reply.audio" && obj.type !== "input.audio" && obj.type !== "transcript.agent.delta") {
|
|
1856
|
+
log.info(`S2S << ${obj.type}`);
|
|
1857
|
+
}
|
|
1519
1858
|
if (obj.type === "reply.audio" && typeof obj.data === "string") {
|
|
1520
1859
|
const audioBytes = base64ToUint8(obj.data);
|
|
1521
1860
|
target.dispatchEvent(new CustomEvent("audio", { detail: { audio: audioBytes } }));
|
|
@@ -1523,13 +1862,12 @@ function connectS2s(opts) {
|
|
|
1523
1862
|
}
|
|
1524
1863
|
const parsed = S2sServerMessageSchema.safeParse(raw);
|
|
1525
1864
|
if (!parsed.success) {
|
|
1526
|
-
log.
|
|
1527
|
-
`S2S << unrecognised message type: ${obj.type ?? JSON.stringify(raw).slice(0,
|
|
1865
|
+
log.warn(
|
|
1866
|
+
`S2S << unrecognised message type: ${obj.type ?? JSON.stringify(raw).slice(0, 200)}`
|
|
1528
1867
|
);
|
|
1529
1868
|
return;
|
|
1530
1869
|
}
|
|
1531
1870
|
const msg = parsed.data;
|
|
1532
|
-
log.debug(`S2S << ${msg.type}`);
|
|
1533
1871
|
dispatchS2sMessage(target, msg);
|
|
1534
1872
|
});
|
|
1535
1873
|
ws.on("close", (code, reason) => {
|
|
@@ -1560,66 +1898,47 @@ var init_s2s = __esm({
|
|
|
1560
1898
|
"use strict";
|
|
1561
1899
|
init_runtime();
|
|
1562
1900
|
WS_OPEN = 1;
|
|
1563
|
-
S2sServerMessageSchema =
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
type:
|
|
1571
|
-
item_id:
|
|
1572
|
-
text:
|
|
1901
|
+
S2sServerMessageSchema = z5.discriminatedUnion("type", [
|
|
1902
|
+
z5.object({ type: z5.literal("session.ready"), session_id: z5.string() }),
|
|
1903
|
+
z5.object({ type: z5.literal("session.updated") }).passthrough(),
|
|
1904
|
+
z5.object({ type: z5.literal("input.speech.started") }),
|
|
1905
|
+
z5.object({ type: z5.literal("input.speech.stopped") }),
|
|
1906
|
+
z5.object({ type: z5.literal("transcript.user.delta"), text: z5.string() }),
|
|
1907
|
+
z5.object({
|
|
1908
|
+
type: z5.literal("transcript.user"),
|
|
1909
|
+
item_id: z5.string(),
|
|
1910
|
+
text: z5.string()
|
|
1573
1911
|
}),
|
|
1574
|
-
|
|
1912
|
+
z5.object({ type: z5.literal("reply.started"), reply_id: z5.string() }),
|
|
1575
1913
|
// reply.audio is handled on the fast path before Zod — see message handler.
|
|
1576
|
-
|
|
1577
|
-
|
|
1578
|
-
|
|
1579
|
-
|
|
1580
|
-
|
|
1581
|
-
type:
|
|
1582
|
-
call_id:
|
|
1583
|
-
name:
|
|
1584
|
-
args:
|
|
1914
|
+
z5.object({ type: z5.literal("transcript.agent.delta"), delta: z5.string() }).passthrough(),
|
|
1915
|
+
z5.object({ type: z5.literal("transcript.agent"), text: z5.string() }),
|
|
1916
|
+
z5.object({ type: z5.literal("reply.content_part.started") }).passthrough(),
|
|
1917
|
+
z5.object({ type: z5.literal("reply.content_part.done") }).passthrough(),
|
|
1918
|
+
z5.object({
|
|
1919
|
+
type: z5.literal("tool.call"),
|
|
1920
|
+
call_id: z5.string(),
|
|
1921
|
+
name: z5.string(),
|
|
1922
|
+
args: z5.record(z5.string(), z5.unknown()).optional().default({})
|
|
1585
1923
|
}),
|
|
1586
|
-
|
|
1587
|
-
type:
|
|
1588
|
-
status:
|
|
1924
|
+
z5.object({
|
|
1925
|
+
type: z5.literal("reply.done"),
|
|
1926
|
+
status: z5.string().optional()
|
|
1589
1927
|
}),
|
|
1590
|
-
|
|
1591
|
-
type:
|
|
1592
|
-
code:
|
|
1593
|
-
message:
|
|
1928
|
+
z5.object({
|
|
1929
|
+
type: z5.literal("session.error"),
|
|
1930
|
+
code: z5.string(),
|
|
1931
|
+
message: z5.string()
|
|
1594
1932
|
}),
|
|
1595
1933
|
// Connection-level error (bare "error" without "session." prefix).
|
|
1596
|
-
|
|
1597
|
-
type:
|
|
1598
|
-
message:
|
|
1934
|
+
z5.object({
|
|
1935
|
+
type: z5.literal("error"),
|
|
1936
|
+
message: z5.string()
|
|
1599
1937
|
})
|
|
1600
1938
|
]);
|
|
1601
1939
|
}
|
|
1602
1940
|
});
|
|
1603
1941
|
|
|
1604
|
-
// sdk/types.ts
|
|
1605
|
-
var DEFAULT_INSTRUCTIONS;
|
|
1606
|
-
var init_types = __esm({
|
|
1607
|
-
"sdk/types.ts"() {
|
|
1608
|
-
"use strict";
|
|
1609
|
-
DEFAULT_INSTRUCTIONS = `You are AAI, a helpful AI assistant.
|
|
1610
|
-
|
|
1611
|
-
Voice-First Rules:
|
|
1612
|
-
- Optimize for natural speech. Avoid jargon unless central to the answer. Use short, punchy sentences.
|
|
1613
|
-
- Never mention "search results," "sources," or "the provided text." Speak as if the knowledge is your own.
|
|
1614
|
-
- No visual formatting. Do not say "bullet point," "bold," or "bracketed one." If you need to list items, say "First," "Next," and "Finally."
|
|
1615
|
-
- Start with the most important information. No introductory filler.
|
|
1616
|
-
- Be concise. Keep answers to 1-3 sentences. For complex topics, provide a high-level summary.
|
|
1617
|
-
- Be confident. Avoid hedging phrases like "It seems that" or "I believe."
|
|
1618
|
-
- If you don't have enough information, say so directly rather than guessing.
|
|
1619
|
-
- Never use exclamation points. Keep your tone calm and conversational.`;
|
|
1620
|
-
}
|
|
1621
|
-
});
|
|
1622
|
-
|
|
1623
1942
|
// sdk/system_prompt.ts
|
|
1624
1943
|
function buildSystemPrompt(config, opts) {
|
|
1625
1944
|
const { hasTools } = opts;
|
|
@@ -1822,6 +2141,9 @@ function createS2sSession(opts) {
|
|
|
1822
2141
|
on(handle, "audio", (e) => {
|
|
1823
2142
|
client.playAudioChunk(e.detail.audio);
|
|
1824
2143
|
});
|
|
2144
|
+
on(handle, "agent_transcript_delta", (e) => {
|
|
2145
|
+
client.event({ type: "chat_delta", text: e.detail.text });
|
|
2146
|
+
});
|
|
1825
2147
|
on(handle, "agent_transcript", (e) => {
|
|
1826
2148
|
const { text } = e.detail;
|
|
1827
2149
|
client.event({ type: "chat", text });
|
|
@@ -1841,8 +2163,8 @@ function createS2sSession(opts) {
|
|
|
1841
2163
|
pendingTools = [];
|
|
1842
2164
|
client.event({ type: "cancelled" });
|
|
1843
2165
|
} else if (pendingTools.length > 0) {
|
|
1844
|
-
for (const
|
|
1845
|
-
s2s?.sendToolResult(
|
|
2166
|
+
for (const tool2 of pendingTools) {
|
|
2167
|
+
s2s?.sendToolResult(tool2.call_id, tool2.result);
|
|
1846
2168
|
}
|
|
1847
2169
|
pendingTools = [];
|
|
1848
2170
|
} else {
|
|
@@ -1860,6 +2182,7 @@ function createS2sSession(opts) {
|
|
|
1860
2182
|
code: "internal",
|
|
1861
2183
|
message: e.detail.message
|
|
1862
2184
|
});
|
|
2185
|
+
handle.close();
|
|
1863
2186
|
});
|
|
1864
2187
|
handle.addEventListener("close", () => {
|
|
1865
2188
|
log.info("S2S closed");
|
|
@@ -2023,8 +2346,8 @@ function buildToolContext(opts) {
|
|
|
2023
2346
|
};
|
|
2024
2347
|
}
|
|
2025
2348
|
async function executeToolCall(name, args, options) {
|
|
2026
|
-
const { tool } = options;
|
|
2027
|
-
const schema =
|
|
2349
|
+
const { tool: tool2 } = options;
|
|
2350
|
+
const schema = tool2.parameters ?? EMPTY_PARAMS;
|
|
2028
2351
|
const parsed = schema.safeParse(args);
|
|
2029
2352
|
if (!parsed.success) {
|
|
2030
2353
|
const issues = (parsed.error?.issues ?? []).map((i) => `${i.path.map(String).join(".")}: ${i.message}`).join(", ");
|
|
@@ -2033,7 +2356,7 @@ async function executeToolCall(name, args, options) {
|
|
|
2033
2356
|
try {
|
|
2034
2357
|
const ctx = buildToolContext(options);
|
|
2035
2358
|
await yieldTick();
|
|
2036
|
-
const result = await Promise.resolve(
|
|
2359
|
+
const result = await Promise.resolve(tool2.execute(parsed.data, ctx));
|
|
2037
2360
|
await yieldTick();
|
|
2038
2361
|
if (result == null) return "null";
|
|
2039
2362
|
return typeof result === "string" ? result : JSON.stringify(result);
|
|
@@ -2061,8 +2384,7 @@ function buildAgentConfig(agent) {
|
|
|
2061
2384
|
const config = {
|
|
2062
2385
|
name: agent.name,
|
|
2063
2386
|
instructions: agent.instructions,
|
|
2064
|
-
greeting: agent.greeting
|
|
2065
|
-
voice: agent.voice
|
|
2387
|
+
greeting: agent.greeting
|
|
2066
2388
|
};
|
|
2067
2389
|
if (agent.sttPrompt !== void 0) config.sttPrompt = agent.sttPrompt;
|
|
2068
2390
|
if (typeof agent.maxSteps !== "function") config.maxSteps = agent.maxSteps;
|
|
@@ -2117,10 +2439,10 @@ function createDirectExecutor(opts) {
|
|
|
2117
2439
|
};
|
|
2118
2440
|
}
|
|
2119
2441
|
const executeTool = async (name, args, sessionId, messages) => {
|
|
2120
|
-
const
|
|
2121
|
-
if (!
|
|
2442
|
+
const tool2 = allTools[name];
|
|
2443
|
+
if (!tool2) return JSON.stringify({ error: `Unknown tool: ${name}` });
|
|
2122
2444
|
return executeToolCall(name, args, {
|
|
2123
|
-
tool,
|
|
2445
|
+
tool: tool2,
|
|
2124
2446
|
env: frozenEnv,
|
|
2125
2447
|
sessionId,
|
|
2126
2448
|
state: getState(sessionId ?? ""),
|
|
@@ -2590,30 +2912,64 @@ var init_server = __esm({
|
|
|
2590
2912
|
|
|
2591
2913
|
// cli/cli.ts
|
|
2592
2914
|
init_help();
|
|
2593
|
-
init_deploy2();
|
|
2594
2915
|
import { readFileSync } from "node:fs";
|
|
2595
|
-
import
|
|
2916
|
+
import path11 from "node:path";
|
|
2596
2917
|
import { fileURLToPath as fileURLToPath2 } from "node:url";
|
|
2597
|
-
import
|
|
2918
|
+
import minimist8 from "minimist";
|
|
2598
2919
|
|
|
2599
|
-
// cli/
|
|
2600
|
-
|
|
2920
|
+
// cli/build.tsx
|
|
2921
|
+
init_build();
|
|
2922
|
+
init_discover();
|
|
2923
|
+
init_help();
|
|
2924
|
+
init_ink();
|
|
2925
|
+
init_init2();
|
|
2926
|
+
import path6 from "node:path";
|
|
2601
2927
|
import minimist3 from "minimist";
|
|
2928
|
+
import { jsx as jsx5 } from "react/jsx-runtime";
|
|
2929
|
+
var buildCommandDef = {
|
|
2930
|
+
name: "build",
|
|
2931
|
+
description: "Bundle agent and client (validates code without deploying or starting a server)",
|
|
2932
|
+
options: [{ flags: "-y, --yes", description: "Accept defaults (no prompts)" }]
|
|
2933
|
+
};
|
|
2934
|
+
async function runBuildCommand(args, version) {
|
|
2935
|
+
const parsed = minimist3(args, {
|
|
2936
|
+
boolean: ["help", "yes"],
|
|
2937
|
+
alias: { h: "help", y: "yes" }
|
|
2938
|
+
});
|
|
2939
|
+
if (parsed.help) {
|
|
2940
|
+
console.log(subcommandHelp(buildCommandDef, version));
|
|
2941
|
+
return;
|
|
2942
|
+
}
|
|
2943
|
+
const cwd = process.env.INIT_CWD || process.cwd();
|
|
2944
|
+
if (!await fileExists(path6.join(cwd, "agent.ts"))) {
|
|
2945
|
+
await runInitCommand(parsed.yes ? ["-y"] : [], version, { quiet: true });
|
|
2946
|
+
}
|
|
2947
|
+
await runWithInk(async (log) => {
|
|
2948
|
+
await buildAgentBundle(cwd, log);
|
|
2949
|
+
log(/* @__PURE__ */ jsx5(Step, { action: "Build", msg: "ok" }));
|
|
2950
|
+
});
|
|
2951
|
+
}
|
|
2952
|
+
|
|
2953
|
+
// cli/cli.ts
|
|
2954
|
+
init_deploy2();
|
|
2955
|
+
|
|
2956
|
+
// cli/dev.tsx
|
|
2957
|
+
import path8 from "node:path";
|
|
2958
|
+
import minimist4 from "minimist";
|
|
2602
2959
|
|
|
2603
2960
|
// cli/_dev.ts
|
|
2604
|
-
|
|
2605
|
-
init_discover();
|
|
2961
|
+
init_build();
|
|
2606
2962
|
init_ink();
|
|
2607
|
-
import
|
|
2963
|
+
import React3 from "react";
|
|
2608
2964
|
|
|
2609
2965
|
// cli/_server_common.ts
|
|
2610
2966
|
init_discover();
|
|
2611
2967
|
import fs5 from "node:fs/promises";
|
|
2612
|
-
import
|
|
2613
|
-
import { createServer as
|
|
2968
|
+
import path7 from "node:path";
|
|
2969
|
+
import { createServer as createViteServer2 } from "vite";
|
|
2614
2970
|
async function loadAgentDef(cwd) {
|
|
2615
|
-
const agentPath =
|
|
2616
|
-
const vite = await
|
|
2971
|
+
const agentPath = path7.resolve(cwd, "agent.ts");
|
|
2972
|
+
const vite = await createViteServer2({
|
|
2617
2973
|
root: cwd,
|
|
2618
2974
|
logLevel: "silent",
|
|
2619
2975
|
server: { middlewareMode: true }
|
|
@@ -2642,7 +2998,7 @@ async function bootServer(agentDef, clientDir, env, port) {
|
|
|
2642
2998
|
const wsMod = await import("ws");
|
|
2643
2999
|
const WS = wsMod.default ?? wsMod;
|
|
2644
3000
|
const createWebSocket = (url, opts) => new WS(url, { headers: opts.headers });
|
|
2645
|
-
const clientHtml = await fs5.readFile(
|
|
3001
|
+
const clientHtml = await fs5.readFile(path7.join(clientDir, "index.html"), "utf-8");
|
|
2646
3002
|
const { createServer: createServer2 } = await Promise.resolve().then(() => (init_server(), server_exports));
|
|
2647
3003
|
const server = createServer2({
|
|
2648
3004
|
agent: agentDef,
|
|
@@ -2656,25 +3012,11 @@ async function bootServer(agentDef, clientDir, env, port) {
|
|
|
2656
3012
|
|
|
2657
3013
|
// cli/_dev.ts
|
|
2658
3014
|
async function _startDevServer(cwd, port, log) {
|
|
2659
|
-
const
|
|
2660
|
-
if (!agent) {
|
|
2661
|
-
throw new Error("No agent found \u2014 run `aai init` first");
|
|
2662
|
-
}
|
|
2663
|
-
log(React2.createElement(Step, { action: "Build", msg: agent.slug }));
|
|
2664
|
-
let clientDir;
|
|
2665
|
-
try {
|
|
2666
|
-
const bundle = await bundleAgent(agent);
|
|
2667
|
-
clientDir = bundle.clientDir;
|
|
2668
|
-
} catch (err) {
|
|
2669
|
-
if (err instanceof BundleError) {
|
|
2670
|
-
throw new Error(`Bundle failed: ${err.message}`);
|
|
2671
|
-
}
|
|
2672
|
-
throw err;
|
|
2673
|
-
}
|
|
3015
|
+
const bundle = await buildAgentBundle(cwd, log);
|
|
2674
3016
|
const agentDef = await loadAgentDef(cwd);
|
|
2675
3017
|
const env = await resolveServerEnv();
|
|
2676
|
-
await bootServer(agentDef, clientDir, env, port);
|
|
2677
|
-
log(
|
|
3018
|
+
await bootServer(agentDef, bundle.clientDir, env, port);
|
|
3019
|
+
log(React3.createElement(Step, { action: "Ready", msg: `http://localhost:${port}` }));
|
|
2678
3020
|
}
|
|
2679
3021
|
|
|
2680
3022
|
// cli/dev.tsx
|
|
@@ -2694,7 +3036,7 @@ var devCommandDef = {
|
|
|
2694
3036
|
]
|
|
2695
3037
|
};
|
|
2696
3038
|
async function runDevCommand(args, version) {
|
|
2697
|
-
const parsed =
|
|
3039
|
+
const parsed = minimist4(args, {
|
|
2698
3040
|
string: ["port"],
|
|
2699
3041
|
boolean: ["help", "yes"],
|
|
2700
3042
|
alias: { p: "port", h: "help", y: "yes" }
|
|
@@ -2705,7 +3047,7 @@ async function runDevCommand(args, version) {
|
|
|
2705
3047
|
}
|
|
2706
3048
|
const cwd = process.env.INIT_CWD || process.cwd();
|
|
2707
3049
|
const port = Number.parseInt(parsed.port ?? "3000", 10);
|
|
2708
|
-
if (!await fileExists(
|
|
3050
|
+
if (!await fileExists(path8.join(cwd, "agent.ts"))) {
|
|
2709
3051
|
await runInitCommand(parsed.yes ? ["-y"] : [], version, { quiet: true });
|
|
2710
3052
|
}
|
|
2711
3053
|
await getApiKey();
|
|
@@ -2722,10 +3064,10 @@ init_discover();
|
|
|
2722
3064
|
init_help();
|
|
2723
3065
|
init_ink();
|
|
2724
3066
|
import { render as render3, Text as Text3, useApp as useApp2 } from "ink";
|
|
2725
|
-
import
|
|
3067
|
+
import minimist5 from "minimist";
|
|
2726
3068
|
import pLimit from "p-limit";
|
|
2727
3069
|
import { useEffect, useState as useState2 } from "react";
|
|
2728
|
-
import { Fragment as Fragment2, jsx as
|
|
3070
|
+
import { Fragment as Fragment2, jsx as jsx6, jsxs as jsxs3 } from "react/jsx-runtime";
|
|
2729
3071
|
var ragCommandDef = {
|
|
2730
3072
|
name: "rag",
|
|
2731
3073
|
description: "Ingest a site's llms-full.txt into the vector store",
|
|
@@ -2740,7 +3082,7 @@ var ragCommandDef = {
|
|
|
2740
3082
|
]
|
|
2741
3083
|
};
|
|
2742
3084
|
var FETCH_TIMEOUT_MS = 6e4;
|
|
2743
|
-
var PAD =
|
|
3085
|
+
var PAD = 2;
|
|
2744
3086
|
function RagUI({ url, apiKey, serverUrl, slug, chunkSize, onError }) {
|
|
2745
3087
|
const { exit } = useApp2();
|
|
2746
3088
|
const { items, log } = useStepLog();
|
|
@@ -2768,8 +3110,8 @@ function RagUI({ url, apiKey, serverUrl, slug, chunkSize, onError }) {
|
|
|
2768
3110
|
})();
|
|
2769
3111
|
}, [apiKey, chunkSize, exit, log, onError, serverUrl, slug, url]);
|
|
2770
3112
|
return /* @__PURE__ */ jsxs3(Fragment2, { children: [
|
|
2771
|
-
/* @__PURE__ */
|
|
2772
|
-
err && /* @__PURE__ */
|
|
3113
|
+
/* @__PURE__ */ jsx6(StepLog, { items }),
|
|
3114
|
+
err && /* @__PURE__ */ jsx6(ErrorLine, { msg: err }),
|
|
2773
3115
|
progress && /* @__PURE__ */ jsxs3(Text3, { children: [
|
|
2774
3116
|
" ".repeat(PAD + 1),
|
|
2775
3117
|
"Upsert ",
|
|
@@ -2784,7 +3126,7 @@ function RagUI({ url, apiKey, serverUrl, slug, chunkSize, onError }) {
|
|
|
2784
3126
|
}
|
|
2785
3127
|
async function runRag(opts) {
|
|
2786
3128
|
const { url, apiKey, serverUrl, slug, chunkSize, log, setProgress } = opts;
|
|
2787
|
-
log(/* @__PURE__ */
|
|
3129
|
+
log(/* @__PURE__ */ jsx6(Step, { action: "Fetch", msg: url }));
|
|
2788
3130
|
const resp = await fetch(url, {
|
|
2789
3131
|
headers: { "User-Agent": "aai-cli/1.0" },
|
|
2790
3132
|
redirect: "follow",
|
|
@@ -2795,27 +3137,27 @@ async function runRag(opts) {
|
|
|
2795
3137
|
}
|
|
2796
3138
|
const content = await resp.text();
|
|
2797
3139
|
if (content.length === 0) {
|
|
2798
|
-
log(/* @__PURE__ */
|
|
3140
|
+
log(/* @__PURE__ */ jsx6(Warn, { msg: "File is empty" }));
|
|
2799
3141
|
return;
|
|
2800
3142
|
}
|
|
2801
|
-
log(/* @__PURE__ */
|
|
3143
|
+
log(/* @__PURE__ */ jsx6(Info, { msg: `${(content.length / 1024).toFixed(0)} KB` }));
|
|
2802
3144
|
const origin = new URL(url).origin;
|
|
2803
3145
|
const pages = splitPages(content);
|
|
2804
|
-
log(/* @__PURE__ */
|
|
3146
|
+
log(/* @__PURE__ */ jsx6(Step, { action: "Parse", msg: `${pages.length} pages` }));
|
|
2805
3147
|
const { RecursiveChunker } = await import("@chonkiejs/core");
|
|
2806
3148
|
const chunker = await RecursiveChunker.create({ chunkSize });
|
|
2807
3149
|
const siteSlug = slugify(origin);
|
|
2808
3150
|
const allChunks = await chunkPages(pages, chunker, origin, siteSlug);
|
|
2809
|
-
log(/* @__PURE__ */
|
|
3151
|
+
log(/* @__PURE__ */ jsx6(Step, { action: "Chunk", msg: `${allChunks.length} chunks` }));
|
|
2810
3152
|
const vectorUrl = `${serverUrl}/${slug}/vector`;
|
|
2811
|
-
log(/* @__PURE__ */
|
|
3153
|
+
log(/* @__PURE__ */ jsx6(Info, { msg: `target: ${vectorUrl}` }));
|
|
2812
3154
|
const result = await upsertChunks(allChunks, vectorUrl, apiKey, setProgress);
|
|
2813
|
-
log(/* @__PURE__ */
|
|
3155
|
+
log(/* @__PURE__ */ jsx6(Step, { action: "Done", msg: `${result.upserted} chunks upserted` }));
|
|
2814
3156
|
if (result.errors > 0) {
|
|
2815
|
-
log(/* @__PURE__ */
|
|
2816
|
-
if (result.lastError) log(/* @__PURE__ */
|
|
3157
|
+
log(/* @__PURE__ */ jsx6(Warn, { msg: `${result.errors} failed` }));
|
|
3158
|
+
if (result.lastError) log(/* @__PURE__ */ jsx6(Info, { msg: `last error: ${result.lastError}` }));
|
|
2817
3159
|
}
|
|
2818
|
-
log(/* @__PURE__ */
|
|
3160
|
+
log(/* @__PURE__ */ jsx6(Detail, { msg: `Agent: ${slug}` }));
|
|
2819
3161
|
}
|
|
2820
3162
|
async function chunkPages(pages, chunker, origin, siteSlug) {
|
|
2821
3163
|
const allChunks = [];
|
|
@@ -2884,7 +3226,7 @@ async function upsertChunks(chunks, vectorUrl, apiKey, setProgress) {
|
|
|
2884
3226
|
return { upserted, errors, lastError };
|
|
2885
3227
|
}
|
|
2886
3228
|
async function runRagCommand(args, version) {
|
|
2887
|
-
const parsed =
|
|
3229
|
+
const parsed = minimist5(args, {
|
|
2888
3230
|
string: ["server", "chunk-size"],
|
|
2889
3231
|
boolean: ["help", "yes"],
|
|
2890
3232
|
alias: { s: "server", h: "help", y: "yes" },
|
|
@@ -2916,7 +3258,7 @@ async function runRagCommand(args, version) {
|
|
|
2916
3258
|
const chunkSize = Number.parseInt(parsed["chunk-size"] ?? "512", 10);
|
|
2917
3259
|
let thrownError;
|
|
2918
3260
|
const app = render3(
|
|
2919
|
-
/* @__PURE__ */
|
|
3261
|
+
/* @__PURE__ */ jsx6(
|
|
2920
3262
|
RagUI,
|
|
2921
3263
|
{
|
|
2922
3264
|
url,
|
|
@@ -2984,8 +3326,8 @@ init_discover();
|
|
|
2984
3326
|
init_help();
|
|
2985
3327
|
init_ink();
|
|
2986
3328
|
init_prompts();
|
|
2987
|
-
import
|
|
2988
|
-
import { jsx as
|
|
3329
|
+
import minimist6 from "minimist";
|
|
3330
|
+
import { jsx as jsx7 } from "react/jsx-runtime";
|
|
2989
3331
|
var secretCommandDef = {
|
|
2990
3332
|
name: "secret",
|
|
2991
3333
|
description: "Manage secrets",
|
|
@@ -3003,7 +3345,7 @@ async function requireProjectConfig(cwd) {
|
|
|
3003
3345
|
return config;
|
|
3004
3346
|
}
|
|
3005
3347
|
async function runSecretCommand(args, version) {
|
|
3006
|
-
const parsed =
|
|
3348
|
+
const parsed = minimist6(args, {
|
|
3007
3349
|
boolean: ["help", "yes"],
|
|
3008
3350
|
alias: { h: "help", y: "yes" },
|
|
3009
3351
|
stopEarly: true
|
|
@@ -3058,7 +3400,7 @@ async function secretPut(cwd, name, value) {
|
|
|
3058
3400
|
const text = await resp.text();
|
|
3059
3401
|
throw new Error(`Failed to set secret: ${text}`);
|
|
3060
3402
|
}
|
|
3061
|
-
log(/* @__PURE__ */
|
|
3403
|
+
log(/* @__PURE__ */ jsx7(Step, { action: "Set", msg: `${name} for ${slug}` }));
|
|
3062
3404
|
});
|
|
3063
3405
|
}
|
|
3064
3406
|
async function secretDelete(cwd, name) {
|
|
@@ -3073,7 +3415,7 @@ async function secretDelete(cwd, name) {
|
|
|
3073
3415
|
const text = await resp.text();
|
|
3074
3416
|
throw new Error(`Failed to delete secret: ${text}`);
|
|
3075
3417
|
}
|
|
3076
|
-
log(/* @__PURE__ */
|
|
3418
|
+
log(/* @__PURE__ */ jsx7(Step, { action: "Deleted", msg: `${name} from ${slug}` }));
|
|
3077
3419
|
});
|
|
3078
3420
|
}
|
|
3079
3421
|
async function secretList(cwd) {
|
|
@@ -3088,10 +3430,10 @@ async function secretList(cwd) {
|
|
|
3088
3430
|
}
|
|
3089
3431
|
const { vars } = await resp.json();
|
|
3090
3432
|
if (vars.length === 0) {
|
|
3091
|
-
log(/* @__PURE__ */
|
|
3433
|
+
log(/* @__PURE__ */ jsx7(StepInfo, { action: "Secrets", msg: "none set" }));
|
|
3092
3434
|
} else {
|
|
3093
3435
|
for (const name of vars) {
|
|
3094
|
-
log(/* @__PURE__ */
|
|
3436
|
+
log(/* @__PURE__ */ jsx7(Detail, { msg: name }));
|
|
3095
3437
|
}
|
|
3096
3438
|
}
|
|
3097
3439
|
});
|
|
@@ -3101,25 +3443,24 @@ async function secretList(cwd) {
|
|
|
3101
3443
|
init_discover();
|
|
3102
3444
|
init_help();
|
|
3103
3445
|
init_ink();
|
|
3104
|
-
import
|
|
3105
|
-
import
|
|
3446
|
+
import path10 from "node:path";
|
|
3447
|
+
import minimist7 from "minimist";
|
|
3106
3448
|
|
|
3107
3449
|
// cli/_start.ts
|
|
3108
3450
|
init_ink();
|
|
3109
|
-
import
|
|
3110
|
-
import
|
|
3451
|
+
import path9 from "node:path";
|
|
3452
|
+
import React4 from "react";
|
|
3111
3453
|
async function _startProductionServer(cwd, port, log) {
|
|
3112
|
-
const clientDir =
|
|
3113
|
-
log(
|
|
3454
|
+
const clientDir = path9.join(cwd, ".aai", "client");
|
|
3455
|
+
log(React4.createElement(Step, { action: "Start", msg: "loading agent" }));
|
|
3114
3456
|
const agentDef = await loadAgentDef(cwd);
|
|
3115
3457
|
const env = await resolveServerEnv();
|
|
3116
|
-
log(React3.createElement(Step, { action: "Start", msg: `http://localhost:${port}` }));
|
|
3117
3458
|
await bootServer(agentDef, clientDir, env, port);
|
|
3118
|
-
log(
|
|
3459
|
+
log(React4.createElement(Step, { action: "Ready", msg: `http://localhost:${port}` }));
|
|
3119
3460
|
}
|
|
3120
3461
|
|
|
3121
3462
|
// cli/start.tsx
|
|
3122
|
-
import { jsx as
|
|
3463
|
+
import { jsx as jsx8 } from "react/jsx-runtime";
|
|
3123
3464
|
var startCommandDef = {
|
|
3124
3465
|
name: "start",
|
|
3125
3466
|
description: "Start the production server from a build",
|
|
@@ -3132,7 +3473,7 @@ var startCommandDef = {
|
|
|
3132
3473
|
]
|
|
3133
3474
|
};
|
|
3134
3475
|
async function runStartCommand(args, version) {
|
|
3135
|
-
const parsed =
|
|
3476
|
+
const parsed = minimist7(args, {
|
|
3136
3477
|
string: ["port"],
|
|
3137
3478
|
boolean: ["help", "yes"],
|
|
3138
3479
|
alias: { p: "port", h: "help", y: "yes" }
|
|
@@ -3143,24 +3484,24 @@ async function runStartCommand(args, version) {
|
|
|
3143
3484
|
}
|
|
3144
3485
|
const cwd = process.env.INIT_CWD || process.cwd();
|
|
3145
3486
|
const port = Number.parseInt(parsed.port ?? "3000", 10);
|
|
3146
|
-
const buildDir =
|
|
3147
|
-
if (!await fileExists(
|
|
3487
|
+
const buildDir = path10.join(cwd, ".aai", "build");
|
|
3488
|
+
if (!await fileExists(path10.join(buildDir, "worker.js"))) {
|
|
3148
3489
|
throw new Error("No build found \u2014 run `aai build` first");
|
|
3149
3490
|
}
|
|
3150
3491
|
await getApiKey();
|
|
3151
3492
|
await runWithInk(async (log) => {
|
|
3152
|
-
log(/* @__PURE__ */
|
|
3493
|
+
log(/* @__PURE__ */ jsx8(Step, { action: "Start", msg: `production server on port ${port}` }));
|
|
3153
3494
|
await _startProductionServer(cwd, port, log);
|
|
3154
3495
|
});
|
|
3155
3496
|
}
|
|
3156
3497
|
|
|
3157
3498
|
// cli/cli.ts
|
|
3158
|
-
var cliDir =
|
|
3159
|
-
var pkgJsonPath =
|
|
3499
|
+
var cliDir = path11.dirname(fileURLToPath2(import.meta.url));
|
|
3500
|
+
var pkgJsonPath = path11.join(cliDir, "..", "package.json");
|
|
3160
3501
|
var pkgJson = JSON.parse(readFileSync(pkgJsonPath, "utf-8"));
|
|
3161
3502
|
var VERSION = pkgJson.version;
|
|
3162
3503
|
async function main(args) {
|
|
3163
|
-
const parsed =
|
|
3504
|
+
const parsed = minimist8(args, {
|
|
3164
3505
|
boolean: ["help", "version"],
|
|
3165
3506
|
alias: { h: "help", V: "version" },
|
|
3166
3507
|
stopEarly: true
|
|
@@ -3179,6 +3520,9 @@ async function main(args) {
|
|
|
3179
3520
|
case "init":
|
|
3180
3521
|
await runInitCommand(subArgs, VERSION);
|
|
3181
3522
|
return;
|
|
3523
|
+
case "build":
|
|
3524
|
+
await runBuildCommand(subArgs, VERSION);
|
|
3525
|
+
return;
|
|
3182
3526
|
case "deploy":
|
|
3183
3527
|
await runDeployCommand(subArgs, VERSION);
|
|
3184
3528
|
return;
|