/** * Shared types for the opencode-bridge frontend. * * Mirrors the Python server's response shapes in `opencode_bridge/routes.py` * and the OpenCode Serve SSE event shape documented in * `/Users/taochen/temp/demo.html` (`handleGlobalEvent` / `processSessionEvent`). * * v4: POST /edit is async (returns immediately with sessionId). The LLM * reply is consumed via the GET /events SSE stream. Each SSE event is * a JSON object with a `type` string; consumers route on `type`. */ /** * Minimal context carried with each edit request. Only the * notebookPath is needed (so the server can pick the right OpenCode * session). The cell source, previous-cell, and traceback are NO * LONGER auto-injected into the LLM prompt — the user inserts them * manually via the "📋 插入单元格内容" button (or pastes anything * else they want) so the LLM only sees what they explicitly chose * to send. v0.1.x used to pack a lot more here; that auto-wrap * made the LLM context hard to reason about and made the user's * intent ambiguous. */ export interface CellContext { notebookPath: string; } export interface OpenCodeRequest { prompt: string; context: CellContext; providerId?: string; modelId?: string; } /** * Response from POST /opencode-bridge/edit (async). * The actual assistant reply arrives via the /events SSE stream and is * NOT embedded in this response. */ export interface OpenCodeEditSuccess { ok: true; sessionId: string; notebookPath: string; } export interface OpenCodeEditFailure { ok: false; error: string; } export type OpenCodeEditResponse = OpenCodeEditSuccess | OpenCodeEditFailure; /** * One SSE event from GET /opencode-bridge/events (proxied from OpenCode * Serve's /global/event). The shape is loosely typed because OpenCode's * payload envelope is not strictly documented; we follow demo.html's * defensive property lookup pattern (try top-level then nested under * `payload`). */ export interface OpenCodeEvent { type: string; payload?: { type?: string; properties?: { [k: string]: any }; syncEvent?: { aggregateID?: string }; }; properties?: { [k: string]: any }; syncEvent?: { aggregateID?: string }; } /** Response from GET /opencode-bridge/session-messages?notebook=... . * Projected from OpenCode's {info, parts}[] by the server into a * frontend-friendly {role, content}[]. */ export interface OpenCodeMessage { role: "user" | "assistant"; content: string; } export interface OpenCodeMessagesResponse { messages: OpenCodeMessage[]; } // --------------------------------------------------------------------------- // Multi-session management types (1 notebook can bind N sessions, one active) // --------------------------------------------------------------------------- /** One session on the OpenCode Serve side (returned by GET /session). */ export interface OpenCodeSessionMeta { id: string; title?: string; createdAt?: number; updatedAt?: number; [k: string]: unknown; } /** Response from GET /opencode-bridge/sessions/all. */ export interface OpenCodeAllSessionsResponse { ok: boolean; sessions: OpenCodeSessionMeta[]; error?: string; } /** One session bound to a notebook (returned by GET /sessions/notebook). */ export interface OpenCodeNotebookSession { sessionId: string; title?: string; createdAt?: number; updatedAt?: number; isActive: boolean; } /** Response from GET /opencode-bridge/sessions/notebook?notebook=... */ export interface OpenCodeNotebookSessionsResponse { ok: boolean; notebookPath: string; activeSessionId: string | null; sessions: OpenCodeNotebookSession[]; error?: string; } /** Response from POST/PUT /sessions/notebook and PUT /sessions/active. */ export interface OpenCodeSessionOpResponse { ok: boolean; notebookPath: string; sessionId?: string; activeSessionId?: string | null; deleted?: boolean; error?: string; } /** Response from GET /opencode-bridge/providers (proxies OpenCode /config/providers). * Each Provider.models is a Record keyed by modelID (NOT an array). */ export interface OpenCodeModel { id: string; name?: string; [k: string]: unknown; } export interface OpenCodeProvider { id: string; name?: string; source?: string; models: { [modelID: string]: OpenCodeModel }; } export interface OpenCodeProvidersResponse { providers: OpenCodeProvider[]; default?: { [providerID: string]: string }; }