/**
 * Message History Manager
 *
 * Encapsulates message and chat history management.
 * This class handles:
 * - Chat history storage and retrieval
 * - LLM message management
 * - History trimming and cleanup
 * - Memory optimization for long sessions
 */
import { logger } from '../../utils/logger.js';
/**
 * Default configuration values
 */
const DEFAULT_CONFIG = {
    maxHistorySize: 1000,
    maxMessagesSize: 500,
    recentEntriesToKeepFull: 100,
    maxContentLength: 500,
    maxOutputLength: 200,
};
/**
 * Manager for message and chat history in agents.
 *
 * Responsibilities:
 * - Storing and retrieving chat history
 * - Managing LLM message arrays
 * - Trimming history to prevent memory leaks
 * - Cleaning up obsolete references for garbage collection
 */
export class MessageHistoryManager {
    chatHistory = [];
    messages = [];
    config;
    constructor(config = {}) {
        this.config = { ...DEFAULT_CONFIG, ...config };
    }
    // ============================================================================
    // Chat History Operations
    // ============================================================================
    /**
     * Get a copy of the chat history
     */
    getChatHistory() {
        return [...this.chatHistory];
    }
    /**
     * Get the raw chat history array (for internal use)
     */
    getChatHistoryRef() {
        return this.chatHistory;
    }
    /**
     * Add an entry to chat history
     */
    addChatEntry(entry) {
        this.chatHistory.push(entry);
        this.trimHistory();
    }
    /**
     * Add multiple entries to chat history
     */
    addChatEntries(entries) {
        this.chatHistory.push(...entries);
        this.trimHistory();
    }
    /**
     * Set the entire chat history (e.g., when loading a session)
     */
    setChatHistory(history) {
        this.chatHistory = history;
        this.trimHistory();
    }
    /**
     * Clear chat history
     */
    clearChatHistory() {
        this.chatHistory = [];
    }
    // ============================================================================
    // LLM Message Operations
    // ============================================================================
    /**
     * Get a copy of the messages array
     */
    getMessages() {
        return [...this.messages];
    }
    /**
     * Get the raw messages array (for internal use)
     */
    getMessagesRef() {
        return this.messages;
    }
    /**
     * Add a message to the messages array
     */
    addMessage(message) {
        this.messages.push(message);
        this.trimHistory();
    }
    /**
     * Add multiple messages
     */
    addMessages(messages) {
        this.messages.push(...messages);
        this.trimHistory();
    }
    /**
     * Set the entire messages array
     */
    setMessages(messages) {
        this.messages = messages;
        this.trimHistory();
    }
    /**
     * Clear messages while optionally preserving system message
     */
    clearMessages(preserveSystemMessage = true) {
        if (preserveSystemMessage && this.messages.length > 0 && this.messages[0].role === 'system') {
            this.messages = [this.messages[0]];
        }
        else {
            this.messages = [];
        }
    }
    /**
     * Get the system message if present
     */
    getSystemMessage() {
        if (this.messages.length > 0 && this.messages[0].role === 'system') {
            return this.messages[0];
        }
        return null;
    }
    /**
     * Set or update the system message
     */
    setSystemMessage(content) {
        const systemMessage = { role: 'system', content };
        if (this.messages.length > 0 && this.messages[0].role === 'system') {
            this.messages[0] = systemMessage;
        }
        else {
            this.messages.unshift(systemMessage);
        }
    }
    // ============================================================================
    // Clear All
    // ============================================================================
    /**
     * Clear both chat history and messages
     */
    clearAll(preserveSystemMessage = true) {
        this.clearChatHistory();
        this.clearMessages(preserveSystemMessage);
    }
    // ============================================================================
    // Statistics
    // ============================================================================
    /**
     * Get current history statistics
     */
    getStats() {
        return {
            chatHistorySize: this.chatHistory.length,
            messagesSize: this.messages.length,
            maxHistory: this.config.maxHistorySize,
            maxMessages: this.config.maxMessagesSize,
        };
    }
    // ============================================================================
    // Internal: History Management
    // ============================================================================
    /**
     * Trim history arrays to prevent memory leaks.
     *
     * Implements a sliding window approach:
     * - For chatHistory: keeps the most recent entries up to maxHistorySize
     * - For messages: preserves system message and keeps recent conversation messages
     */
    trimHistory() {
        this.trimChatHistory();
        this.trimMessages();
        this.cleanupObsoleteReferences();
    }
    /**
     * Trim chat history using sliding window
     */
    trimChatHistory() {
        if (this.chatHistory.length > this.config.maxHistorySize) {
            const trimCount = this.chatHistory.length - this.config.maxHistorySize;
            this.chatHistory = this.chatHistory.slice(trimCount);
            logger.debug(`Trimmed ${trimCount} old chat history entries`);
        }
    }
    /**
     * Trim LLM messages, preserving system message
     */
    trimMessages() {
        if (this.messages.length > this.config.maxMessagesSize) {
            const hasSystemMessage = this.messages[0]?.role === 'system';
            if (hasSystemMessage) {
                const systemMessage = this.messages[0];
                const trimCount = this.messages.length - this.config.maxMessagesSize;
                const recentMessages = this.messages.slice(-(this.config.maxMessagesSize - 1));
                this.messages = [systemMessage, ...recentMessages];
                logger.debug(`Trimmed ${trimCount} old LLM messages (system message preserved)`);
            }
            else {
                const trimCount = this.messages.length - this.config.maxMessagesSize;
                this.messages = this.messages.slice(trimCount);
                logger.debug(`Trimmed ${trimCount} old LLM messages`);
            }
        }
    }
    /**
     * Clean up large objects in old chat history entries.
     * This helps garbage collection by removing references to
     * potentially large tool results from older entries.
     */
    cleanupObsoleteReferences() {
        if (this.chatHistory.length <= this.config.recentEntriesToKeepFull) {
            return;
        }
        const olderEntries = this.chatHistory.slice(0, -this.config.recentEntriesToKeepFull);
        for (const entry of olderEntries) {
            // Truncate large content in older entries
            if (entry.content && entry.content.length > this.config.maxContentLength) {
                entry.content = entry.content.substring(0, this.config.maxContentLength) + '... [truncated]';
            }
            // Truncate tool result outputs
            if (entry.toolResult?.output && entry.toolResult.output.length > this.config.maxOutputLength) {
                entry.toolResult.output =
                    entry.toolResult.output.substring(0, this.config.maxOutputLength) + '... [truncated]';
            }
        }
    }
    // ============================================================================
    // Disposal
    // ============================================================================
    /**
     * Clear all data for disposal
     */
    dispose() {
        this.chatHistory = [];
        this.messages = [];
    }
}
//# sourceMappingURL=message-history-manager.js.map