/**
 * [MOCK] AI决策自动化配置数据源
 * AI注意: 这是Mock实现，不是真实业务逻辑
 * 仅在USE_MOCK=true时启用
 */

export type AutomationLevel = 'L1' | 'L2' | 'L3' | 'L4';
export type RiskLevel = 'LOW' | 'MEDIUM' | 'HIGH' | 'CRITICAL';
export type DecisionModule = 
  | 'PRICING' 
  | 'INVENTORY' 
  | 'AD_OPTIMIZE' 
  | 'PRODUCT_SELECT'
  | 'LOGISTICS' 
  | 'RISK_CONTROL' 
  | 'CUSTOMER_SERVICE' 
  | 'SETTLEMENT';

export interface AutoExecutionConfig {
  id: string;
  tenant_id: string;
  shop_id: string;
  module: DecisionModule;
  automation_level: AutomationLevel;
  confidence_thresholds: {
    auto_execute: number;
    pending_review: number;
    auto_reject: number;
  };
  risk_limits: {
    max_amount: number;
    max_quantity: number;
    allowed_risk_levels: RiskLevel[];
  };
  time_restrictions: {
    allowed_hours: number[];
    excluded_dates: string[];
  };
  rollback_config: {
    enabled: boolean;
    max_attempts: number;
    cooldown_minutes: number;
  };
  notification_config: {
    on_execute: boolean;
    on_fail: boolean;
    on_rollback: boolean;
    channels: ('EMAIL' | 'SMS' | 'WEBHOOK')[];
  };
  statistics: {
    total_executions: number;
    success_count: number;
    fail_count: number;
    rollback_count: number;
    avg_confidence: number;
    last_execution_at?: string;
  };
  status: 'ACTIVE' | 'INACTIVE' | 'SUSPENDED';
  created_by: string;
  updated_by: string;
  created_at: string;
  updated_at: string;
}

export interface LevelEvolutionRecord {
  id: string;
  tenant_id: string;
  shop_id: string;
  module: DecisionModule;
  from_level: AutomationLevel;
  to_level: AutomationLevel;
  reason: string;
  metrics: {
    success_rate: number;
    total_executions: number;
    avg_confidence: number;
  };
  approved_by: string;
  created_at: string;
}

export interface LevelCapability {
  max_risk_level: RiskLevel;
  max_amount_multiplier: number;
  requires_approval: boolean;
  description: string;
}

export interface IAutoExecutionDataSource {
  fetchConfigs(tenantId: string, shopId?: string): Promise<AutoExecutionConfig[]>;
  fetchConfig(tenantId: string, shopId: string, module: DecisionModule): Promise<AutoExecutionConfig>;
  updateConfig(configId: string, updates: Partial<AutoExecutionConfig>): Promise<AutoExecutionConfig>;
  upgradeLevel(tenantId: string, shopId: string, module: DecisionModule, targetLevel: AutomationLevel, reason: string): Promise<LevelEvolutionRecord>;
  downgradeLevel(tenantId: string, shopId: string, module: DecisionModule, targetLevel: AutomationLevel, reason: string): Promise<LevelEvolutionRecord>;
  fetchEvolutionHistory(tenantId: string, shopId?: string, module?: DecisionModule): Promise<LevelEvolutionRecord[]>;
  fetchLevelCapabilities(): Promise<Record<AutomationLevel, LevelCapability>>;
  fetchModuleDefaults(): Promise<Record<DecisionModule, Partial<AutoExecutionConfig>>>;
}

const MODULE_NAMES: Record<DecisionModule, string> = {
  PRICING: '定价模块',
  INVENTORY: '库存模块',
  AD_OPTIMIZE: '广告优化',
  PRODUCT_SELECT: '选品模块',
  LOGISTICS: '物流模块',
  RISK_CONTROL: '风控模块',
  CUSTOMER_SERVICE: '客服模块',
  SETTLEMENT: '结算模块',
};

const LEVEL_CAPABILITIES: Record<AutomationLevel, LevelCapability> = {
  L1: {
    max_risk_level: 'LOW',
    max_amount_multiplier: 0.5,
    requires_approval: true,
    description: '仅建议，所有操作需人工确认',
  },
  L2: {
    max_risk_level: 'MEDIUM',
    max_amount_multiplier: 1.0,
    requires_approval: false,
    description: '低风险操作可自动执行，中高风险需审核',
  },
  L3: {
    max_risk_level: 'HIGH',
    max_amount_multiplier: 2.0,
    requires_approval: false,
    description: '大部分操作可自动执行，仅高风险需审核',
  },
  L4: {
    max_risk_level: 'CRITICAL',
    max_amount_multiplier: 5.0,
    requires_approval: false,
    description: '全自动化，包含关键操作，需严格监控',
  },
};

