export type AIUsage = {
    inputTokens: number;
    outputTokens: number;
};
export type RAGSource = {
    chunkId: string;
    score: number;
    text: string;
    title?: string;
    source?: string;
    metadata?: Record<string, unknown>;
};
export type RAGDocumentChunk = {
    chunkId: string;
    text: string;
    title?: string;
    source?: string;
    metadata?: Record<string, unknown>;
    embedding?: number[];
};
export type RAGQueryInput = {
    queryVector: number[];
    topK: number;
    filter?: Record<string, unknown>;
};
export type RAGQueryResult = {
    chunkId: string;
    score: number;
    chunkText: string;
    title?: string;
    source?: string;
    metadata?: Record<string, unknown>;
};
export type RAGUpsertInput = {
    chunks: RAGDocumentChunk[];
};
export type SQLiteVecResolutionSource = 'absolute-package' | 'explicit' | 'env' | 'database';
export type SQLiteVecResolutionStatus = 'resolved' | 'not_configured' | 'unsupported_platform' | 'package_not_installed' | 'binary_missing' | 'package_invalid';
export type SQLiteVecResolution = {
    status: SQLiteVecResolutionStatus;
    source: SQLiteVecResolutionSource;
    platformKey: string;
    packageName?: string;
    packageVersion?: string;
    packageRoot?: string;
    libraryFile?: string;
    libraryPath?: string;
    reason?: string;
};
export type RAGSQLiteNativeDiagnostics = {
    requested: boolean;
    available: boolean;
    active: boolean;
    mode?: 'vec0';
    tableName?: string;
    distanceMetric?: 'cosine' | 'l2';
    resolution?: SQLiteVecResolution;
    fallbackReason?: string;
    lastLoadError?: string;
    lastQueryError?: string;
    lastUpsertError?: string;
};
export type RAGVectorStoreStatus = {
    backend: 'in_memory' | 'sqlite';
    vectorMode: 'in_memory' | 'json_fallback' | 'native_vec0';
    dimensions?: number;
    native?: RAGSQLiteNativeDiagnostics;
};
export type RAGBackendCapabilities = {
    backend: 'in_memory' | 'sqlite' | 'postgres' | 'custom';
    persistence: 'memory_only' | 'embedded' | 'external';
    nativeVectorSearch: boolean;
    serverSideFiltering: boolean;
    streamingIngestStatus: boolean;
};
export type RAGVectorStore = {
    embed: (input: {
        text: string;
        model?: string;
        signal?: AbortSignal;
    }) => Promise<number[]>;
    query: (input: RAGQueryInput) => Promise<RAGQueryResult[]>;
    upsert: (input: RAGUpsertInput) => Promise<void>;
    clear?: () => Promise<void> | void;
    getStatus?: () => RAGVectorStoreStatus;
    getCapabilities?: () => RAGBackendCapabilities;
};
export type RAGCollectionSearchParams = {
    query: string;
    topK?: number;
    filter?: Record<string, unknown>;
    scoreThreshold?: number;
    model?: string;
    signal?: AbortSignal;
};
export type RAGSearchRequest = Omit<RAGCollectionSearchParams, 'signal'>;
export type RAGIngestResponse = {
    ok: boolean;
    count?: number;
    error?: string;
};
export type RAGStatusResponse = {
    ok: true;
    status?: RAGVectorStoreStatus;
    capabilities?: RAGBackendCapabilities;
};
export type RAGCollection = {
    store: RAGVectorStore;
    search: (input: RAGCollectionSearchParams) => Promise<RAGQueryResult[]>;
    ingest: (input: RAGUpsertInput) => Promise<void>;
    clear?: () => Promise<void> | void;
    getStatus?: () => RAGVectorStoreStatus;
    getCapabilities?: () => RAGBackendCapabilities;
};
export type AITextChunk = {
    type: 'text';
    content: string;
};
export type AIToolUseChunk = {
    type: 'tool_use';
    id: string;
    name: string;
    input: unknown;
};
export type AIDoneChunk = {
    type: 'done';
    usage?: AIUsage;
};
export type AIThinkingChunk = {
    type: 'thinking';
    content: string;
    signature?: string;
};
export type AIImageChunk = {
    type: 'image';
    data: string;
    format: string;
    isPartial: boolean;
    revisedPrompt?: string;
    imageId?: string;
};
export type AIChunk = AITextChunk | AIThinkingChunk | AIToolUseChunk | AIImageChunk | AIDoneChunk;
export type AIProviderStreamParams = {
    model: string;
    messages: AIProviderMessage[];
    tools?: AIProviderToolDefinition[];
    systemPrompt?: string;
    thinking?: {
        type: string;
        budget_tokens: number;
    };
    signal?: AbortSignal;
};
export type AIProviderMessage = {
    role: 'user' | 'assistant' | 'system';
    content: string | AIProviderContentBlock[];
};
export type AIImageSource = {
    type: 'base64';
    data: string;
    media_type: 'image/png' | 'image/jpeg' | 'image/gif' | 'image/webp';
};
export type AIDocumentSource = {
    type: 'base64';
    data: string;
    media_type: 'application/pdf';
};
export type AIProviderContentBlock = {
    type: 'text';
    content: string;
} | {
    type: 'thinking';
    thinking: string;
    signature?: string;
} | {
    type: 'image';
    source: AIImageSource;
} | {
    type: 'document';
    source: AIDocumentSource;
    name?: string;
} | {
    type: 'tool_use';
    id: string;
    name: string;
    input: unknown;
} | {
    type: 'tool_result';
    tool_use_id: string;
    content: string;
};
export type AIProviderToolDefinition = {
    name: string;
    description: string;
    input_schema: Record<string, unknown>;
};
export type AIProviderConfig = {
    stream: (params: AIProviderStreamParams) => AsyncIterable<AIChunk>;
};
export type AIToolDefinition = {
    description: string;
    input: Record<string, unknown>;
    handler: (input: unknown) => Promise<string> | string;
};
export type AIToolMap = Record<string, AIToolDefinition>;
export type AIAttachment = {
    data: string;
    media_type: 'image/png' | 'image/jpeg' | 'image/gif' | 'image/webp' | 'application/pdf';
    name?: string;
};
export type AIMessageRequest = {
    type: 'message';
    content: string;
    conversationId?: string;
    attachments?: AIAttachment[];
};
export type AICancelRequest = {
    type: 'cancel';
    conversationId: string;
};
export type AIBranchRequest = {
    type: 'branch';
    messageId: string;
    content: string;
    conversationId: string;
};
export type AIClientMessage = AIMessageRequest | AICancelRequest | AIBranchRequest;
export type AIChunkMessage = {
    type: 'chunk';
    content: string;
    messageId: string;
    conversationId: string;
};
export type AIThinkingMessage = {
    type: 'thinking';
    content: string;
    messageId: string;
    conversationId: string;
};
export type AIToolStatusMessage = {
    type: 'tool_status';
    name: string;
    status: 'running' | 'complete';
    input?: unknown;
    result?: string;
    messageId: string;
    conversationId: string;
};
export type AICompleteMessage = {
    type: 'complete';
    durationMs?: number;
    messageId: string;
    model?: string;
    conversationId: string;
    usage?: AIUsage;
    sources?: RAGSource[];
};
export type StreamAICompleteMetadata = {
    sources?: RAGSource[];
};
export type AIImageMessage = {
    type: 'image';
    data: string;
    format: string;
    isPartial: boolean;
    revisedPrompt?: string;
    imageId?: string;
    messageId: string;
    conversationId: string;
};
export type AIErrorMessage = {
    type: 'error';
    message: string;
    messageId?: string;
    conversationId?: string;
};
export type AIRetrievedMessage = {
    type: 'rag_retrieved';
    conversationId: string;
    messageId: string;
    sources: RAGSource[];
};
export type AIServerMessage = AIChunkMessage | AIThinkingMessage | AIToolStatusMessage | AIImageMessage | AICompleteMessage | AIRetrievedMessage | AIErrorMessage;
export type AIRole = 'user' | 'assistant' | 'system';
export type AIToolCall = {
    id: string;
    name: string;
    input: unknown;
    result?: string;
};
export type AIImageData = {
    data: string;
    format: string;
    isPartial: boolean;
    revisedPrompt?: string;
    imageId?: string;
};
export type AIMessage = {
    id: string;
    role: AIRole;
    content: string;
    conversationId: string;
    parentId?: string;
    attachments?: AIAttachment[];
    thinking?: string;
    toolCalls?: AIToolCall[];
    images?: AIImageData[];
    isStreaming?: boolean;
    model?: string;
    usage?: AIUsage;
    sources?: RAGSource[];
    durationMs?: number;
    timestamp: number;
};
export type AIConversation = {
    id: string;
    title?: string;
    messages: AIMessage[];
    activeStreamAbort?: AbortController;
    createdAt: number;
    lastMessageAt?: number;
};
export type AIConversationSummary = {
    id: string;
    title: string;
    messageCount: number;
    createdAt: number;
    lastMessageAt?: number;
};
export type StreamAIOptions = {
    provider: AIProviderConfig;
    model: string;
    messages?: AIProviderMessage[];
    systemPrompt?: string;
    tools?: AIToolMap;
    thinking?: boolean | {
        budgetTokens: number;
    };
    onChunk?: (chunk: AITextChunk) => AITextChunk | void;
    onComplete?: (fullResponse: string, usage?: AIUsage, metadata?: StreamAICompleteMetadata) => void;
    onToolUse?: (name: string, input: unknown, result: string) => void;
    onImage?: (imageData: AIImageData) => void;
    maxTurns?: number;
    signal?: AbortSignal;
    completeMeta?: StreamAICompleteMetadata;
};
export type AIStreamState = {
    conversations: Map<string, AIConversation>;
    activeConversationId: string | null;
    isStreaming: boolean;
    error: string | null;
};
export type AIStoreAction = {
    type: 'chunk';
    conversationId: string;
    messageId: string;
    content: string;
} | {
    type: 'thinking';
    conversationId: string;
    messageId: string;
    content: string;
} | {
    type: 'tool_status';
    conversationId: string;
    messageId: string;
    name: string;
    status: 'running' | 'complete';
    input?: unknown;
    result?: string;
} | {
    type: 'complete';
    conversationId: string;
    durationMs?: number;
    messageId: string;
    model?: string;
    usage?: AIUsage;
    sources?: RAGSource[];
} | {
    type: 'image';
    conversationId: string;
    messageId: string;
    data: string;
    format: string;
    isPartial: boolean;
    revisedPrompt?: string;
    imageId?: string;
} | {
    type: 'error';
    message: string;
} | {
    type: 'rag_retrieved';
    conversationId: string;
    messageId: string;
    sources: RAGSource[];
} | {
    type: 'send';
    content: string;
    conversationId: string;
    messageId: string;
    attachments?: AIAttachment[];
} | {
    type: 'cancel';
} | {
    type: 'branch';
    oldConversationId: string;
    newConversationId: string;
    fromMessageId: string;
} | {
    type: 'set_conversation';
    conversationId: string;
};
export type AIWebSocket = {
    send(data: string): void;
    readyState: number;
};
export type AIConversationStore = {
    get: (id: string) => Promise<AIConversation | undefined>;
    getOrCreate: (id: string) => Promise<AIConversation>;
    set: (id: string, conversation: AIConversation) => Promise<void>;
    list: () => Promise<AIConversationSummary[]>;
    remove: (id: string) => Promise<void>;
};
export type AIHTMXRenderConfig = {
    chunk?: (text: string, fullContent: string) => string;
    thinking?: (text: string) => string;
    toolRunning?: (name: string, input: unknown) => string;
    toolComplete?: (name: string, result: string) => string;
    image?: (data: string, format: string, revisedPrompt?: string) => string;
    complete?: (usage?: AIUsage, durationMs?: number, model?: string) => string;
    ragRetrieved?: (sources: RAGSource[]) => string;
    error?: (message: string) => string;
};
export type AIChatPluginConfig = {
    path?: string;
    provider: (providerName: string) => AIProviderConfig;
    model?: string | ((providerName: string) => string);
    tools?: AIToolMap | ((providerName: string, model: string) => AIToolMap | undefined);
    thinking?: boolean | {
        budgetTokens: number;
    } | ((providerName: string, model: string) => boolean | {
        budgetTokens: number;
    } | undefined);
    systemPrompt?: string;
    maxTurns?: number;
    parseProvider?: (content: string) => {
        content: string;
        model?: string;
        providerName: string;
    };
    onComplete?: (conversationId: string, fullResponse: string, usage?: AIUsage) => void;
    store?: AIConversationStore;
    htmx?: boolean | {
        render?: AIHTMXRenderConfig;
    };
};
export type RAGChatPluginConfig = AIChatPluginConfig & {
    path?: string;
    ragStore?: RAGVectorStore;
    collection?: RAGCollection;
    topK?: number;
    scoreThreshold?: number;
    ragCompleteSources?: boolean;
    systemPrompt?: string;
    onComplete?: (conversationId: string, fullResponse: string, usage?: AIUsage, sources?: RAGSource[]) => void;
};
export type AIConnectionOptions = {
    protocols?: string[];
    reconnect?: boolean;
    pingInterval?: number;
    maxReconnectAttempts?: number;
};
