/**
 * 任务调度系统 - 支持自动化任务和定时操作
 * 类似cron的定时任务系统，支持复杂的工作流
 */

import { PlatformManager } from './platform-adapter';
import { ApiResponse } from './api-simulator';

export interface TaskConfig {
  id: string;
  name: string;
  description?: string;
  platform: string;
  type: 'sync' | 'update' | 'batch' | 'custom';
  schedule: string; // cron表达式
  enabled: boolean;
  parameters: Record<string, any>;
  retryCount: number;
  retryDelay: number; // 重试延迟(毫秒)
  timeout: number; // 超时时间(毫秒)
}

interface TaskExecution {
  id: string;
  taskId: string;
  startTime: Date;
  endTime?: Date;
  status: 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';
  result?: ApiResponse;
  error?: string;
  retryCount: number;
}

interface TaskHistory {
  taskId: string;
  executions: TaskExecution[];
  lastRun?: Date;
  nextRun?: Date;
  successCount: number;
  failureCount: number;
}

interface WorkflowStep {
  id: string;
  name: string;
  type: 'sync' | 'update' | 'condition' | 'delay';
  parameters: Record<string, any>;
  nextStep?: string; // 下一步ID
  condition?: (result: ApiResponse) => boolean; // 条件判断
}

export interface WorkflowConfig {
  id: string;
  name: string;
  steps: WorkflowStep[];
  schedule?: string;
  enabled: boolean;
}

/**
 * 任务调度器
 */
export class TaskScheduler {
  private tasks: Map<string, TaskConfig> = new Map();
  private workflows: Map<string, WorkflowConfig> = new Map();
  private executions: Map<string, TaskExecution> = new Map();
  private history: Map<string, TaskHistory> = new Map();
  private timers: Map<string, NodeJS.Timeout> = new Map();
  private platformManager: PlatformManager;

  constructor(platformManager: PlatformManager) {
    this.platformManager = platformManager;
    this.loadDefaultTasks();
  }

  /**
   * 加载默认任务配置
   */
  private loadDefaultTasks(): void {
    const defaultTasks: TaskConfig[] = [
      {
        id: 'sync-orders-daily',
        name: '每日订单同步',
        description: '每天凌晨同步所有平台的订单数据',
        platform: 'all',
        type: 'sync',
        schedule: '0 2 * * *', // 每天凌晨2点
        enabled: true,
        parameters: { limit: 1000, syncAll: true },
        retryCount: 3,
        retryDelay: 5000,
        timeout: 300000 // 5分钟
      },
      {
        id: 'sync-products-hourly',
        name: '每小时商品同步',
        description: '每小时同步商品数据',
        platform: 'all',
        type: 'sync',
        schedule: '0 * * * *', // 每小时
        enabled: true,
        parameters: { limit: 500 },
        retryCount: 2,
        retryDelay: 3000,
        timeout: 180000 // 3分钟
      },
      {
        id: 'price-monitoring',
        name: '价格监控',
        description: '监控商品价格变化',
        platform: 'all',
        type: 'custom',
        schedule: '*/15 * * * *', // 每15分钟
        enabled: true,
        parameters: { monitorInterval: 15 },
        retryCount: 1,
        retryDelay: 2000,
        timeout: 120000 // 2分钟
      }
    ];

    defaultTasks.forEach(task => this.addTask(task));
  }

  /**
   * 添加任务
   */
  addTask(task: TaskConfig): void {
    this.tasks.set(task.id, task);
    this.history.set(task.id, {
      taskId: task.id,
      executions: [],
      successCount: 0,
      failureCount: 0
    });

    if (task.enabled) {
      this.scheduleTask(task);
    }

    console.log(`任务已添加: ${task.name} (${task.id})`);
  }