const MODULE_DEFAULTS: Record<DecisionModule, Partial<AutoExecutionConfig>> = {
  PRICING: {
    confidence_thresholds: { auto_execute: 0.85, pending_review: 0.60, auto_reject: 0.40 },
    risk_limits: { max_amount: 5000, max_quantity: 100, allowed_risk_levels: ['LOW', 'MEDIUM'] },
  },
  INVENTORY: {
    confidence_thresholds: { auto_execute: 0.90, pending_review: 0.70, auto_reject: 0.50 },
    risk_limits: { max_amount: 10000, max_quantity: 500, allowed_risk_levels: ['LOW', 'MEDIUM'] },
  },
  AD_OPTIMIZE: {
    confidence_thresholds: { auto_execute: 0.80, pending_review: 0.55, auto_reject: 0.35 },
    risk_limits: { max_amount: 2000, max_quantity: 50, allowed_risk_levels: ['LOW', 'MEDIUM', 'HIGH'] },
  },
  PRODUCT_SELECT: {
    confidence_thresholds: { auto_execute: 0.75, pending_review: 0.50, auto_reject: 0.30 },
    risk_limits: { max_amount: 3000, max_quantity: 200, allowed_risk_levels: ['LOW', 'MEDIUM'] },
  },
  LOGISTICS: {
    confidence_thresholds: { auto_execute: 0.88, pending_review: 0.65, auto_reject: 0.45 },
    risk_limits: { max_amount: 1000, max_quantity: 100, allowed_risk_levels: ['LOW', 'MEDIUM'] },
  },
  RISK_CONTROL: {
    confidence_thresholds: { auto_execute: 0.95, pending_review: 0.80, auto_reject: 0.60 },
    risk_limits: { max_amount: 50000, max_quantity: 1000, allowed_risk_levels: ['LOW'] },
  },
  CUSTOMER_SERVICE: {
    confidence_thresholds: { auto_execute: 0.82, pending_review: 0.60, auto_reject: 0.40 },
    risk_limits: { max_amount: 500, max_quantity: 10, allowed_risk_levels: ['LOW', 'MEDIUM'] },
  },
  SETTLEMENT: {
    confidence_thresholds: { auto_execute: 0.98, pending_review: 0.90, auto_reject: 0.70 },
    risk_limits: { max_amount: 100000, max_quantity: 100, allowed_risk_levels: ['LOW'] },
  },
};

class MockAutoExecutionDataSource implements IAutoExecutionDataSource {
  private configs: AutoExecutionConfig[] = [];
  private evolutionRecords: LevelEvolutionRecord[] = [];

  constructor() {
    this.initMockData();
  }

  private initMockData() {
    const modules: DecisionModule[] = [
      'PRICING', 'INVENTORY', 'AD_OPTIMIZE', 'PRODUCT_SELECT',
      'LOGISTICS', 'RISK_CONTROL', 'CUSTOMER_SERVICE', 'SETTLEMENT'
    ];
    
    this.configs = modules.map((module, index) => {
      const defaults = MODULE_DEFAULTS[module];
      return {
        id: `AEC-${index + 1}`,
        tenant_id: 'tenant-001',
        shop_id: 'shop-001',
        module,
        automation_level: (['L1', 'L2', 'L3', 'L4'] as AutomationLevel[])[index % 4],
        confidence_thresholds: defaults.confidence_thresholds!,
        risk_limits: defaults.risk_limits!,
        time_restrictions: {
          allowed_hours: Array.from({ length: 24 }, (_, i) => i),
          excluded_dates: [],
        },
        rollback_config: {
          enabled: true,
          max_attempts: 3,
          cooldown_minutes: 30,
        },
        notification_config: {
          on_execute: true,
          on_fail: true,
          on_rollback: true,
          channels: ['EMAIL'] as ('EMAIL' | 'SMS' | 'WEBHOOK')[],
        },
        statistics: {
          total_executions: Math.floor(Math.random() * 1000) + 100,
          success_count: Math.floor(Math.random() * 900) + 90,
          fail_count: Math.floor(Math.random() * 50) + 5,
          rollback_count: Math.floor(Math.random() * 20) + 2,
          avg_confidence: 0.75 + Math.random() * 0.2,
          last_execution_at: new Date(Date.now() - Math.random() * 86400000).toISOString(),
        },
        status: 'ACTIVE',
        created_by: 'admin',
        updated_by: 'admin',
        created_at: new Date(Date.now() - Math.random() * 30 * 86400000).toISOString(),
        updated_at: new Date().toISOString(),
      };
    });

    this.evolutionRecords = [
      {
        id: 'EVO-001',
        tenant_id: 'tenant-001',
        shop_id: 'shop-001',
        module: 'PRICING',
        from_level: 'L1',
        to_level: 'L2',
        reason: '成功率达标，自动升级',
        metrics: {
          success_rate: 0.96,
          total_executions: 150,
          avg_confidence: 0.88,
        },
        approved_by: 'admin',
        created_at: new Date(Date.now() - 7 * 86400000).toISOString(),
      },
    ];
  }

