/**
 * Canonical provider-neutral message and streaming vocabulary for the loop,
 * session log, and plugins. Adapters alone translate provider wire messages;
 * mapped interfaces make the content, source, and finish unions extensible.
 */
import type { Branded } from '@deepseek-ai/dsh-brand';
import type { ImageAttachmentRef } from '@deepseek-ai/dsh-attachment';
import type { CallId, ProviderRequestId, ReasoningEffortId } from './brand.ts';
import type { Message } from './message.ts';
declare module '@deepseek-ai/cordis' {
    interface Events {
        /**
         * The provider topology changed: an adapter registered or unregistered
         * routes, or the configurable-provider directory gained or lost entries.
         * This payload-free registry notification fires at each commit point
         * (including registration disposal); consumers re-read `listProviders()`,
         * `listModels()`, or `listConfigurableProviders()` for the new state.
         * Observer failures are contained and cannot veto the registry mutation.
         * @mode emit
         */
        'llm/adapters-updated'(): void;
    }
}
export type { AssistantMessage, AssistantProvenance, Message, MessageSource, MessageSourceMap, ModelMessageSource, ToolMessageSource, ToolResultMessage, UserMessage, } from './message.ts';
/** Serializable provider or transport failure facts; policy decides whether they are retryable. */
export interface LlmFailure {
    /** Human-readable provider or transport failure. */
    readonly message: string;
    /** Stable provider-neutral machine-routing code. */
    readonly code: string;
    /** HTTP status returned by the provider, when available. */
    readonly status?: number;
    /** Provider-requested delay in milliseconds, when valid and available. */
    readonly providerRetryAfterMs?: number;
    /** Opaque provider-issued request identifier for diagnostics. */
    readonly requestId?: ProviderRequestId;
}
/** Plain text visible to the end user. */
export interface TextBlock {
    type: 'text';
    text: string;
}
/** Reasoning / thinking content, distinct from visible text. */
export interface ReasoningBlock {
    type: 'reasoning';
    text: string;
}
/**
 * A durable raster image reference, valid in user or assistant content. The
 * block is deliberately role-neutral; assistant-side rendering is forward
 * compatibility — the current production adapters declare text-only output,
 * so only user content carries images today.
 */
export interface ImageBlock {
    type: 'image';
    /** Immutable bytes and intrinsic display metadata owned by the attachment service. */
    attachment: ImageAttachmentRef;
}
/** A tool invocation requested by the model. */
export interface ToolCallBlock {
    type: 'tool-call';
    /** Provider-issued call id; correlates with the matching tool result. */
    id: CallId;
    name: string;
    /** Raw JSON string as produced by the model. */
    arguments: string;
}
/** The result of a tool invocation, sent back to the model. */
export interface ToolResultBlock {
    type: 'tool-result';
    toolCallId: CallId;
    content: ContentBlock[];
    isError?: boolean;
}
/**
 * Merge-extensible content blocks keyed by `type`. New core blocks must land
 * with adapter, UI, and compaction support.
 */
export interface ContentBlockMap {
    'text': TextBlock;
    'reasoning': ReasoningBlock;
    'image': ImageBlock;
    'tool-call': ToolCallBlock;
    'tool-result': ToolResultBlock;
}
/** The block `type` tag vocabulary; widens as plugins add entries to {@link ContentBlockMap}. */
export type ContentBlockType = keyof ContentBlockMap;
/** Any known content block, derived from {@link ContentBlockMap}; switch on `type` and fall through unknowns (merge-extensible). */
export type ContentBlock = ContentBlockMap[ContentBlockType];
/**
 * Why a model response stopped.
 * Merge-extensible so adapters can surface provider-specific reasons.
 */
export interface FinishReasonMap {
    'stop': {
        kind: 'stop';
    };
    'tool-calls': {
        kind: 'tool-calls';
    };
    'max-tokens': {
        kind: 'max-tokens';
    };
    'aborted': {
        kind: 'aborted';
        failure: LlmFailure;
    };
    'error': {
        kind: 'error';
        failure: LlmFailure;
    };
}
/** Any known finish reason, derived from {@link FinishReasonMap}; switch on `kind` and fall through unknowns (merge-extensible). */
export type FinishReason = FinishReasonMap[keyof FinishReasonMap];
/**
 * Token accounting for one model call (cache fields are optional).
 *
 * Counts are DISJOINT: `inputTokens` is uncached input only; cached input is
 * reported separately as `cacheReadTokens`/`cacheWriteTokens` (billed input =
 * sum of the three). Adapters whose providers fold cache hits into a total
 * prompt count (DeepSeek's `prompt_tokens`) subtract them out.
 */