  /**
   * 调度任务
   */
  private scheduleTask(task: TaskConfig): void {
    if (this.timers.has(task.id)) {
      clearTimeout(this.timers.get(task.id)!);
    }

    const nextRun = this.calculateNextRun(task.schedule);
    const delay = nextRun.getTime() - Date.now();

    if (delay > 0) {
      const timer = setTimeout(() => {
        this.executeTask(task.id);
        // 重新调度下一次执行
        this.scheduleTask(task);
      }, delay);

      this.timers.set(task.id, timer);
      
      // 更新历史记录
      const history = this.history.get(task.id);
      if (history) {
        history.nextRun = nextRun;
      }

      console.log(`任务已调度: ${task.name}, 下次执行: ${nextRun.toLocaleString()}`);
    }
  }

  /**
   * 计算下次执行时间
   */
  private calculateNextRun(cronExpression: string): Date {
    // 简化的cron表达式解析（实际项目中应该使用cron库）
    const [minute, hour, dayOfMonth, month, dayOfWeek] = cronExpression.split(' ');
    
    const now = new Date();
    const nextRun = new Date(now);
    
    // 简单的实现，实际应该使用成熟的cron库
    if (minute === '*') {
      nextRun.setMinutes(now.getMinutes() + 1);
    } else if (minute.startsWith('*/')) {
      const interval = parseInt(minute.substring(2));
      nextRun.setMinutes(now.getMinutes() + interval);
    } else {
      nextRun.setMinutes(parseInt(minute));
    }
    
    return nextRun;
  }

  /**
   * 执行任务
   */
  async executeTask(taskId: string, manual: boolean = false): Promise<TaskExecution> {
    const task = this.tasks.get(taskId);
    if (!task) {
      throw new Error(`任务不存在: ${taskId}`);
    }

    const execution: TaskExecution = {
      id: this.generateId(),
      taskId,
      startTime: new Date(),
      status: 'running',
      retryCount: 0
    };

    this.executions.set(execution.id, execution);

    // 添加到历史记录
    const history = this.history.get(taskId);
    if (history) {
      history.executions.push(execution);
      history.lastRun = execution.startTime;
    }

    console.log(`开始执行任务: ${task.name}`);

    try {
      const result = await this.executeTaskWithRetry(task, execution);
      
      execution.endTime = new Date();
      execution.status = result.success ? 'completed' : 'failed';
      execution.result = result;

      if (result.success) {
        console.log(`任务执行成功: ${task.name}`);
        if (history) history.successCount++;
      } else {
        console.error(`任务执行失败: ${task.name}`, result.error);
        if (history) history.failureCount++;
      }

      return execution;
    } catch (error) {
      execution.endTime = new Date();
      execution.status = 'failed';
      execution.error = error instanceof Error ? error.message : '未知错误';

      console.error(`任务执行异常: ${task.name}`, error);
      if (history) history.failureCount++;

      return execution;
    }
  }

  /**
   * 带重试的任务执行
   */
  private async executeTaskWithRetry(task: TaskConfig, execution: TaskExecution): Promise<ApiResponse> {
    for (let attempt = 0; attempt <= task.retryCount; attempt++) {
      execution.retryCount = attempt;

      try {
        const result = await this.executeSingleTask(task);
        return result;
      } catch (error) {
        if (attempt === task.retryCount) {
          throw error; // 最后一次重试失败
        }

        console.log(`任务执行失败，${task.retryDelay}ms后重试 (${attempt + 1}/${task.retryCount})`);
        await new Promise(resolve => setTimeout(resolve, task.retryDelay));
      }
    }

    throw new Error('任务执行失败，重试次数已用尽');
  }

  /**
   * 执行单个任务
   */
  private async executeSingleTask(task: TaskConfig): Promise<ApiResponse> {
    const timeoutPromise = new Promise<never>((_, reject) => {
      setTimeout(() => reject(new Error('任务执行超时')), task.timeout);
    });

    const taskPromise = (async () => {
      switch (task.type) {
        case 'sync':
          return await this.executeSyncTask(task);
        case 'update':
          return await this.executeUpdateTask(task);
        case 'batch':
          return await this.executeBatchTask(task);
        case 'custom':
          return await this.executeCustomTask(task);
        default:
          throw new Error(`不支持的任务类型: ${task.type}`);
      }
    })();

    return await Promise.race([taskPromise, timeoutPromise]);
  }

