import { useState, useEffect, useCallback, useRef } from 'react';

interface NetworkState {
  isOnline: boolean;
  isSlowConnection: boolean;
  lastOnlineTime: number | null;
}

interface QueuedOperation {
  id: string;
  operation: () => Promise<void>;
  retryCount: number;
  maxRetries: number;
  onSuccess?: () => void;
  onError?: (error: Error) => void;
}

/**
 * 网络状态检测 Hook
 * 提供网络状态监控、离线队列、自动重试功能
 */
export function useNetworkStatus() {
  const [state, setState] = useState<NetworkState>({
    isOnline: navigator.onLine,
    isSlowConnection: false,
    lastOnlineTime: navigator.onLine ? Date.now() : null
  });

  const queueRef = useRef<QueuedOperation[]>([]);
  const processingRef = useRef(false);

  // 监听网络状态变化
  useEffect(() => {
    const handleOnline = () => {
      setState(prev => ({
        ...prev,
        isOnline: true,
        lastOnlineTime: Date.now()
      }));
      // 网络恢复时处理队列
      processQueue();
    };

    const handleOffline = () => {
      setState(prev => ({
        ...prev,
        isOnline: false
      }));
    };

    window.addEventListener('online', handleOnline);
    window.addEventListener('offline', handleOffline);

    // 检测慢网络（当前环境禁用主动探测，避免产生 502 错误）
    const checkConnectionSpeed = async () => {
      // 仅通过 navigator.connection API 检测（如果可用），不进行 HTTP 请求
      const connection = (navigator as any).connection;
      if (connection) {
        setState(prev => ({
          ...prev,
          isSlowConnection: connection.effectiveType === 'slow-2g' || connection.effectiveType === '2g'
        }));
      }
      // 注意：不再发起 /sb-api/health 请求，该接口在当前环境返回 502
    };

    // 降低检测频率至 120 秒，减少不必要的检查
    const interval = setInterval(checkConnectionSpeed, 120000);
    // 初始加载时不立即执行，等待第一个间隔
    // checkConnectionSpeed();

    return () => {
      window.removeEventListener('online', handleOnline);
      window.removeEventListener('offline', handleOffline);
      clearInterval(interval);
    };
  }, []);

  // 处理离线队列
  const processQueue = useCallback(async () => {
    if (processingRef.current || queueRef.current.length === 0) return;
    
    processingRef.current = true;
    
    while (queueRef.current.length > 0 && navigator.onLine) {
      const item = queueRef.current[0];
      
      try {
        await item.operation();
        item.onSuccess?.();
        queueRef.current.shift(); // 成功移除
      } catch (error) {
        item.retryCount++;
        if (item.retryCount >= item.maxRetries) {
          item.onError?.(error as Error);
          queueRef.current.shift(); // 超过重试次数移除
        } else {
          // 等待后重试
          await new Promise(resolve => setTimeout(resolve, 2000 * item.retryCount));
        }
      }
    }
    
    processingRef.current = false;
  }, []);

  // 添加操作到队列
  const enqueueOperation = useCallback((
    operation: () => Promise<void>,
    options?: {
      maxRetries?: number;
      onSuccess?: () => void;
      onError?: (error: Error) => void;
    }
  ) => {
    const id = `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;
    const queuedOp: QueuedOperation = {
      id,
      operation,
      retryCount: 0,
      maxRetries: options?.maxRetries ?? 3,
      onSuccess: options?.onSuccess,
      onError: options?.onError
    };
    
    queueRef.current.push(queuedOp);
    
    // 如果在线立即处理
    if (navigator.onLine) {
      processQueue();
    }
    
    return id;
  }, [processQueue]);

  // 立即执行（带重试）
  const executeWithRetry = useCallback(async <T>(
    operation: () => Promise<T>,
    options?: {
      maxRetries?: number;
      retryDelay?: number;
      onRetry?: (attempt: number) => void;
    }
  ): Promise<T> => {
    const maxRetries = options?.maxRetries ?? 3;
    const retryDelay = options?.retryDelay ?? 1000;
    
    let lastError: Error | undefined;
    
    for (let attempt = 0; attempt <= maxRetries; attempt++) {
      try {
        return await operation();
      } catch (error) {
        lastError = error as Error;
        
        if (attempt < maxRetries) {
          options?.onRetry?.(attempt + 1);
          await new Promise(resolve => 
            setTimeout(resolve, retryDelay * Math.pow(2, attempt))
          );
        }
      }
    }
    
    throw lastError;
  }, []);

  return {
    ...state,
    enqueueOperation,
    executeWithRetry,
    queueLength: queueRef.current.length
  };
}

/**
 * 乐观更新工具 Hook
 * 先更新UI，后提交服务器，失败自动回滚
 */
export function useOptimisticUpdate<T>() {
  const rollbackRef = useRef<(() => void) | null>(null);

  const optimisticUpdate = useCallback(async (
    options: {
      // 立即执行的乐观更新
      optimistic: () => void;
      // 保存回滚函数的回调
      onRollbackReady?: (rollback: () => void) => void;
      // 实际的服务器操作
      serverOperation: () => Promise<T>;
      // 成功回调
      onSuccess?: (result: T) => void;
      // 失败回调
      onError?: (error: Error) => void;
    }
  ) => {
    // 执行乐观更新
    options.optimistic();

    // 设置回滚函数
    const setRollback = (fn: () => void) => {
      rollbackRef.current = fn;
    };

    // 通知外部回滚函数已就绪
    if (options.onRollbackReady) {
      options.onRollbackReady(() => {
        if (rollbackRef.current) {
          rollbackRef.current();
        }
      });
    }

    try {
      const result = await options.serverOperation();
      rollbackRef.current = null; // 成功，清除回滚
      options.onSuccess?.(result);
      return { success: true, data: result };
    } catch (error) {
      // 执行回滚
      if (rollbackRef.current) {
        rollbackRef.current();
        rollbackRef.current = null;
      }
      options.onError?.(error as Error);
      return { success: false, error };
    }
  }, []);

  return { optimisticUpdate };
}