  async fetchConfigs(tenantId: string, shopId?: string): Promise<AutoExecutionConfig[]> {
    await this.delay(300);
    return this.configs.filter(c => 
      c.tenant_id === tenantId && 
      (!shopId || c.shop_id === shopId)
    );
  }

  async fetchConfig(tenantId: string, shopId: string, module: DecisionModule): Promise<AutoExecutionConfig> {
    await this.delay(200);
    const config = this.configs.find(c => 
      c.tenant_id === tenantId && 
      c.shop_id === shopId && 
      c.module === module
    );
    if (!config) {
      const defaults = MODULE_DEFAULTS[module];
      return {
        id: `AEC-NEW-${Date.now()}`,
        tenant_id: tenantId,
        shop_id: shopId,
        module,
        automation_level: 'L1',
        confidence_thresholds: defaults.confidence_thresholds!,
        risk_limits: defaults.risk_limits!,
        time_restrictions: {
          allowed_hours: Array.from({ length: 24 }, (_, i) => i),
          excluded_dates: [],
        },
        rollback_config: {
          enabled: true,
          max_attempts: 3,
          cooldown_minutes: 30,
        },
        notification_config: {
          on_execute: true,
          on_fail: true,
          on_rollback: true,
          channels: ['EMAIL'],
        },
        statistics: {
          total_executions: 0,
          success_count: 0,
          fail_count: 0,
          rollback_count: 0,
          avg_confidence: 0,
        },
        status: 'ACTIVE',
        created_by: 'SYSTEM',
        updated_by: 'SYSTEM',
        created_at: new Date().toISOString(),
        updated_at: new Date().toISOString(),
      };
    }
    return config;
  }

  async updateConfig(configId: string, updates: Partial<AutoExecutionConfig>): Promise<AutoExecutionConfig> {
    await this.delay(300);
    const index = this.configs.findIndex(c => c.id === configId);
    if (index === -1) {
      throw new Error('Config not found');
    }
    this.configs[index] = {
      ...this.configs[index],
      ...updates,
      updated_at: new Date().toISOString(),
    };
    return this.configs[index];
  }

  async upgradeLevel(
    tenantId: string, 
    shopId: string, 
    module: DecisionModule, 
    targetLevel: AutomationLevel, 
    reason: string
  ): Promise<LevelEvolutionRecord> {
    await this.delay(500);
    const config = await this.fetchConfig(tenantId, shopId, module);
    const record: LevelEvolutionRecord = {
      id: `EVO-${Date.now()}`,
      tenant_id: tenantId,
      shop_id: shopId,
      module,
      from_level: config.automation_level,
      to_level: targetLevel,
      reason,
      metrics: {
        success_rate: config.statistics.total_executions > 0 
          ? config.statistics.success_count / config.statistics.total_executions 
          : 0,
        total_executions: config.statistics.total_executions,
        avg_confidence: config.statistics.avg_confidence,
      },
      approved_by: 'admin',
      created_at: new Date().toISOString(),
    };
    this.evolutionRecords.unshift(record);
    
    const index = this.configs.findIndex(c => c.module === module);
    if (index !== -1) {
      this.configs[index].automation_level = targetLevel;
    }
    
    return record;
  }

  async downgradeLevel(
    tenantId: string, 
    shopId: string, 
    module: DecisionModule, 
    targetLevel: AutomationLevel, 
    reason: string
  ): Promise<LevelEvolutionRecord> {
    await this.delay(500);
    const config = await this.fetchConfig(tenantId, shopId, module);
    const record: LevelEvolutionRecord = {
      id: `EVO-${Date.now()}`,
      tenant_id: tenantId,
      shop_id: shopId,
      module,
      from_level: config.automation_level,
      to_level: targetLevel,
      reason,
      metrics: {
        success_rate: config.statistics.total_executions > 0 
          ? config.statistics.success_count / config.statistics.total_executions 
          : 0,
        total_executions: config.statistics.total_executions,
        avg_confidence: config.statistics.avg_confidence,
      },
      approved_by: 'admin',
      created_at: new Date().toISOString(),
    };
    this.evolutionRecords.unshift(record);
    
    const index = this.configs.findIndex(c => c.module === module);
    if (index !== -1) {
      this.configs[index].automation_level = targetLevel;
    }
    
    return record;
  }

