import type { ImageContent, Message, TextContent } from '../../ai/types.js';
import { type NewSessionOptions, type SessionContext, type SessionEntry, type SessionHeader, type SessionTreeNode } from '../../core/session-schema.js';
import { type CustomMessage } from '../messages.js';
import type { SessionPersistenceBackend } from './session-persistence-backend.js';
/**
 * Manages conversation sessions as append-only trees stored in JSONL files.
 *
 * Each session entry has an id and parentId forming a tree structure. The "leaf"
 * pointer tracks the current position. Appending creates a child of the current leaf.
 * Branching moves the leaf to an earlier entry, allowing new branches without
 * modifying history.
 *
 * Use buildSessionContext() to get the resolved message list for the LLM, which
 * handles compaction summaries and follows the path from root to current leaf.
 */
export declare class SessionManager {
    private sessionId;
    private sessionFile;
    private sessionDir;
    private cwd;
    private persist;
    private persistenceBackend;
    private flushed;
    private fileEntries;
    private byId;
    private labelsById;
    private leafId;
    constructor(cwd: string, sessionDir: string, sessionFile: string | undefined, persist: boolean, persistenceBackend?: SessionPersistenceBackend, initialSessionOptions?: NewSessionOptions);
    /** Switch to a different session file (used for resume and branching) */
    setSessionFile(sessionFile: string): void;
    newSession(options?: NewSessionOptions): string | undefined;
    private _buildIndex;
    private _rewriteFile;
    isPersisted(): boolean;
    getCwd(): string;
    getSessionDir(): string;
    getSessionId(): string;
    getSessionFile(): string | undefined;
    _persist(entry: SessionEntry): void;
    private _appendEntry;
    /** Append a message as child of current leaf, then advance leaf. Returns entry id.
     * Does not allow writing compaction summary messages directly.
     * Reason: we want these to be top-level entries in the session, not message session entries,
     * so it is easier to find them.
     * These need to be appended via appendCompaction().
     */
    appendMessage(message: Message | CustomMessage, durationMs?: number): string;
    /** Append a thinking level change as child of current leaf, then advance leaf. Returns entry id. */
    appendThinkingLevelChange(thinkingLevel: string): string;
    /** Append a model change as child of current leaf, then advance leaf. Returns entry id. */
    appendModelChange(provider: string, modelId: string): string;
    /** Append a compaction summary as child of current leaf, then advance leaf. Returns entry id. */
    appendCompaction<T = unknown>(summary: string, firstKeptEntryId: string, tokensBefore: number, details?: T, fromHook?: boolean): string;
    /** Append a custom entry (for extensions) as child of current leaf, then advance leaf. Returns entry id. */
    appendCustomEntry(customType: string, data?: unknown): string;
    /** Append a session info entry (e.g., display name). Returns entry id. */
    appendSessionInfo(name: string): string;
    /** Append a turn start boundary entry. Returns entry id. */
    appendTurnStart(turnIndex: number): string;
    /** Append a turn end boundary entry with duration. Returns entry id. */
    appendTurnEnd(turnIndex: number, durationMs: number): string;
    /** Append a system prompt snapshot. Returns entry id. */
    appendSystemPrompt(content: string): string;
    /** Append a tool definitions snapshot. Returns entry id. */
    appendToolDefinitions(tools: {
        name: string;
        description: string;
        parameters: unknown;
    }[]): string;
    /** Get the current session name from the latest session_info entry, if any. */
    getSessionName(): string | undefined;
    /**
     * Append a custom message entry (for extensions) that participates in LLM context.
     * @param customType Extension identifier for filtering on reload
     * @param content Message content (string or TextContent/ImageContent array)
     * @param display Whether to show in TUI (true = styled display, false = hidden)
     * @param details Optional extension-specific metadata (not sent to LLM)
     * @returns Entry id
     */
    appendCustomMessageEntry<T = unknown>(customType: string, content: string | (TextContent | ImageContent)[], display: boolean, details?: T): string;
    getLeafId(): string | null;
    getLeafEntry(): SessionEntry | undefined;
    getEntry(id: string): SessionEntry | undefined;
    /**
     * Get all direct children of an entry.
     */
    getChildren(parentId: string): SessionEntry[];
    /**
     * Get the label for an entry, if any.
     */
    getLabel(id: string): string | undefined;
    /**
     * Set or clear a label on an entry.
     * Labels are user-defined markers for bookmarking/navigation.
     * Pass undefined or empty string to clear the label.
     */
    appendLabelChange(targetId: string, label: string | undefined): string;
    /**
     * Walk from entry to root, returning all entries in path order.
     * Includes all entry types (messages, compaction, model changes, etc.).
     * Use buildSessionContext() to get the resolved messages for the LLM.
     */
    getBranch(fromId?: string): SessionEntry[];
    /**
     * Build the session context (what gets sent to the LLM).
     * Uses tree traversal from current leaf.
     */
    buildSessionContext(): SessionContext;
    /**
     * Get session header.
     */
    getHeader(): SessionHeader | null;
    /**
     * Get all session entries (excludes header). Returns a shallow copy.
     * The session is append-only: use appendXXX() to add entries, branch() to
     * change the leaf pointer. Entries cannot be modified or deleted.
     */
    getEntries(): SessionEntry[];
    /**
     * Get the session as a tree structure. Returns a shallow defensive copy of all entries.
     * A well-formed session has exactly one root (first entry with parentId === null).
     * Orphaned entries (broken parent chain) are also returned as roots.
     */
    getTree(): SessionTreeNode[];
    /**
     * Start a new branch from an earlier entry.
     * Moves the leaf pointer to the specified entry. The next appendXXX() call
     * will create a child of that entry, forming a new branch. Existing entries
     * are not modified or deleted.
     */
    branch(branchFromId: string): void;
    /**
     * Reset the leaf pointer to null (before any entries).
     * The next appendXXX() call will create a new root entry (parentId = null).
     * Use this when navigating to re-edit the first user message.
     */
    resetLeaf(): void;
    /**
     * Create a new session file containing only the path from root to the specified leaf.
     * Useful for extracting a single conversation path from a branched session.
     * Returns the new session file path, or undefined if not persisting.
     */
    createBranchedSession(leafId: string): string | undefined;
}
//# sourceMappingURL=session-manager.d.ts.map