export interface TokenUsage {
    inputTokens: number;
    outputTokens: number;
    cacheReadTokens?: number;
    cacheWriteTokens?: number;
    reasoningTokens?: number;
}
/** Display metadata for one registered provider route. */
export interface LlmProviderInfo {
    /** Provider route key used by {@link GenerateOptions.provider}. */
    id: string;
    /** Human-readable provider name for selectors and diagnostics. */
    name: string;
}
/** Merge-extensible provider model modality vocabulary. */
export interface ModelModalityMap {
    text: 'text';
    image: 'image';
}
/** Any declared provider model modality. */
export type ModelModality = ModelModalityMap[keyof ModelModalityMap];
/**
 * One provider route an adapter plugin can activate through configuration,
 * whether or not the route is currently registered. Configuration surfaces
 * merge this directory with `listProviders()` to offer every configurable
 * provider alongside its live/dormant state.
 */
export interface LlmConfigurableProvider {
    /** Provider route key this entry activates when configured. */
    provider: string;
    /** Human-readable provider name for configuration surfaces. */
    displayName: string;
    /** User-settings namespace whose section configures this provider. */
    settingsNs: string;
    /**
     * Path from that namespace's section root to this provider's profile
     * object; empty when the whole section is the profile.
     */
    settingsPath: readonly string[];
    /**
     * Whether the owning adapter knows this route only because configuration
     * declared it — a gateway or self-hosted server it ships nothing about.
     * Absent means the adapter draws no such distinction; false means it does
     * and this route is one of its own. Only the adapter can answer: a stored
     * profile is how a user-added route AND a corrected shipped one both look
     * from outside.
     */
    declared?: boolean;
}
/**
 * One interrogation of a provider endpoint that configuration has not stored
 * yet. Configuration surfaces send the draft a user is still editing, so the
 * request carries the endpoint and credential directly instead of naming a
 * route: a provider being added has no route to name.
 */
export interface LlmModelDiscoveryRequest {
    /**
     * Route the draft is editing, when it edits an existing one. A route whose
     * adapter already knows its models answers from that knowledge instead of
     * asking the endpoint — the adapter's own registry is the better answer, and
     * it costs no network call.
     */
    provider?: string;
    /**
     * Endpoint to interrogate. Optional because a route the adapter already
     * describes needs none; a route it does not must supply one.
     */
    baseURL?: string;
    /** Wire protocol the endpoint speaks, when the draft names one. */
    api?: string;
    /** Credential for this interrogation alone; the harness never stores it. */
    apiKey?: string;
    /** Caller cancellation; implementations must settle promptly after it aborts. */
    signal?: AbortSignal;
}
/**
 * One model an endpoint reports about itself. Every field but the id is
 * optional because most provider listings disclose an id and nothing else;
 * a surface adopting one of these still owes the capacities its adapter needs.
 */
export interface LlmDiscoveredModel {
    /** Model id the endpoint accepts. */
    id: string;
    /** Human-readable name when the endpoint supplies one. */
    name?: string;
    /** Maximum combined request and response context, when disclosed. */
    contextWindow?: number;
    /** Maximum output tokens, when disclosed. */
    maxTokens?: number;
}
/** One adapter-discovered model; catalog membership is advisory, not request validation. */
export interface LlmModelInfo {
    /** Provider route that owns this model entry. */
    provider: string;
    /** Model id passed to {@link GenerateOptions.model}. */
    id: string;
    /** Human-readable model name for selectors. */
    name: string;
    /** Optional user-facing distinction from otherwise similar models. */
    description?: string;
    /** Accepted request modalities; absent means unknown, while an explicit omission is negative capability. */
    inputModalities?: readonly ModelModality[];
}
/** Provider-owned context capacity for one exact provider/model route. */
export interface LlmModelContext {
    /** Maximum combined request and response context in tokens. */
    contextWindow: number;
}
/** Display metadata for one adapter-owned reasoning effort. */
export interface LlmReasoningEffortInfo {
    /** Opaque stable value accepted by {@link GenerateOptions.reasoningEffort}. */
    id: ReasoningEffortId;
    /** Human-readable effort name for selectors and diagnostics. */
    name: string;
    /** Optional user-facing distinction from otherwise similar efforts. */
    description?: string;
}
/** Selectable reasoning efforts for one exact provider/model route. */
export interface LlmModelReasoningInfo {
    /** Supported efforts in adapter-preferred display order. */
    efforts: readonly LlmReasoningEffortInfo[];
    /**
     * Adapter-configured default materialized into requests when callers omit
     * an effort. Absence preserves the provider's own default.
     */
    defaultEffort?: ReasoningEffortId;
}
/** Exact-route model metadata resolved by its owning adapter. */
export interface LlmResolvedModelInfo extends LlmModelInfo {
    /** Provider-owned context capacity when known. */
    context?: LlmModelContext;
    /** Adapter-configured per-request output cap materialized when callers omit one. */
    defaultMaxTokens?: number;
    /** Adapter-owned selectable reasoning levels when exposed. */
    reasoning?: LlmModelReasoningInfo;
}
/**
 * Adapter-private lossless-JSON state for replaying a successful response,
 * carried by a terminal `finish` chunk and stored on the assembled assistant
 * message's model source. Both halves stay opaque to the harness; only the
 * split is shared vocabulary, so assembly can keep stored metadata aligned
 * with stored content without reading either half.
 */
