import type { Event, Provider, Session as SessionData, SessionState } from "@aexhq/brain/session"; import type { NetworkPolicy, WebSocketFactory } from "@aexhq/brain"; import * as z from "zod"; import type { EventOptions } from "./transport.js"; import { Transport } from "./transport.js"; import type { Tool } from "./tools.js"; import { SessionChildren, SessionSandbox, SessionStorage } from "./resources.js"; export type SessionInput = string; export interface ModelOptions { provider: Provider; name: string; apiKey: string; baseUrl?: string; maxOutputTokens?: number; /** Immutable context capacity used for admission and compaction; Brain never guesses by name. */ contextWindowTokens?: number; temperature?: number; reasoningEffort?: "low" | "medium" | "high"; } /** * A built agentloop implementation, as exported by a loop package or produced by * `buildLoopBundle` from `@aexhq/agentloop`. Assignment is by import, never by name: * the sealed identity is the content digest plus the pinned toolchain. */ export interface AgentloopBundle { /** The complete deterministic ESM source bundle — the exact bytes sealed and uploaded. */ source: string; /** SHA-256 hex of the UTF-8 source bytes. */ sha256: string; /** The pinned loop-toolchain identity the bundle was built for. */ toolchain: string; } export interface CreateSessionOptions { model: ModelOptions; /** Omitted or empty grants no tools. A non-empty list is the exact grant. */ tools?: readonly Tool[]; /** * The agentloop driving this session's turns, assigned by importing its implementation. * Sealed at create for the life of the session; children inherit it. Omission seals the * official aex loop. */ agentloop?: AgentloopBundle; systemPrompt?: string; /** Write-only values for environment names declared by managed Tools. */ secrets?: Record; /** Maximum direct outbound network authority sealed for managed sandboxes. Omission is deny-all. */ network?: NetworkPolicy; /** Replacement attempts after an unrecoverable provider outcome. Defaults to one. */ providerRecoveryRetries?: 0 | 1; client?: { /** Replacement sends to the same customer process and operation. Defaults to one. */ submitRetries?: 0 | 1; }; /** Optional ceilings for durable child sessions. Omitted fields use the hosted defaults. */ children?: { maxDepth?: number; maxDirectChildren?: number; maxDescendants?: number; }; metadata?: Record; } export interface RequestOptions { signal?: AbortSignal; idempotencyKey?: string; metadata?: Record; } export interface OutputOptions extends RequestOptions { output: Schema; /** Extra attempts after the first invalid candidate. Defaults to 1; maximum 2. */ outputRetries?: 0 | 1 | 2; } export interface ListSessionsOptions { limit?: number; cursor?: string; state?: SessionState; signal?: AbortSignal; } export interface SessionList { data: Session[]; hasMore: boolean; nextCursor?: string; } export interface ModelSummary { provider: Provider; name: string; baseUrl?: string; contextWindowTokens: number; } export interface SessionSummary { id: string; parentId: string | undefined; rootId: string; depth: number; state: SessionState; turnState: SessionData["turn_state"]; model: ModelSummary; createdAt: string; updatedAt: string; metadata: Readonly>; } export declare class Sessions { #private; constructor(transport: Transport, webSocketFactory?: WebSocketFactory, clientId?: string); /** @internal Called by `Aex.close()`. */ close(): void; create(options: CreateSessionOptions, request?: RequestOptions): Promise; get(id: string, options?: Pick): Promise; list(options?: ListSessionsOptions): Promise; } export declare class Session implements SessionSummary { #private; readonly sandbox: SessionSandbox; readonly storage: SessionStorage; readonly children: SessionChildren; constructor(transport: Transport, data: SessionData); get id(): string; get state(): SessionState; get turnState(): SessionData["turn_state"]; get parentId(): string | undefined; get rootId(): string; get depth(): number; get model(): ModelSummary; get createdAt(): string; get updatedAt(): string; get metadata(): Readonly>; refresh(options?: Pick): Promise; send(input: SessionInput, options?: RequestOptions): Promise; send(input: SessionInput, options: OutputOptions): Promise>; /** * Raw, attempt-aware event stream. Provisional frames have no durable cursor and may later be * superseded; consumers rendering them must key by `attempt_id` and process * `model.attempt_superseded`. Use `send()` when only the durable winning answer is needed. */ events(options?: EventOptions): AsyncGenerator; cancel(options?: Pick): Promise; end(options?: Pick): Promise; delete(options?: Pick & { queue?: boolean; }): Promise; private markIdle; }