@adonis-agora/agent
Version:
Governed, durable-backed AI agent (chat + tool-calling + governance) for AdonisJS — part of the Agora ecosystem.
258 lines • 12.8 kB
TypeScript
/**
* A2UI (https://a2ui.org) — Google's declarative agent-to-UI protocol — for this agent's generative
* UI, framework-free. Targets A2UI **v0.9** (the current production family: v0.9.1 is a patch of
* it; v1.0 is a release candidate).
*
* - Outbound: a `ui` frame (one component, or a composed `genui:tree`) becomes a surface — a flat
* list of A2UI components keyed by id — that any A2UI renderer (Lit, Angular, Flutter, React)
* draws. Library builtins map onto A2UI's basic catalog; an app maps its own components with a
* function, or sends them through as custom components of its own A2UI catalog.
* - Streamed: a preview frame the model is still writing becomes the same surface, partially —
* A2UI renderers draw what has arrived and leave a child that is not there yet as a placeholder.
* - Inbound: an A2UI `action` (v0.9) or `userAction` (v0.8) becomes a {@link UiAction}: the next
* user turn.
*/
import type { AgUiEvent, AgUiInterrupt } from '../ag-ui/core/types.js';
import { type UiAction, type UiActionMessage } from '../genui/actions.js';
import type { Catalog } from '../genui/catalog.js';
/** The A2UI protocol version every message is stamped with. */
export declare const A2UI_VERSION = "v0.9";
/** The catalog id of A2UI v0.9's basic catalog (what `@a2ui/react`'s `basicCatalog.id` is). */
export declare const A2UI_BASIC_CATALOG_ID = "https://a2ui.org/specification/v0_9/catalogs/basic/catalog.json";
/**
* The id the AG-UI A2UI binding knows the basic catalog by: `@ag-ui/a2ui-middleware`,
* `@ag-ui/a2ui-toolkit` and CopilotKit's A2UI renderer (1.77, on `@a2ui/web_core` 0.10) register it
* under this earlier v0.9 id, not {@link A2UI_BASIC_CATALOG_ID}. The AG-UI transport's default.
*/
export declare const A2UI_LEGACY_BASIC_CATALOG_ID = "https://a2ui.org/specification/v0_9/basic_catalog.json";
/** Every id the basic catalog goes by: the current one first. */
export declare const A2UI_BASIC_CATALOG_IDS: readonly string[];
/** Whether a catalog id names A2UI v0.9's basic catalog (under either of its ids). */
export declare function isA2uiBasicCatalogId(id: unknown): id is string;
/** The components of A2UI v0.9's basic catalog. */
export declare const A2UI_BASIC_COMPONENTS: readonly ['Text', 'Image', 'Icon', 'Video', 'AudioPlayer', 'Row', 'Column', 'List', 'Card', 'Tabs', 'Modal', 'Divider', 'Button', 'CheckBox', 'TextField', 'DateTimeInput', 'ChoicePicker', 'Slider'];
/** The AG-UI activity type A2UI surfaces travel under (AG-UI's A2UI middleware, CopilotKit). */
export declare const A2UI_ACTIVITY_TYPE = "a2ui-surface";
/** The key of the A2UI messages in an `a2ui-surface` activity's content. */
export declare const A2UI_OPERATIONS_KEY = "a2ui_operations";
/** Action names the transports answer themselves: deciding a parked approval. */
export declare const A2UI_APPROVE_ACTION = "agora.approve";
export declare const A2UI_REJECT_ACTION = "agora.reject";
/** One A2UI component: its id, its catalog type, and its properties flat beside them. */
export interface A2uiComponent {
id: string;
component: string;
[property: string]: unknown;
}
/** One server-to-client A2UI message. */
export type A2uiServerMessage = {
version: typeof A2UI_VERSION;
} & ({
createSurface: {
surfaceId: string;
catalogId: string;
theme?: Record<string, unknown>;
sendDataModel?: boolean;
};
} | {
updateComponents: {
surfaceId: string;
components: A2uiComponent[];
};
} | {
updateDataModel: {
surfaceId: string;
path?: string;
value?: unknown;
};
} | {
deleteSurface: {
surfaceId: string;
};
});
/** What a mapper is handed for one node. */
export interface A2uiMapContext {
/** The id the node's root component MUST take (its parent references it). */
id: string;
/** The ids of the node's children, already converted (a layout lists them). */
children: readonly string[];
/** A fresh id derived from the node's (`<id>~<suffix>`), for the extra components a mapping needs. */
derive(suffix: string): string;
/** The node is still being written (a preview): props may be missing — default them. */
incomplete: boolean;
/** The component's plain-text fallback (`fallbackText`), for a mapping that only has text. */
text(): string;
}
/**
* Maps one of this agent's components to A2UI components. Must return a component whose `id` is
* `ctx.id`; any others it adds take ids from `ctx.derive`.
*/
export type A2uiMapper = (props: Record<string, unknown>, ctx: A2uiMapContext) => A2uiComponent[];
export interface A2uiOptions {
/**
* The A2UI catalog surfaces are created with. Default the basic catalog. An app that registers
* its own components on the client names its catalog here (and lists them in `custom`). Either id
* of the basic catalog ({@link A2UI_BASIC_CATALOG_IDS}) means "the basic catalog": the id the
* client advertises for it wins.
*/
catalogId?: string;
/**
* The id the client knows the basic catalog by — what text, approval and error surfaces (always
* basic) are created with, and `catalogId`'s default. Normally left unset: each transport picks
* it from the catalogs the client advertises (`a2uiClientCapabilities`), else uses its own
* default ({@link A2UI_BASIC_CATALOG_ID} on the A2UI route, {@link A2UI_LEGACY_BASIC_CATALOG_ID}
* over AG-UI).
*/
basicCatalogId?: string;
/**
* Create every surface with `sendDataModel: true`: the client sends the surface's data model back
* with its next message (`a2uiClientDataModel`), which the A2UI route hands the prompt builder as
* `pageContext.a2uiDataModel`.
*/
sendDataModel?: boolean;
/** Per component: a mapping to A2UI (overrides a builtin's), or `'custom'` to send it as is. */
components?: Record<string, A2uiMapper | 'custom'>;
/**
* A component with no mapping: `'text'` (default) draws its `fallbackText` as an A2UI `Text`;
* `'custom'` sends it as a custom component of the same name, props flat (the client's catalog
* must have it).
*/
unmapped?: 'text' | 'custom';
/** The agent's catalog: what unmapped components' text comes from. */
catalog?: Catalog;
/** `createSurface.theme` (basic catalog: `primaryColor`, `agentDisplayName`, `iconUrl`). */
theme?: Record<string, unknown>;
}
/** The library builtins, mapped onto A2UI's basic catalog. */
export declare const A2UI_BUILTIN_MAPPERS: Readonly<Record<string, A2uiMapper>>;
/**
* A `ui` frame as A2UI components, flat, the root's id `root`. A composed tree (`genui:tree`) maps
* node by node — node ids are their positions (`root`, `root.0`, `root.0.2`), stable from the first
* preview to the final frame, so a streamed surface only ever grows. A node still held back
* (`held`) is left out: its parent references an id that arrives later, which A2UI draws as a
* placeholder.
*/
export declare function toA2uiComponents(frame: {
component: string;
props: unknown;
}, options?: A2uiOptions): A2uiComponent[];
/** The messages that draw (or redraw) a surface: `createSurface` the first time, then its components. */
export declare function a2uiSurfaceMessages(surfaceId: string, components: A2uiComponent[], options: A2uiOptions & {
create: boolean;
sendDataModel?: boolean;
}): A2uiServerMessage[];
/** A surface id A2UI clients accept, from a `ui` frame id (`<toolCallId>:ui:0`). */
export declare function a2uiSurfaceId(frameId: string): string;
/**
* A2UI's AG-UI binding (the AG-UI A2UI middleware, CopilotKit's renderer): one `ACTIVITY_SNAPSHOT`
* of type `a2ui-surface` per `ui` frame, carrying the whole surface (`createSurface` +
* `updateComponents`) with `replace: true` — so each preview of a streaming tree repaints the same
* activity in place, keyed by the frame id.
*/
export declare function a2uiActivityEvent(frame: {
id: string;
component: string;
props: unknown;
partial?: boolean;
}, options?: A2uiOptions): AgUiEvent | null;
/**
* An A2UI catalog definition (v0.9 inline catalog shape) for an agent catalog's components sent
* as custom components: `{ catalogId, components: { Name: JSON Schema } }` — what a client
* registers, or hands an A2UI-aware runtime (`a2uiClientCapabilities.inlineCatalogs`).
*/
export declare function a2uiCatalog(catalog: Catalog, options: {
catalogId: string;
only?: readonly string[];
}): {
catalogId: string;
components: Record<string, Record<string, unknown>>;
};
/**
* A client-to-server A2UI message, or an AG-UI `forwardedProps.a2uiAction`, as a {@link UiAction}:
* v0.9 `{ version, action: { name, surfaceId, sourceComponentId, timestamp, context } }`, v0.8
* `{ userAction: { … } }`, or the bare action object. A string when it is not one.
*/
export declare function readA2uiAction(raw: unknown, options?: {
maxBytes?: number;
}): UiAction | string;
/** The surface an approval interrupt is shown on: its message, and Approve / Reject buttons. */
export declare function a2uiApprovalComponents(interrupt: AgUiInterrupt): A2uiComponent[];
export interface A2uiStreamOptions extends A2uiOptions {
/**
* Assistant text: `'surface'` (default) streams it into a surface of its own — one `Text` bound
* to `/text` in the data model, updated as tokens arrive; `'omit'` leaves text out (UI only).
*/
text?: 'surface' | 'omit';
}
/**
* One AG-UI run as an A2UI message stream — the projection the A2UI transport serves. Stateful
* (which surfaces exist), pure otherwise: feed it the run's AG-UI events in order.
*
* - `CUSTOM agora.ui` → a surface per `ui` frame id, created once and updated in place (previews
* included); a withdrawn preview deletes it;
* - text messages → a text surface each (see {@link A2uiStreamOptions.text});
* - an approval interrupt → a surface with Approve / Reject buttons ({@link A2UI_APPROVE_ACTION});
* any other interrupt → a text surface saying to answer it in the app;
* - `RUN_ERROR` → a text surface with the message.
*/
export declare class A2uiProjector {
private readonly options;
private readonly surfaces;
private readonly texts;
constructor(options?: A2uiStreamOptions);
project(event: AgUiEvent): A2uiServerMessage[];
private surface;
private ui;
}
/**
* The catalog ids a client says it draws, from its `a2uiClientCapabilities`: v0.9's
* `{ 'v0.9': { supportedCatalogIds } }` (what `MessageProcessor.getRendererCapabilities()` builds),
* a `v0.9.1` entry, or a flat `{ supportedCatalogIds }`. `undefined` when it names none.
*/
export declare function readA2uiClientCapabilities(raw: unknown): string[] | undefined;
/**
* The catalog ids an AG-UI client advertises: `forwardedProps.a2uiClientCapabilities`, or the
* `context` entry CopilotKit's A2UI provider adds (its value lists the ids, one `- <id>` per line).
*/
export declare function readAgUiA2uiCatalogIds(input: {
forwardedProps?: unknown;
context?: readonly unknown[];
}): string[] | undefined;
/**
* Options for one client: the basic catalog under the id the client advertises (else the
* configured `basicCatalogId`, a basic `catalogId`, or the transport's `fallback`), and `catalogId`
* resolved — an app catalog stays as configured; the basic catalog takes the negotiated id.
*/
export declare function negotiateA2uiCatalog(options: A2uiOptions, supported: readonly string[] | undefined, fallback?: string): A2uiOptions;
/** One stored message, as much of it as a replay reads. */
export interface A2uiStoredMessage {
id: string;
role: string;
content: string;
ui?: readonly {
id: string;
component: string;
props: unknown;
partial?: true;
}[];
}
/** One entry of a replayed thread: the user's line, or an assistant step's surfaces. */
export type A2uiReplayEntry = {
role: 'user';
id: string;
text: string;
/** The message was a UI action: its parts (draw `action.text`; the values are the model's). */
action?: UiActionMessage;
} | {
role: 'assistant';
id: string;
messages: A2uiServerMessage[];
};
/**
* A stored thread as A2UI, for a client that reopens it: each user message as its line, each
* assistant step as the surfaces the live stream drew — its text (one `Text`), then every `ui`
* frame it kept (the last props per id), mapped exactly as the stream maps them, under the same
* surface ids. An approval the thread is still waiting on is not redrawn: ask again by sending.
*/
export declare function a2uiThreadReplay(messages: readonly A2uiStoredMessage[], options?: A2uiStreamOptions): A2uiReplayEntry[];
//# sourceMappingURL=core.d.ts.map