export interface ReplayEnvelope {
    /** Response-level adapter-private metadata (ids, native stop reason). */
    response: unknown;
    /**
     * Per-block adapter-private metadata, one entry per emitted block in
     * first-seen stream order. When assembly drops a block it drops the entry at
     * the same position; entries whose length does not match the emitted block
     * count discard the whole envelope. An adapter whose metadata is independent
     * of block structure omits this field and the envelope passes through
     * assembly unchanged.
     */
    blocks?: readonly unknown[];
}
/**
 * Raw streaming protocol emitted by adapters.
 * Block indexes correlate interleaved deltas, and `block-end` carries the
 * assembled block. Adapters emit usage before the terminal finish and nothing
 * afterward; tool arguments remain raw JSON strings. An adapter implementation
 * may throw, but `LlmRuntime.stream()` normalizes that failure to a terminal
 * `error` or `aborted` finish before exposing it to consumers.
 */
export type StreamChunk = {
    type: 'block-start';
    index: number;
    blockType: ContentBlockType;
} | {
    type: 'text-delta';
    index: number;
    text: string;
} | {
    type: 'reasoning-delta';
    index: number;
    text: string;
} | {
    type: 'tool-call-delta';
    index: number;
    id: CallId;
    name?: string;
    argumentsDelta: string;
} | {
    type: 'block-end';
    index: number;
    block: ContentBlock;
} | {
    type: 'usage';
    usage: TokenUsage;
} | {
    type: 'finish';
    reason: FinishReason;
    /** Replay metadata for a successful response; see {@link ReplayEnvelope}. */
    replayState?: ReplayEnvelope;
};
/**
 * JSON-schema description of a tool, as sent to the model.
 *
 * Declared here (not in dsh-tools) because it is part of {@link GenerateOptions};
 * dsh-tools' ToolDefinition and dsh-system-prompt's PromptAssembly both import
 * it from this package.
 */
export interface ToolSchema {
    name: string;
    description: string;
    /** JSON Schema object for the arguments. */
    parameters: Record<string, unknown>;
}
/** A single model request, fully assembled. */
export interface GenerateOptions {
    /** Registered provider route selecting the adapter instance. */
    provider: string;
    model: string;
    /** Adapter-owned reasoning effort selected for this exact model. */
    reasoningEffort?: ReasoningEffortId;
    /**
     * Ordered conversation messages, exactly as the provider sees them (after
     * the `system` slot). A loop-built request assembles them as
     * the derived history (dsh-agent-loop); a hand-built one-shot passes any list.
     */
    messages: Message[];
    /** System prompt text (adapters map to the provider's system slot). */
    system?: string;
    /** Tool schemas (adapters map to the provider's `tools` field). */
    tools?: ToolSchema[];
    temperature?: number;
    maxTokens?: number;
    /**
     * Stop sequences: generation halts as soon as the model produces any one of
     * these strings (adapters map to the provider's stop field, e.g. OpenAI
     * `stop`). The stop string itself is not included in the output.
     */
    stop?: string[];
    signal?: AbortSignal;
    /**
     * Session identity stamped by the loop for request routing. Replay uses it
     * to separate cursors; adapters may map it to model-hidden transport metadata.
     */
    sessionId?: Branded<'SessionId'>;
    /**
     * Provider-neutral classification for an auxiliary model call. Adapters may
     * map the purpose to model-hidden transport metadata or purpose-specific
     * generation policy. Ordinary conversation requests leave it unset.
     */
    purpose?: 'compaction' | 'session-title';
}
//# sourceMappingURL=types.d.ts.map