import { log } from '@mondaydotcomorg/atp-runtime';
/**
 * Execution state manager using CacheProvider
 * Works with any CacheProvider (MemoryCache, RedisCache, etc.)
 */
export class ExecutionStateManager {
    cache;
    keyPrefix;
    ttl;
    maxPauseDuration;
    metrics;
    constructor(cache, options) {
        this.cache = cache;
        this.keyPrefix = options?.keyPrefix || 'atp:execution:';
        this.ttl = options?.ttl || 3600;
        this.maxPauseDuration = (options?.maxPauseDuration ?? 3600) * 1000;
        this.metrics = {
            totalPauses: 0,
            totalResumes: 0,
            totalExpired: 0,
            totalFailed: 0,
        };
        log.info('ExecutionStateManager initialized', {
            cacheProvider: cache.name,
            ttl: this.ttl,
            maxPauseDuration: this.maxPauseDuration / 1000,
        });
    }
    /**
     * Saves paused execution state
     */
    async pause(state) {
        this.metrics.totalPauses++;
        const key = this.getKey(state.executionId);
        const serialized = JSON.stringify(state);
        await this.cache.set(key, serialized, this.ttl);
        log.info('Execution paused', {
            executionId: state.executionId,
            clientId: state.clientId,
            callbackType: state.callbackRequest.type,
            cacheProvider: this.cache.name,
            ttl: this.ttl,
            maxPauseDuration: this.maxPauseDuration / 1000,
        });
    }
    /**
     * Retrieves paused execution state
     */
    async get(executionId) {
        const key = this.getKey(executionId);
        const serialized = await this.cache.get(key);
        if (!serialized) {
            log.warn('Execution not found or expired', { executionId });
            this.metrics.totalExpired++;
            return null;
        }
        const state = JSON.parse(serialized);
        const pauseDuration = Date.now() - state.pausedAt;
        if (pauseDuration > this.maxPauseDuration) {
            log.warn('Execution pause duration exceeded maximum', {
                executionId,
                pauseDuration: pauseDuration / 1000,
                maxDuration: this.maxPauseDuration / 1000,
            });
            await this.delete(executionId);
            this.metrics.totalExpired++;
            return null;
        }
        await this.cache.set(key, serialized, this.ttl);
        this.metrics.totalResumes++;
        return state;
    }
    /**
     * Deletes execution state
     */
    async delete(executionId) {
        const key = this.getKey(executionId);
        await this.cache.delete(key);
        log.debug('Execution state deleted', { executionId });
    }
    /**
     * Gets the full cache key for an execution ID
     */
    getKey(executionId) {
        return `${this.keyPrefix}${executionId}`;
    }
    /**
     * Closes connections and cleanup
     */
    async close() {
        if (this.cache.disconnect) {
            await this.cache.disconnect();
        }
        log.debug('ExecutionStateManager closed');
    }
    /**
     * Gets storage type from cache provider
     */
    getStorageType() {
        return this.cache.name;
    }
    /**
     * Gets pause/resume metrics
     */
    getMetrics() {
        return {
            ...this.metrics,
            successRate: this.metrics.totalResumes > 0
                ? ((this.metrics.totalResumes / (this.metrics.totalPauses || 1)) * 100).toFixed(2) + '%'
                : '0%',
            expiredRate: this.metrics.totalExpired > 0
                ? ((this.metrics.totalExpired / (this.metrics.totalPauses || 1)) * 100).toFixed(2) + '%'
                : '0%',
        };
    }
    /**
     * Resets metrics (useful for testing)
     */
    resetMetrics() {
        this.metrics = {
            totalPauses: 0,
            totalResumes: 0,
            totalExpired: 0,
            totalFailed: 0,
        };
    }
}
//# sourceMappingURL=index.js.map