package com.ruoyi.credit.service;

import java.util.Date;
import java.util.concurrent.atomic.AtomicLong;

/**
 * 规则执行统计信息
 * 
 * @author ruoyi
 * @date 2025-01-05
 */
public class RuleExecutionStats {
    
    private final String ruleName;
    private final AtomicLong totalExecutions = new AtomicLong(0);
    private final AtomicLong successCount = new AtomicLong(0);
    private final AtomicLong failureCount = new AtomicLong(0);
    private final AtomicLong totalExecutionTime = new AtomicLong(0);
    private volatile long minExecutionTime = Long.MAX_VALUE;
    private volatile long maxExecutionTime = 0;
    private volatile Date lastExecutionTime;
    private volatile Date firstExecutionTime;
    
    public RuleExecutionStats(String ruleName) {
        this.ruleName = ruleName;
    }
    
    /**
     * 记录一次执行
     * 
     * @param success 是否成功
     * @param executionTime 执行时间（毫秒）
     */
    public synchronized void recordExecution(boolean success, long executionTime) {
        totalExecutions.incrementAndGet();
        totalExecutionTime.addAndGet(executionTime);
        
        if (success) {
            successCount.incrementAndGet();
        } else {
            failureCount.incrementAndGet();
        }
        
        // 更新执行时间统计
        if (executionTime < minExecutionTime) {
            minExecutionTime = executionTime;
        }
        if (executionTime > maxExecutionTime) {
            maxExecutionTime = executionTime;
        }
        
        Date now = new Date();
        lastExecutionTime = now;
        if (firstExecutionTime == null) {
            firstExecutionTime = now;
        }
    }
    
    public String getRuleName() {
        return ruleName;
    }
    
    public long getTotalExecutions() {
        return totalExecutions.get();
    }
    
    public long getSuccessCount() {
        return successCount.get();
    }
    
    public long getFailureCount() {
        return failureCount.get();
    }
    
    public double getSuccessRate() {
        long total = totalExecutions.get();
        return total > 0 ? (double) successCount.get() / total : 0.0;
    }
    
    public double getFailureRate() {
        long total = totalExecutions.get();
        return total > 0 ? (double) failureCount.get() / total : 0.0;
    }
    
    public long getAverageExecutionTime() {
        long total = totalExecutions.get();
        return total > 0 ? totalExecutionTime.get() / total : 0;
    }
    
    public long getMinExecutionTime() {
        return minExecutionTime == Long.MAX_VALUE ? 0 : minExecutionTime;
    }
    
    public long getMaxExecutionTime() {
        return maxExecutionTime;
    }
    
    public Date getLastExecutionTime() {
        return lastExecutionTime;
    }
    
    public Date getFirstExecutionTime() {
        return firstExecutionTime;
    }
    
    @Override
    public String toString() {
        return String.format("RuleExecutionStats{ruleName='%s', total=%d, success=%d, failure=%d, successRate=%.2f%%, avgTime=%dms}",
                ruleName, getTotalExecutions(), getSuccessCount(), getFailureCount(), 
                getSuccessRate() * 100, getAverageExecutionTime());
    }
}