  async fetchEvolutionHistory(
    tenantId: string, 
    shopId?: string, 
    module?: DecisionModule
  ): Promise<LevelEvolutionRecord[]> {
    await this.delay(200);
    return this.evolutionRecords.filter(r => 
      r.tenant_id === tenantId && 
      (!shopId || r.shop_id === shopId) &&
      (!module || r.module === module)
    );
  }

  async fetchLevelCapabilities(): Promise<Record<AutomationLevel, LevelCapability>> {
    await this.delay(100);
    return LEVEL_CAPABILITIES;
  }

  async fetchModuleDefaults(): Promise<Record<DecisionModule, Partial<AutoExecutionConfig>>> {
    await this.delay(100);
    return MODULE_DEFAULTS;
  }

  private delay(ms: number): Promise<void> {
    return new Promise(resolve => setTimeout(resolve, ms));
  }
}

class ApiAutoExecutionDataSource implements IAutoExecutionDataSource {
  private baseUrl = '/api/auto-execution';

  async fetchConfigs(tenantId: string, shopId?: string): Promise<AutoExecutionConfig[]> {
    const params = new URLSearchParams({ tenant_id: tenantId });
    if (shopId) params.append('shop_id', shopId);
    const response = await fetch(`${this.baseUrl}/configs?${params}`);
    if (!response.ok) throw new Error('Failed to fetch configs');
    const data = await response.json();
    return data.data;
  }

  async fetchConfig(tenantId: string, shopId: string, module: DecisionModule): Promise<AutoExecutionConfig> {
    const params = new URLSearchParams({ tenant_id: tenantId, shop_id: shopId });
    const response = await fetch(`${this.baseUrl}/config/${module}?${params}`);
    if (!response.ok) throw new Error('Failed to fetch config');
    const data = await response.json();
    return data.data;
  }

  async updateConfig(configId: string, updates: Partial<AutoExecutionConfig>): Promise<AutoExecutionConfig> {
    const response = await fetch(`${this.baseUrl}/config/${configId}`, {
      method: 'PUT',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify(updates),
    });
    if (!response.ok) throw new Error('Failed to update config');
    const data = await response.json();
    return data.data;
  }

  async upgradeLevel(
    tenantId: string, 
    shopId: string, 
    module: DecisionModule, 
    targetLevel: AutomationLevel, 
    reason: string
  ): Promise<LevelEvolutionRecord> {
    const response = await fetch(`${this.baseUrl}/level/upgrade`, {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({ tenant_id: tenantId, shop_id: shopId, module, target_level: targetLevel, reason }),
    });
    if (!response.ok) throw new Error('Failed to upgrade level');
    const data = await response.json();
    return data.data;
  }

  async downgradeLevel(
    tenantId: string, 
    shopId: string, 
    module: DecisionModule, 
    targetLevel: AutomationLevel, 
    reason: string
  ): Promise<LevelEvolutionRecord> {
    const response = await fetch(`${this.baseUrl}/level/downgrade`, {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({ tenant_id: tenantId, shop_id: shopId, module, target_level: targetLevel, reason }),
    });
    if (!response.ok) throw new Error('Failed to downgrade level');
    const data = await response.json();
    return data.data;
  }

  async fetchEvolutionHistory(
    tenantId: string, 
    shopId?: string, 
    module?: DecisionModule
  ): Promise<LevelEvolutionRecord[]> {
    const params = new URLSearchParams({ tenant_id: tenantId });
    if (shopId) params.append('shop_id', shopId);
    if (module) params.append('module', module);
    const response = await fetch(`${this.baseUrl}/evolution-history?${params}`);
    if (!response.ok) throw new Error('Failed to fetch evolution history');
    const data = await response.json();
    return data.data;
  }

  async fetchLevelCapabilities(): Promise<Record<AutomationLevel, LevelCapability>> {
    const response = await fetch(`${this.baseUrl}/level-capabilities`);
    if (!response.ok) throw new Error('Failed to fetch level capabilities');
    const data = await response.json();
    return data.data;
  }

  async fetchModuleDefaults(): Promise<Record<DecisionModule, Partial<AutoExecutionConfig>>> {
    const response = await fetch(`${this.baseUrl}/module-defaults`);
    if (!response.ok) throw new Error('Failed to fetch module defaults');
    const data = await response.json();
    return data.data;
  }
}

const useMock = process.env.REACT_APP_USE_MOCK === 'true';
export const autoExecutionDataSource: IAutoExecutionDataSource = useMock
  ? new MockAutoExecutionDataSource()
  : new ApiAutoExecutionDataSource();

export { MODULE_NAMES, LEVEL_CAPABILITIES, MODULE_DEFAULTS };