  /**
   * 执行同步任务
   */
  private async executeSyncTask(task: TaskConfig): Promise<ApiResponse> {
    const platforms = task.platform === 'all' 
      ? this.platformManager.getLoggedInPlatforms() 
      : [task.platform];

    if (platforms.length === 0) {
      return {
        success: false,
        error: '没有已登录的平台',
        timestamp: Date.now()
      };
    }

    const results = await this.platformManager.batchOperation(platforms, async (adapter) => {
      if (task.name.includes('订单')) {
        return await adapter.syncOrders();
      } else if (task.name.includes('商品')) {
        return await adapter.syncProducts();
      } else {
        return await adapter.getProducts(task.parameters);
      }
    });

    const successCount = Object.values(results).filter(r => r.success).length;
    
    return {
      success: successCount > 0,
      data: {
        message: `同步任务完成，成功${successCount}个平台，失败${platforms.length - successCount}个`,
        results
      },
      timestamp: Date.now()
    };
  }

  /**
   * 执行更新任务
   */
  private async executeUpdateTask(task: TaskConfig): Promise<ApiResponse> {
    // 更新任务实现
    return {
      success: true,
      data: { message: '更新任务执行完成' },
      timestamp: Date.now()
    };
  }

  /**
   * 执行批量任务
   */
  private async executeBatchTask(task: TaskConfig): Promise<ApiResponse> {
    // 批量任务实现
    return {
      success: true,
      data: { message: '批量任务执行完成' },
      timestamp: Date.now()
    };
  }

  /**
   * 执行自定义任务
   */
  private async executeCustomTask(task: TaskConfig): Promise<ApiResponse> {
    // 自定义任务实现
    return {
      success: true,
      data: { message: '自定义任务执行完成' },
      timestamp: Date.now()
    };
  }

  /**
   * 添加工作流
   */
  addWorkflow(workflow: WorkflowConfig): void {
    this.workflows.set(workflow.id, workflow);
    
    if (workflow.schedule && workflow.enabled) {
      // 调度工作流执行
      this.scheduleWorkflow(workflow);
    }

    console.log(`工作流已添加: ${workflow.name}`);
  }

  /**
   * 调度工作流
   */
  private scheduleWorkflow(workflow: WorkflowConfig): void {
    // 工作流调度逻辑
    console.log(`工作流已调度: ${workflow.name}`);
  }

  /**
   * 获取任务列表
   */
  getTasks(): TaskConfig[] {
    return Array.from(this.tasks.values());
  }

  /**
   * 获取任务执行历史
   */
  getTaskHistory(taskId: string): TaskHistory | undefined {
    return this.history.get(taskId);
  }

  /**
   * 获取所有任务历史
   */
  getAllHistory(): Map<string, TaskHistory> {
    return new Map(this.history);
  }

  /**
   * 启用/禁用任务
   */
  setTaskEnabled(taskId: string, enabled: boolean): void {
    const task = this.tasks.get(taskId);
    if (task) {
      task.enabled = enabled;
      
      if (enabled) {
        this.scheduleTask(task);
      } else {
        const timer = this.timers.get(taskId);
        if (timer) {
          clearTimeout(timer);
          this.timers.delete(taskId);
        }
      }
    }
  }

  /**
   * 停止所有任务
   */
  stopAllTasks(): void {
    for (const timer of this.timers.values()) {
      clearTimeout(timer);
    }
    this.timers.clear();
    console.log('所有任务已停止');
  }

  /**
   * 生成唯一ID
   */
  private generateId(): string {
    return `task-exec-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;
  }
}

// 导出单例实例
import { platformManager } from './platform-adapter';
export const taskScheduler = new TaskScheduler(platformManager);