@genesislcap/ai-assistant 14.434.0 → 14.435.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/ai-assistant.api.json +1513 -70
- package/dist/ai-assistant.d.ts +367 -7
- package/dist/dts/components/ai-driver/ai-driver.d.ts +8 -0
- package/dist/dts/components/ai-driver/ai-driver.d.ts.map +1 -1
- package/dist/dts/components/chat-driver/chat-driver.d.ts +79 -3
- package/dist/dts/components/chat-driver/chat-driver.d.ts.map +1 -1
- package/dist/dts/components/orchestrating-driver/orchestrating-driver.d.ts +23 -0
- package/dist/dts/components/orchestrating-driver/orchestrating-driver.d.ts.map +1 -1
- package/dist/dts/config/config.d.ts +106 -2
- package/dist/dts/config/config.d.ts.map +1 -1
- package/dist/dts/config/define-stateful-agent.d.ts +115 -0
- package/dist/dts/config/define-stateful-agent.d.ts.map +1 -0
- package/dist/dts/index.d.ts +1 -0
- package/dist/dts/index.d.ts.map +1 -1
- package/dist/dts/main/main.d.ts +36 -4
- package/dist/dts/main/main.d.ts.map +1 -1
- package/dist/dts/main/main.template.d.ts.map +1 -1
- package/dist/esm/components/chat-driver/chat-driver.js +126 -11
- package/dist/esm/components/orchestrating-driver/orchestrating-driver.js +192 -33
- package/dist/esm/config/define-stateful-agent.js +174 -0
- package/dist/esm/index.js +1 -0
- package/dist/esm/main/main.js +164 -21
- package/dist/esm/main/main.template.js +2 -11
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +16 -16
- package/src/components/ai-driver/ai-driver.ts +9 -0
- package/src/components/chat-driver/chat-driver.ts +178 -8
- package/src/components/orchestrating-driver/orchestrating-driver.ts +191 -17
- package/src/config/config.ts +112 -2
- package/src/config/define-stateful-agent.ts +293 -0
- package/src/index.ts +1 -0
- package/src/main/main.template.ts +2 -9
- package/src/main/main.ts +167 -14
package/dist/ai-assistant.d.ts
CHANGED
|
@@ -129,6 +129,22 @@ export declare interface AgenticActivityEvents {
|
|
|
129
129
|
'chat-popin': undefined;
|
|
130
130
|
}
|
|
131
131
|
|
|
132
|
+
/**
|
|
133
|
+
* Context passed to `onActivate` / `onDeactivate` lifecycle hooks on an agent.
|
|
134
|
+
*
|
|
135
|
+
* @beta
|
|
136
|
+
*/
|
|
137
|
+
export declare interface AgentLifecycleContext {
|
|
138
|
+
/** The agent the hook is firing for. */
|
|
139
|
+
agentName: string;
|
|
140
|
+
/** The assistant session key — stable across reloads, unique per assistant instance. */
|
|
141
|
+
sessionKey: string;
|
|
142
|
+
/** The agent that was active immediately before this one, if any. Only set on `onActivate`. */
|
|
143
|
+
previousAgentName?: string;
|
|
144
|
+
/** Aborted if the session disconnects mid-activation. */
|
|
145
|
+
signal: AbortSignal;
|
|
146
|
+
}
|
|
147
|
+
|
|
132
148
|
/**
|
|
133
149
|
* User-facing agent picker rendered above the chat input.
|
|
134
150
|
*
|
|
@@ -317,6 +333,13 @@ export declare interface AiDriver extends EventTarget {
|
|
|
317
333
|
* Get query suggestions from the AI.
|
|
318
334
|
*/
|
|
319
335
|
getSuggestions(history: ChatMessage[], prompt: string, count: number, allAgentInfo?: AllAgentSummary[]): Promise<string[]>;
|
|
336
|
+
/**
|
|
337
|
+
* Per-LLM-call snapshots — what the model saw each turn (prompt, tools,
|
|
338
|
+
* agent state). Used by the host's debug-log exporter. Optional because the
|
|
339
|
+
* interface is implemented by both leaf and orchestrating drivers; the
|
|
340
|
+
* orchestrator just delegates to its inner `ChatDriver`.
|
|
341
|
+
*/
|
|
342
|
+
getTurnSnapshots?(): ReadonlyArray<TurnSnapshot>;
|
|
320
343
|
}
|
|
321
344
|
|
|
322
345
|
/**
|
|
@@ -357,12 +380,21 @@ declare interface BaseAgentConfig {
|
|
|
357
380
|
name: string;
|
|
358
381
|
/**
|
|
359
382
|
* System prompt injected into every conversation turn for this agent.
|
|
383
|
+
*
|
|
384
|
+
* Either a string (resolved once) or a function resolved each tool-loop
|
|
385
|
+
* iteration — pick the function form when the prompt depends on per-turn state
|
|
386
|
+
* (e.g. a state machine's current step). See {@link SystemPromptInput}.
|
|
360
387
|
*/
|
|
361
|
-
systemPrompt?:
|
|
388
|
+
systemPrompt?: SystemPromptInput;
|
|
362
389
|
/**
|
|
363
390
|
* Tool definitions (JSON Schema) passed to the AI provider for this agent.
|
|
391
|
+
*
|
|
392
|
+
* Either a static array or a function resolved each tool-loop iteration —
|
|
393
|
+
* pick the function form to narrow the tool surface per turn (e.g. expose
|
|
394
|
+
* only the tools valid in the current state of a state machine).
|
|
395
|
+
* See {@link ToolDefinitionsInput}.
|
|
364
396
|
*/
|
|
365
|
-
toolDefinitions?:
|
|
397
|
+
toolDefinitions?: ToolDefinitionsInput;
|
|
366
398
|
/**
|
|
367
399
|
* Tool handler implementations for this agent.
|
|
368
400
|
*/
|
|
@@ -387,6 +419,40 @@ declare interface BaseAgentConfig {
|
|
|
387
419
|
* disabled. See {@link ManualSelectionConfig}.
|
|
388
420
|
*/
|
|
389
421
|
manualSelection?: ManualSelectionConfig;
|
|
422
|
+
/**
|
|
423
|
+
* Fires when this agent becomes the active specialist (including being pinned).
|
|
424
|
+
* Use to instantiate per-agent state that should outlive a single turn — e.g.
|
|
425
|
+
* a state machine the agent owns across the conversation. Awaited before the
|
|
426
|
+
* agent's first turn runs.
|
|
427
|
+
*
|
|
428
|
+
* Capture dependencies (services, redux store refs, etc.) via closure on the
|
|
429
|
+
* host element rather than expecting them on the context.
|
|
430
|
+
*
|
|
431
|
+
* @beta
|
|
432
|
+
*/
|
|
433
|
+
onActivate?: (ctx: AgentLifecycleContext) => void | Promise<void>;
|
|
434
|
+
/**
|
|
435
|
+
* Fires when this agent is being deactivated (the user switches to another
|
|
436
|
+
* agent, the session is torn down, or the agent is unpinned and replaced).
|
|
437
|
+
* Use to dispose per-agent state created in `onActivate`. Awaited before the
|
|
438
|
+
* incoming agent's `onActivate` runs.
|
|
439
|
+
*
|
|
440
|
+
* @beta
|
|
441
|
+
*/
|
|
442
|
+
onDeactivate?: (ctx: AgentLifecycleContext) => void | Promise<void>;
|
|
443
|
+
/**
|
|
444
|
+
* Returns an agent-supplied debug payload for the export log. Called once per
|
|
445
|
+
* LLM call by the driver (alongside the resolved prompt and tool list) and
|
|
446
|
+
* once at log-export time for the latest snapshot. Stateful agents should
|
|
447
|
+
* return their machine state and captured context so the exported timeline
|
|
448
|
+
* captures what drove each turn.
|
|
449
|
+
*
|
|
450
|
+
* Return value must be JSON-serializable. {@link defineStatefulAgent} wires a
|
|
451
|
+
* sensible default that snapshots any machine-shaped state automatically.
|
|
452
|
+
*
|
|
453
|
+
* @beta
|
|
454
|
+
*/
|
|
455
|
+
getDebugSnapshot?: () => unknown;
|
|
390
456
|
}
|
|
391
457
|
|
|
392
458
|
/**
|
|
@@ -406,7 +472,19 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
406
472
|
private busy;
|
|
407
473
|
private pendingInteractions;
|
|
408
474
|
private systemPrompt?;
|
|
475
|
+
/**
|
|
476
|
+
* Resolved tool definitions visible to the LLM. Folds mutate this in place
|
|
477
|
+
* (push/pop on open/close). When `toolDefinitionsFactory` is set, this is
|
|
478
|
+
* overwritten each tool-loop iteration with the factory's output.
|
|
479
|
+
*/
|
|
409
480
|
private toolDefinitions;
|
|
481
|
+
/**
|
|
482
|
+
* Optional dynamic-tools source. When set, called each tool-loop iteration
|
|
483
|
+
* to recompute `toolDefinitions` before the LLM call. `defineStatefulAgent`
|
|
484
|
+
* forbids folds when this is set, so the fold-mutation path is unreachable
|
|
485
|
+
* in that case.
|
|
486
|
+
*/
|
|
487
|
+
private toolDefinitionsFactory?;
|
|
410
488
|
private toolHandlers;
|
|
411
489
|
private primerHistory?;
|
|
412
490
|
private activeAgentName?;
|
|
@@ -438,7 +516,28 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
438
516
|
* `undefined` means the loop has not been stopped early.
|
|
439
517
|
*/
|
|
440
518
|
private subAgentCompletion;
|
|
441
|
-
|
|
519
|
+
/**
|
|
520
|
+
* Set by `releaseAgent` inside a top-level tool handler — typically a stateful
|
|
521
|
+
* agent's terminal-state handler signalling that its flow is complete and the
|
|
522
|
+
* auto-pin lock can release. Checked by the orchestrator after `sendMessage`
|
|
523
|
+
* returns; the orchestrator fires `onDeactivate` and clears the pin.
|
|
524
|
+
*
|
|
525
|
+
* Reset at the start of each `sendMessage` so a release from a previous turn
|
|
526
|
+
* doesn't leak forward.
|
|
527
|
+
*/
|
|
528
|
+
private agentReleaseRequested;
|
|
529
|
+
/**
|
|
530
|
+
* Ring buffer of per-LLM-call snapshots. Cap is configurable via
|
|
531
|
+
* `chatConfig.agent.maxTurnSnapshots`; older entries drop off as new ones
|
|
532
|
+
* arrive. See {@link TurnSnapshot} for the captured shape.
|
|
533
|
+
*/
|
|
534
|
+
private turnSnapshots;
|
|
535
|
+
/** Monotonic counter that survives agent swaps — useful for cross-referencing with history. */
|
|
536
|
+
private globalTurnIndex;
|
|
537
|
+
/** Captured from `applyAgent` so we don't store the whole `AgentConfig`. */
|
|
538
|
+
private debugSnapshotter?;
|
|
539
|
+
private readonly maxTurnSnapshots;
|
|
540
|
+
constructor(aiProvider: AIProvider, toolHandlers?: ChatToolHandlers, toolDefinitions?: ToolDefinitionsInput, systemPrompt?: SystemPromptInput, primerHistory?: ChatMessage[], maxToolIterations?: number, maxFoldOperations?: number, maxTurnSnapshots?: number);
|
|
442
541
|
/**
|
|
443
542
|
* Swap in a new agent's configuration. Called by OrchestratingDriver before
|
|
444
543
|
* each specialist turn so the shared driver runs with the right tools and prompt.
|
|
@@ -451,6 +550,25 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
451
550
|
getSubAgentCompletion(): {
|
|
452
551
|
result: unknown;
|
|
453
552
|
} | undefined;
|
|
553
|
+
/**
|
|
554
|
+
* Returns true if `releaseAgent` was called during the most recent turn.
|
|
555
|
+
* Consumed by the orchestrator to trigger the auto-pin release path.
|
|
556
|
+
*/
|
|
557
|
+
getAgentReleaseRequested(): boolean;
|
|
558
|
+
/**
|
|
559
|
+
* Return the per-turn snapshots captured so far. Used by the host's debug
|
|
560
|
+
* log exporter to show what the LLM saw on each turn — system prompt, tool
|
|
561
|
+
* surface, and agent-supplied state (e.g. a machine snapshot).
|
|
562
|
+
*
|
|
563
|
+
* Ring-buffered at `MAX_TURN_SNAPSHOTS`; older entries are dropped.
|
|
564
|
+
*/
|
|
565
|
+
getTurnSnapshots(): ReadonlyArray<TurnSnapshot>;
|
|
566
|
+
/**
|
|
567
|
+
* Push one snapshot to the ring buffer. Called inside `runToolLoop` just
|
|
568
|
+
* before each LLM call — that's the latest point where the prompt, tool
|
|
569
|
+
* surface, and agent state line up with what the model is about to see.
|
|
570
|
+
*/
|
|
571
|
+
private recordTurnSnapshot;
|
|
454
572
|
/**
|
|
455
573
|
* Optional transform applied to conversation history immediately before each LLM request.
|
|
456
574
|
* Cleared when `undefined`. Does not alter stored history.
|
|
@@ -631,6 +749,33 @@ export declare function createToolFold(config: {
|
|
|
631
749
|
*/
|
|
632
750
|
export declare function defineAgent<const T extends AgentConfig>(config: T): T;
|
|
633
751
|
|
|
752
|
+
/**
|
|
753
|
+
* Build an `AgentConfig` whose `systemPrompt`, `toolDefinitions`, and tool
|
|
754
|
+
* handlers all close over a long-lived state object created on activation.
|
|
755
|
+
*
|
|
756
|
+
* The framework wires the lifecycle: `init` on `onActivate`, `dispose` on
|
|
757
|
+
* `onDeactivate`. State is held inside the helper's closure — never exposed on
|
|
758
|
+
* the resulting `AgentConfig` — so the redux serializer doesn't see it.
|
|
759
|
+
*
|
|
760
|
+
* @example
|
|
761
|
+
* ```ts
|
|
762
|
+
* const guidedBooking = defineStatefulAgent<{ machine: GuidedBookingMachine }>({
|
|
763
|
+
* name: 'Guided Booking',
|
|
764
|
+
* description: 'Books a trade via a guided wizard.',
|
|
765
|
+
* excludeFromClassifier: true,
|
|
766
|
+
* manualSelection: { enabled: true, hint: 'Step-by-step trade booking' },
|
|
767
|
+
* init: () => ({ machine: new GuidedBookingMachine() }),
|
|
768
|
+
* dispose: ({ state }) => state.machine.stop(),
|
|
769
|
+
* systemPrompt: ({ state }) => composeFromMachine(state.machine),
|
|
770
|
+
* toolDefinitions: ({ state }) => toolsForState(state.machine.state),
|
|
771
|
+
* toolHandlers: ({ machine }) => ({ ... }),
|
|
772
|
+
* });
|
|
773
|
+
* ```
|
|
774
|
+
*
|
|
775
|
+
* @beta
|
|
776
|
+
*/
|
|
777
|
+
export declare function defineStatefulAgent<S>(opts: StatefulAgentInit<S>): AgentConfig;
|
|
778
|
+
|
|
634
779
|
/**
|
|
635
780
|
* Expands a flat list of tool definitions into a nested tree by resolving fold
|
|
636
781
|
* metadata from the corresponding handlers. Use this for debug output so the
|
|
@@ -830,6 +975,14 @@ export declare class FoundationAiAssistant extends GenesisElement {
|
|
|
830
975
|
* current agent configuration. Does not wire event listeners or register in
|
|
831
976
|
* the driver registry.
|
|
832
977
|
*/
|
|
978
|
+
/**
|
|
979
|
+
* Warn at config time if any stateful agent (one with lifecycle hooks) is
|
|
980
|
+
* configured in a way that makes it unreachable: `excludeFromClassifier`
|
|
981
|
+
* removes the classifier path, so the only entry left is manual pinning —
|
|
982
|
+
* which requires both `manualSelection.enabled` on the agent and the picker
|
|
983
|
+
* itself being enabled at the assistant level.
|
|
984
|
+
*/
|
|
985
|
+
private warnUnreachableStatefulAgents;
|
|
833
986
|
private createDriver;
|
|
834
987
|
/**
|
|
835
988
|
* Attaches event listeners to the current driver. Stores a cleanup function
|
|
@@ -888,6 +1041,21 @@ export declare class FoundationAiAssistant extends GenesisElement {
|
|
|
888
1041
|
get agentPickerEnabled(): boolean;
|
|
889
1042
|
/** Hint text for the currently pinned agent, if any. Used in the toggle button tooltip. */
|
|
890
1043
|
get pinnedAgentHint(): string | undefined;
|
|
1044
|
+
/**
|
|
1045
|
+
* The pin is locked when a stateful agent (one with lifecycle hooks) is
|
|
1046
|
+
* *actively running* — i.e. its `onActivate` has fired and it owns live
|
|
1047
|
+
* state. Until the user sends their first message, a freshly pinned stateful
|
|
1048
|
+
* agent is not yet active and the picker should remain free; the user might
|
|
1049
|
+
* change their mind and unpin without anything to clean up.
|
|
1050
|
+
*
|
|
1051
|
+
* We derive from `activeAgent` (set by the orchestrator after `onActivate`
|
|
1052
|
+
* completes) rather than `pinnedAgentName` (set immediately on picker
|
|
1053
|
+
* click). The serialized `activeAgent` strips lifecycle hooks, so we look
|
|
1054
|
+
* up the live config from `this.agents` to check for them.
|
|
1055
|
+
*/
|
|
1056
|
+
get pinLocked(): boolean;
|
|
1057
|
+
/** Tooltip shown on the picker toggle button. */
|
|
1058
|
+
get agentToggleTitle(): string;
|
|
891
1059
|
/**
|
|
892
1060
|
* Tint applied to the pin icon when an agent is pinned. Picked from the
|
|
893
1061
|
* brand palette by agent position (modulo the palette length), so each agent
|
|
@@ -912,23 +1080,30 @@ export declare class FoundationAiAssistant extends GenesisElement {
|
|
|
912
1080
|
timestamp: string;
|
|
913
1081
|
host: string;
|
|
914
1082
|
agentSummary: ({
|
|
915
|
-
toolDefinitions: ToolTreeNode[];
|
|
1083
|
+
toolDefinitions: string | ToolTreeNode[];
|
|
916
1084
|
toolHandlers: any;
|
|
1085
|
+
onActivate: any;
|
|
1086
|
+
onDeactivate: any;
|
|
1087
|
+
getDebugSnapshot: any;
|
|
917
1088
|
description: string;
|
|
918
1089
|
fallback?: never;
|
|
1090
|
+
excludeFromClassifier?: boolean;
|
|
919
1091
|
name: string;
|
|
920
|
-
systemPrompt?:
|
|
1092
|
+
systemPrompt?: SystemPromptInput;
|
|
921
1093
|
primerHistory?: ChatMessage[];
|
|
922
1094
|
subAgents?: AgentConfig[];
|
|
923
1095
|
chatInputDuringExecution?: ChatInputDuringExecutionMode;
|
|
924
1096
|
manualSelection?: ManualSelectionConfig;
|
|
925
1097
|
} | {
|
|
926
|
-
toolDefinitions: ToolTreeNode[];
|
|
1098
|
+
toolDefinitions: string | ToolTreeNode[];
|
|
927
1099
|
toolHandlers: any;
|
|
1100
|
+
onActivate: any;
|
|
1101
|
+
onDeactivate: any;
|
|
1102
|
+
getDebugSnapshot: any;
|
|
928
1103
|
fallback: true;
|
|
929
1104
|
description?: never;
|
|
930
1105
|
name: string;
|
|
931
|
-
systemPrompt?:
|
|
1106
|
+
systemPrompt?: SystemPromptInput;
|
|
932
1107
|
primerHistory?: ChatMessage[];
|
|
933
1108
|
subAgents?: AgentConfig[];
|
|
934
1109
|
chatInputDuringExecution?: ChatInputDuringExecutionMode;
|
|
@@ -937,6 +1112,8 @@ export declare class FoundationAiAssistant extends GenesisElement {
|
|
|
937
1112
|
activeSystemPrompt: string;
|
|
938
1113
|
activePrimerHistory: ChatMessage[];
|
|
939
1114
|
activeFoldStack: string[];
|
|
1115
|
+
activeDebugSnapshot: unknown;
|
|
1116
|
+
turnSnapshots: readonly TurnSnapshot[];
|
|
940
1117
|
debug: unknown;
|
|
941
1118
|
};
|
|
942
1119
|
};
|
|
@@ -1056,14 +1233,22 @@ export declare class OrchestratingDriver extends EventTarget implements AiDriver
|
|
|
1056
1233
|
private readonly maxHandoffs;
|
|
1057
1234
|
private readonly classifierHistoryLength;
|
|
1058
1235
|
private readonly classifierRetries;
|
|
1236
|
+
private readonly sessionKey;
|
|
1237
|
+
/**
|
|
1238
|
+
* Aborted on driver disposal. Threaded into `AgentLifecycleContext.signal`
|
|
1239
|
+
* so long-running `onActivate` work can bail if the session disconnects.
|
|
1240
|
+
*/
|
|
1241
|
+
private readonly lifecycleAbortController;
|
|
1059
1242
|
private pinnedAgentName;
|
|
1060
1243
|
activeAgent?: AgentConfig;
|
|
1061
1244
|
constructor(aiProvider: AIProvider, agents: AgentConfig[], options?: {
|
|
1245
|
+
sessionKey?: string;
|
|
1062
1246
|
maxHandoffs?: number;
|
|
1063
1247
|
classifierHistoryLength?: number;
|
|
1064
1248
|
classifierRetries?: number;
|
|
1065
1249
|
maxToolIterations?: number;
|
|
1066
1250
|
maxFoldOperations?: number;
|
|
1251
|
+
maxTurnSnapshots?: number;
|
|
1067
1252
|
});
|
|
1068
1253
|
resolveInteraction(interactionId: string, result: unknown): void;
|
|
1069
1254
|
isBusy(): boolean;
|
|
@@ -1076,10 +1261,24 @@ export declare class OrchestratingDriver extends EventTarget implements AiDriver
|
|
|
1076
1261
|
setPinnedAgent(name: string | null): void;
|
|
1077
1262
|
loadHistory(messages: ChatMessage[]): void;
|
|
1078
1263
|
getRawHistory(): readonly ChatMessage[];
|
|
1264
|
+
/** Delegates to the inner {@link ChatDriver} — turns are captured there. */
|
|
1265
|
+
getTurnSnapshots(): ReadonlyArray<TurnSnapshot>;
|
|
1079
1266
|
getSuggestions(history: ChatMessage[], prompt: string, count: number, allAgentInfo?: AllAgentSummary[]): Promise<string[]>;
|
|
1080
1267
|
sendMessage(input: string, attachments?: ChatAttachment[]): Promise<ChatDriverResult>;
|
|
1081
1268
|
continueFromHistory(transientPrimer?: ChatMessage[]): Promise<ChatDriverResult>;
|
|
1082
1269
|
private applyAgent;
|
|
1270
|
+
/**
|
|
1271
|
+
* Release the current stateful agent: fire `onDeactivate`, clear the pin,
|
|
1272
|
+
* dispatch events so the host (and Redux) reflect the unpinned state. Called
|
|
1273
|
+
* automatically when a tool handler invokes `context.releaseAgent`.
|
|
1274
|
+
*/
|
|
1275
|
+
private releaseActiveAgent;
|
|
1276
|
+
/**
|
|
1277
|
+
* Fire `onDeactivate` on the current active agent and abort any pending
|
|
1278
|
+
* lifecycle work. Called by the host on session teardown so machines can
|
|
1279
|
+
* release resources cleanly.
|
|
1280
|
+
*/
|
|
1281
|
+
dispose(): Promise<void>;
|
|
1083
1282
|
private classify;
|
|
1084
1283
|
/**
|
|
1085
1284
|
* Returns the pinned agent if `pinnedAgentName` matches a known specialist or
|
|
@@ -1118,6 +1317,106 @@ export declare interface SpecialistAgentConfig extends BaseAgentConfig {
|
|
|
1118
1317
|
*/
|
|
1119
1318
|
description: string;
|
|
1120
1319
|
fallback?: never;
|
|
1320
|
+
/**
|
|
1321
|
+
* When `true`, the classifier never auto-routes to this agent. The user can
|
|
1322
|
+
* still select it manually via the picker, provided both prerequisites are
|
|
1323
|
+
* met: this agent has `manualSelection.enabled` set to `true`, *and* the
|
|
1324
|
+
* assistant has the picker enabled via `chatConfig.picker.mode`.
|
|
1325
|
+
*
|
|
1326
|
+
* Use this for agents that overlap heavily with a sibling (e.g. a guided
|
|
1327
|
+
* wizard sitting next to a free-form agent in the same domain) and should
|
|
1328
|
+
* only be reached intentionally rather than via classifier routing.
|
|
1329
|
+
*
|
|
1330
|
+
* @beta
|
|
1331
|
+
*/
|
|
1332
|
+
excludeFromClassifier?: boolean;
|
|
1333
|
+
}
|
|
1334
|
+
|
|
1335
|
+
/**
|
|
1336
|
+
* Init options for {@link defineStatefulAgent}. Generic over the state shape `S`
|
|
1337
|
+
* the agent owns (a state machine, an observable controller, anything).
|
|
1338
|
+
*
|
|
1339
|
+
* The helper threads `state` through `systemPrompt`, `toolDefinitions`, and the
|
|
1340
|
+
* `toolHandlers` factory so consumer code never has to reach for a closure or
|
|
1341
|
+
* a module-level mutable.
|
|
1342
|
+
*
|
|
1343
|
+
* @beta
|
|
1344
|
+
*/
|
|
1345
|
+
export declare interface StatefulAgentInit<S> {
|
|
1346
|
+
/** Display name — must be unique within the agents array. */
|
|
1347
|
+
name: string;
|
|
1348
|
+
/** Plain-language description used by the classifier. Required: stateful agents are always specialists. */
|
|
1349
|
+
description: string;
|
|
1350
|
+
/**
|
|
1351
|
+
* Hide this agent from the classifier — only reachable via manual pinning.
|
|
1352
|
+
* Stateful agents are always specialists; they cannot be the fallback (a
|
|
1353
|
+
* fallback is a leaf invoked when no specialist matches, with no flow to
|
|
1354
|
+
* own state for).
|
|
1355
|
+
*/
|
|
1356
|
+
excludeFromClassifier?: boolean;
|
|
1357
|
+
/** Static primer history prepended to every call (not visible to the user). */
|
|
1358
|
+
primerHistory?: ChatMessage[];
|
|
1359
|
+
/** Sub-agents available to this agent's tool handlers via `requestSubAgent`. */
|
|
1360
|
+
subAgents?: AgentConfig[];
|
|
1361
|
+
/** Opt this agent in to manual picker selection. */
|
|
1362
|
+
manualSelection?: ManualSelectionConfig;
|
|
1363
|
+
/** How the main chat input behaves while this agent is executing. */
|
|
1364
|
+
chatInputDuringExecution?: ChatInputDuringExecutionMode;
|
|
1365
|
+
/**
|
|
1366
|
+
* Construct the agent-scoped state. Called by the framework when this agent
|
|
1367
|
+
* becomes active (`onActivate`). Awaited before the agent's first turn runs.
|
|
1368
|
+
*/
|
|
1369
|
+
init: (ctx: AgentLifecycleContext) => S | Promise<S>;
|
|
1370
|
+
/**
|
|
1371
|
+
* Tear down the agent-scoped state. Called when the agent is being replaced.
|
|
1372
|
+
* Awaited before the incoming agent's `init` runs.
|
|
1373
|
+
*/
|
|
1374
|
+
dispose?: (ctx: AgentLifecycleContext & {
|
|
1375
|
+
state: S;
|
|
1376
|
+
}) => void | Promise<void>;
|
|
1377
|
+
/**
|
|
1378
|
+
* System prompt composed from current state. Resolved each tool-loop
|
|
1379
|
+
* iteration. Use this to feed the LLM whatever the current state implies
|
|
1380
|
+
* (e.g. a state machine's `meta.systemPrompt` plus captured context).
|
|
1381
|
+
*/
|
|
1382
|
+
systemPrompt?: (ctx: SystemPromptContext & {
|
|
1383
|
+
state: S;
|
|
1384
|
+
}) => string | Promise<string>;
|
|
1385
|
+
/**
|
|
1386
|
+
* Tool definitions the LLM sees. Either a static array (resolved once) or a
|
|
1387
|
+
* function resolved each tool-loop iteration. The function form is how a
|
|
1388
|
+
* machine-driven agent narrows the surface per state.
|
|
1389
|
+
*
|
|
1390
|
+
* **Constraint:** the resolved handlers (returned from {@link StatefulAgentInit.toolHandlers})
|
|
1391
|
+
* must not include fold facades. Folds are an LLM-driven UX optimisation
|
|
1392
|
+
* that competes with the machine for control of the tool view; one of them
|
|
1393
|
+
* has to be in charge. Helper throws at init time if a fold-tagged handler
|
|
1394
|
+
* is detected.
|
|
1395
|
+
*/
|
|
1396
|
+
toolDefinitions?: ChatToolDefinition[] | ((ctx: SystemPromptContext & {
|
|
1397
|
+
state: S;
|
|
1398
|
+
}) => ChatToolDefinition[] | Promise<ChatToolDefinition[]>);
|
|
1399
|
+
/**
|
|
1400
|
+
* Factory returning the tool handler map. Called with the live `state` at
|
|
1401
|
+
* `onActivate` time; the handlers it returns are cached for the lifetime of
|
|
1402
|
+
* this activation. Each handler closes over `state` and any other deps you
|
|
1403
|
+
* captured.
|
|
1404
|
+
*
|
|
1405
|
+
* The handler set returned must be the **union** of every tool name your
|
|
1406
|
+
* agent might advertise across all states — `toolDefinitions` filters which
|
|
1407
|
+
* are visible to the LLM per turn, but every name still needs an entry here.
|
|
1408
|
+
*/
|
|
1409
|
+
toolHandlers?: (state: S) => ChatToolHandlers;
|
|
1410
|
+
/**
|
|
1411
|
+
* Optional getter for the debug-log snapshot. Defaults to auto-snapshotting
|
|
1412
|
+
* any property on `state` that looks like a foundation-state-machine
|
|
1413
|
+
* instance (has `state`, `context`, and `complete` fields). Override when
|
|
1414
|
+
* the default doesn't capture what you need — e.g. multiple machines, or
|
|
1415
|
+
* non-machine state worth recording.
|
|
1416
|
+
*
|
|
1417
|
+
* Return value must be JSON-serializable.
|
|
1418
|
+
*/
|
|
1419
|
+
getDebugSnapshot?: (state: S) => unknown;
|
|
1121
1420
|
}
|
|
1122
1421
|
|
|
1123
1422
|
/**
|
|
@@ -1161,6 +1460,32 @@ export declare type SuggestionsState = {
|
|
|
1161
1460
|
message: string;
|
|
1162
1461
|
};
|
|
1163
1462
|
|
|
1463
|
+
/**
|
|
1464
|
+
* Context passed to the function form of `systemPrompt` / `toolDefinitions`.
|
|
1465
|
+
* Resolved each tool-loop iteration so the agent can vary what the LLM sees per turn.
|
|
1466
|
+
*
|
|
1467
|
+
* @beta
|
|
1468
|
+
*/
|
|
1469
|
+
export declare interface SystemPromptContext {
|
|
1470
|
+
/** The active agent's name. */
|
|
1471
|
+
agentName: string;
|
|
1472
|
+
/** Full conversation history up to (but not including) the message being processed. */
|
|
1473
|
+
history: ReadonlyArray<ChatMessage>;
|
|
1474
|
+
/** 0 = first LLM call this turn; > 0 = retry or subsequent tool-loop iteration. */
|
|
1475
|
+
turnIndex: number;
|
|
1476
|
+
/** Aborted if the turn is cancelled. */
|
|
1477
|
+
signal: AbortSignal;
|
|
1478
|
+
}
|
|
1479
|
+
|
|
1480
|
+
/**
|
|
1481
|
+
* System prompt for an agent. Either a static string (resolved once) or a function
|
|
1482
|
+
* resolved each tool-loop iteration. The function form lets the agent compute the
|
|
1483
|
+
* prompt from external state — e.g. a state machine's current step.
|
|
1484
|
+
*
|
|
1485
|
+
* @beta
|
|
1486
|
+
*/
|
|
1487
|
+
export declare type SystemPromptInput = string | ((ctx: SystemPromptContext) => string | Promise<string>);
|
|
1488
|
+
|
|
1164
1489
|
/**
|
|
1165
1490
|
* Symbol used to attach ToolFold metadata to a facade handler function.
|
|
1166
1491
|
* The ChatDriver inspects this to detect fold facades at runtime.
|
|
@@ -1169,6 +1494,16 @@ export declare type SuggestionsState = {
|
|
|
1169
1494
|
*/
|
|
1170
1495
|
export declare const TOOL_FOLD_SYMBOL: unique symbol;
|
|
1171
1496
|
|
|
1497
|
+
/**
|
|
1498
|
+
* Tool definitions for an agent. Either a static array (the conventional shape) or
|
|
1499
|
+
* a function resolved each tool-loop iteration. The function form lets the agent
|
|
1500
|
+
* narrow the tool surface per turn — e.g. expose only the tools valid in the
|
|
1501
|
+
* current state of a state machine.
|
|
1502
|
+
*
|
|
1503
|
+
* @beta
|
|
1504
|
+
*/
|
|
1505
|
+
export declare type ToolDefinitionsInput = ChatToolDefinition[] | ((ctx: SystemPromptContext) => ChatToolDefinition[] | Promise<ChatToolDefinition[]>);
|
|
1506
|
+
|
|
1172
1507
|
/**
|
|
1173
1508
|
* Internal metadata for a tool fold. Attached to the facade handler via TOOL_FOLD_SYMBOL.
|
|
1174
1509
|
*
|
|
@@ -1224,4 +1559,29 @@ export declare interface ToolTreeNode extends ChatToolDefinition {
|
|
|
1224
1559
|
tools?: ToolTreeNode[];
|
|
1225
1560
|
}
|
|
1226
1561
|
|
|
1562
|
+
/**
|
|
1563
|
+
* One captured frame of what the LLM saw on a single tool-loop iteration.
|
|
1564
|
+
* The driver records these as a ring buffer (cap: configurable via
|
|
1565
|
+
* `chatConfig.agent.maxTurnSnapshots`, default 40) so the export log can show,
|
|
1566
|
+
* per turn: which agent was active, the resolved system prompt, the tool names
|
|
1567
|
+
* visible to the LLM, and any agent-supplied debug snapshot (e.g. machine
|
|
1568
|
+
* state for stateful agents).
|
|
1569
|
+
*
|
|
1570
|
+
* @beta
|
|
1571
|
+
*/
|
|
1572
|
+
export declare interface TurnSnapshot {
|
|
1573
|
+
/** Monotonic counter across the driver's lifetime (does not reset on agent swap). */
|
|
1574
|
+
turnIndex: number;
|
|
1575
|
+
/** ISO timestamp captured just before the LLM call. */
|
|
1576
|
+
timestamp: string;
|
|
1577
|
+
/** Name of the agent active when this LLM call ran. */
|
|
1578
|
+
agentName?: string;
|
|
1579
|
+
/** Final system prompt sent to the LLM (post-fold-suffix, post-retry hint). */
|
|
1580
|
+
systemPrompt?: string;
|
|
1581
|
+
/** Tool names sent to the LLM, in order — definitions are static per name so names alone suffice. */
|
|
1582
|
+
toolNames: string[];
|
|
1583
|
+
/** Agent-supplied snapshot — machine state/context for stateful agents, undefined otherwise. */
|
|
1584
|
+
agentSnapshot?: unknown;
|
|
1585
|
+
}
|
|
1586
|
+
|
|
1227
1587
|
export { }
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { ChatAttachment, ChatDriverResult, ChatMessage, ChatToolDefinition } from '@genesislcap/foundation-ai';
|
|
2
|
+
import type { TurnSnapshot } from '../chat-driver/chat-driver';
|
|
2
3
|
/** @internal */
|
|
3
4
|
export interface AllAgentSummary {
|
|
4
5
|
name: string;
|
|
@@ -48,5 +49,12 @@ export interface AiDriver extends EventTarget {
|
|
|
48
49
|
* Get query suggestions from the AI.
|
|
49
50
|
*/
|
|
50
51
|
getSuggestions(history: ChatMessage[], prompt: string, count: number, allAgentInfo?: AllAgentSummary[]): Promise<string[]>;
|
|
52
|
+
/**
|
|
53
|
+
* Per-LLM-call snapshots — what the model saw each turn (prompt, tools,
|
|
54
|
+
* agent state). Used by the host's debug-log exporter. Optional because the
|
|
55
|
+
* interface is implemented by both leaf and orchestrating drivers; the
|
|
56
|
+
* orchestrator just delegates to its inner `ChatDriver`.
|
|
57
|
+
*/
|
|
58
|
+
getTurnSnapshots?(): ReadonlyArray<TurnSnapshot>;
|
|
51
59
|
}
|
|
52
60
|
//# sourceMappingURL=ai-driver.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ai-driver.d.ts","sourceRoot":"","sources":["../../../../src/components/ai-driver/ai-driver.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,cAAc,EACd,gBAAgB,EAChB,WAAW,EACX,kBAAkB,EACnB,MAAM,4BAA4B,CAAC;
|
|
1
|
+
{"version":3,"file":"ai-driver.d.ts","sourceRoot":"","sources":["../../../../src/components/ai-driver/ai-driver.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,cAAc,EACd,gBAAgB,EAChB,WAAW,EACX,kBAAkB,EACnB,MAAM,4BAA4B,CAAC;AACpC,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,4BAA4B,CAAC;AAE/D,gBAAgB;AAChB,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,KAAK,EAAE,kBAAkB,EAAE,CAAC;CAC7B;AAED;;;;;;;;;;GAUG;AACH,MAAM,WAAW,QAAS,SAAQ,WAAW;IAC3C;;OAEG;IACH,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,cAAc,EAAE,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAAC;IAEtF;;;;;OAKG;IACH,mBAAmB,CAAC,eAAe,CAAC,EAAE,WAAW,EAAE,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAAC;IAEhF;;OAEG;IACH,kBAAkB,CAAC,aAAa,EAAE,MAAM,EAAE,MAAM,EAAE,OAAO,GAAG,IAAI,CAAC;IAEjE;;OAEG;IACH,WAAW,CAAC,QAAQ,EAAE,WAAW,EAAE,GAAG,IAAI,CAAC;IAE3C;;OAEG;IACH,aAAa,CAAC,IAAI,SAAS,WAAW,EAAE,CAAC;IAEzC;;OAEG;IACH,MAAM,IAAI,OAAO,CAAC;IAElB;;OAEG;IACH,cAAc,CACZ,OAAO,EAAE,WAAW,EAAE,EACtB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,MAAM,EACb,YAAY,CAAC,EAAE,eAAe,EAAE,GAC/B,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IAErB;;;;;OAKG;IACH,gBAAgB,CAAC,IAAI,aAAa,CAAC,YAAY,CAAC,CAAC;CAClD"}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import type { AIProvider, ChatAttachment, ChatDriverResult, ChatMessage,
|
|
2
|
-
import type { AgentConfig } from '../../config/config';
|
|
1
|
+
import type { AIProvider, ChatAttachment, ChatDriverResult, ChatMessage, ChatToolHandlers } from '@genesislcap/foundation-ai';
|
|
2
|
+
import type { AgentConfig, SystemPromptInput, ToolDefinitionsInput } from '../../config/config';
|
|
3
3
|
import type { AiDriver, AllAgentSummary } from '../ai-driver/ai-driver';
|
|
4
4
|
/** Name reserved for the cross-agent handoff tool — injected by OrchestratingDriver. */
|
|
5
5
|
export declare const REQUEST_CONTINUATION_TOOL = "request_continuation";
|
|
@@ -9,6 +9,30 @@ export declare const REQUEST_CONTINUATION_TOOL = "request_continuation";
|
|
|
9
9
|
* @beta
|
|
10
10
|
*/
|
|
11
11
|
export type ChatHistoryUpdatedEvent = CustomEvent<ReadonlyArray<ChatMessage>>;
|
|
12
|
+
/**
|
|
13
|
+
* One captured frame of what the LLM saw on a single tool-loop iteration.
|
|
14
|
+
* The driver records these as a ring buffer (cap: configurable via
|
|
15
|
+
* `chatConfig.agent.maxTurnSnapshots`, default 40) so the export log can show,
|
|
16
|
+
* per turn: which agent was active, the resolved system prompt, the tool names
|
|
17
|
+
* visible to the LLM, and any agent-supplied debug snapshot (e.g. machine
|
|
18
|
+
* state for stateful agents).
|
|
19
|
+
*
|
|
20
|
+
* @beta
|
|
21
|
+
*/
|
|
22
|
+
export interface TurnSnapshot {
|
|
23
|
+
/** Monotonic counter across the driver's lifetime (does not reset on agent swap). */
|
|
24
|
+
turnIndex: number;
|
|
25
|
+
/** ISO timestamp captured just before the LLM call. */
|
|
26
|
+
timestamp: string;
|
|
27
|
+
/** Name of the agent active when this LLM call ran. */
|
|
28
|
+
agentName?: string;
|
|
29
|
+
/** Final system prompt sent to the LLM (post-fold-suffix, post-retry hint). */
|
|
30
|
+
systemPrompt?: string;
|
|
31
|
+
/** Tool names sent to the LLM, in order — definitions are static per name so names alone suffice. */
|
|
32
|
+
toolNames: string[];
|
|
33
|
+
/** Agent-supplied snapshot — machine state/context for stateful agents, undefined otherwise. */
|
|
34
|
+
agentSnapshot?: unknown;
|
|
35
|
+
}
|
|
12
36
|
/**
|
|
13
37
|
* Plain TS class that drives a multi-turn chat conversation, including the tool-call loop.
|
|
14
38
|
* Owned by `FoundationAiAssistant` — created in `connectedCallback`, torn down in `disconnectedCallback`.
|
|
@@ -26,7 +50,19 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
26
50
|
private busy;
|
|
27
51
|
private pendingInteractions;
|
|
28
52
|
private systemPrompt?;
|
|
53
|
+
/**
|
|
54
|
+
* Resolved tool definitions visible to the LLM. Folds mutate this in place
|
|
55
|
+
* (push/pop on open/close). When `toolDefinitionsFactory` is set, this is
|
|
56
|
+
* overwritten each tool-loop iteration with the factory's output.
|
|
57
|
+
*/
|
|
29
58
|
private toolDefinitions;
|
|
59
|
+
/**
|
|
60
|
+
* Optional dynamic-tools source. When set, called each tool-loop iteration
|
|
61
|
+
* to recompute `toolDefinitions` before the LLM call. `defineStatefulAgent`
|
|
62
|
+
* forbids folds when this is set, so the fold-mutation path is unreachable
|
|
63
|
+
* in that case.
|
|
64
|
+
*/
|
|
65
|
+
private toolDefinitionsFactory?;
|
|
30
66
|
private toolHandlers;
|
|
31
67
|
private primerHistory?;
|
|
32
68
|
private activeAgentName?;
|
|
@@ -58,7 +94,28 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
58
94
|
* `undefined` means the loop has not been stopped early.
|
|
59
95
|
*/
|
|
60
96
|
private subAgentCompletion;
|
|
61
|
-
|
|
97
|
+
/**
|
|
98
|
+
* Set by `releaseAgent` inside a top-level tool handler — typically a stateful
|
|
99
|
+
* agent's terminal-state handler signalling that its flow is complete and the
|
|
100
|
+
* auto-pin lock can release. Checked by the orchestrator after `sendMessage`
|
|
101
|
+
* returns; the orchestrator fires `onDeactivate` and clears the pin.
|
|
102
|
+
*
|
|
103
|
+
* Reset at the start of each `sendMessage` so a release from a previous turn
|
|
104
|
+
* doesn't leak forward.
|
|
105
|
+
*/
|
|
106
|
+
private agentReleaseRequested;
|
|
107
|
+
/**
|
|
108
|
+
* Ring buffer of per-LLM-call snapshots. Cap is configurable via
|
|
109
|
+
* `chatConfig.agent.maxTurnSnapshots`; older entries drop off as new ones
|
|
110
|
+
* arrive. See {@link TurnSnapshot} for the captured shape.
|
|
111
|
+
*/
|
|
112
|
+
private turnSnapshots;
|
|
113
|
+
/** Monotonic counter that survives agent swaps — useful for cross-referencing with history. */
|
|
114
|
+
private globalTurnIndex;
|
|
115
|
+
/** Captured from `applyAgent` so we don't store the whole `AgentConfig`. */
|
|
116
|
+
private debugSnapshotter?;
|
|
117
|
+
private readonly maxTurnSnapshots;
|
|
118
|
+
constructor(aiProvider: AIProvider, toolHandlers?: ChatToolHandlers, toolDefinitions?: ToolDefinitionsInput, systemPrompt?: SystemPromptInput, primerHistory?: ChatMessage[], maxToolIterations?: number, maxFoldOperations?: number, maxTurnSnapshots?: number);
|
|
62
119
|
/**
|
|
63
120
|
* Swap in a new agent's configuration. Called by OrchestratingDriver before
|
|
64
121
|
* each specialist turn so the shared driver runs with the right tools and prompt.
|
|
@@ -71,6 +128,25 @@ export declare class ChatDriver extends EventTarget implements AiDriver {
|
|
|
71
128
|
getSubAgentCompletion(): {
|
|
72
129
|
result: unknown;
|
|
73
130
|
} | undefined;
|
|
131
|
+
/**
|
|
132
|
+
* Returns true if `releaseAgent` was called during the most recent turn.
|
|
133
|
+
* Consumed by the orchestrator to trigger the auto-pin release path.
|
|
134
|
+
*/
|
|
135
|
+
getAgentReleaseRequested(): boolean;
|
|
136
|
+
/**
|
|
137
|
+
* Return the per-turn snapshots captured so far. Used by the host's debug
|
|
138
|
+
* log exporter to show what the LLM saw on each turn — system prompt, tool
|
|
139
|
+
* surface, and agent-supplied state (e.g. a machine snapshot).
|
|
140
|
+
*
|
|
141
|
+
* Ring-buffered at `MAX_TURN_SNAPSHOTS`; older entries are dropped.
|
|
142
|
+
*/
|
|
143
|
+
getTurnSnapshots(): ReadonlyArray<TurnSnapshot>;
|
|
144
|
+
/**
|
|
145
|
+
* Push one snapshot to the ring buffer. Called inside `runToolLoop` just
|
|
146
|
+
* before each LLM call — that's the latest point where the prompt, tool
|
|
147
|
+
* surface, and agent state line up with what the model is about to see.
|
|
148
|
+
*/
|
|
149
|
+
private recordTurnSnapshot;
|
|
74
150
|
/**
|
|
75
151
|
* Optional transform applied to conversation history immediately before each LLM request.
|
|
76
152
|
* Cleared when `undefined`. Does not alter stored history.
|