import 'dart:async';
import 'dart:convert';

import 'package:dio/dio.dart';
import 'package:get/get.dart';
import 'package:uuid/uuid.dart';

import '../../pigeons/core_api.g.dart';
import '../../utils/haptic_feedback_manager.dart';
import '../../utils/log/logger.dart';
import '../constants/enums.dart';
import '../data/models/vpn_message.dart';
import '../dialog/error_dialog.dart';
import '../dialog/feedback_bottom_sheet.dart';
import 'api_controller.dart';

class CoreController extends GetxService {
  final TAG = 'CoreController';
  final _apiController = Get.find<ApiController>();
  final _state = ConnectionState.disconnected.obs;
  ConnectionState get state => _state.value;
  set state(ConnectionState value) => _state.value = value;

  final _timer = "00:00:00".obs;
  String get timer => _timer.value;
  set timer(String value) => _timer.value = value;

  // VPN 事件流订阅
  StreamSubscription<String>? _eventSubscription;

  CancelToken? _cancelToken;

  @override
  void onInit() {
    super.onInit();
    _initCheckConnect();
    _startListeningToEvents();
  }

  @override
  void onClose() {
    super.onClose();
    // 取消事件流订阅
    _eventSubscription?.cancel();
    _eventSubscription = null;
  }

  void _initCheckConnect() {
    CoreApi().isConnected().then((value) {
      if (value == true) {
        state = ConnectionState.connected;
        CoreApi().reconnect();
      } else {
        state = ConnectionState.disconnected;
      }
    });
  }

  void handleConnection() {
    if (state == ConnectionState.disconnected) {
      // 开始连接 - 轻微震动
      state = ConnectionState.connecting;
      HapticFeedbackManager.connectionStart();
      getDispatchInfo();
    } else {
      // 断开连接
      CoreApi().disconnect();
    }
  }

  Future<void> getDispatchInfo() async {
    // 如果正在请求中，取消当前请求
    if (_cancelToken != null) {
      log(TAG, '取消当前请求，重新发起新请求');
      _cancelToken?.cancel('取消旧请求，发起新请求');
    }

    // 创建新的 CancelToken
    final currentToken = CancelToken();
    _cancelToken = currentToken;

    try {
      final locationId = 187;
      final locationCode = 'auto_mm';
      final launch = await _apiController.getDispatchInfo(
        locationId,
        locationCode,
        cancelToken: currentToken,
      );

      // 只有当前 token 没有被替换时才清空
      if (_cancelToken == currentToken) {
        _cancelToken = null;
      }

      if (state == ConnectionState.connecting) {
        final sessionId = Uuid().v4();
        final socksPort = launch.socksPort!;
        final tunnelConfig = launch.tunnelConfig!;
        final configJson = jsonEncode(launch.nodes);
        CoreApi().connect(sessionId, socksPort, tunnelConfig, configJson);
      }
    } on DioException catch (e) {
      // 只有当前 token 没有被替换时才清空
      if (_cancelToken == currentToken) {
        _cancelToken = null;
      }

      // 如果是取消错误，不处理
      if (e.type == DioExceptionType.cancel) {
        log(TAG, '请求已取消');
        return;
      }

      if (state == ConnectionState.connecting) {
        state = ConnectionState.disconnected;
      }
      log(TAG, 'getDispatchInfo error: $e');
    } catch (e) {
      // 只有当前 token 没有被替换时才清空
      if (_cancelToken == currentToken) {
        _cancelToken = null;
      }

      if (state == ConnectionState.connecting) {
        state = ConnectionState.disconnected;
      }
      log(TAG, 'getDispatchInfo error: $e');
    }
  }

  /// 开始监听来自 Android 的事件
  void _startListeningToEvents() {
    _eventSubscription = onEventChange().listen(
      _handleEventChange,
      onError: (error) {
        log(TAG, '事件流错误: $error');
      },
    );
  }

  // 处理从原生端接收到的消息
  void _handleEventChange(String message) {
    try {
      final Map<String, dynamic> json = jsonDecode(message);
      final String type = json['type'] ?? '';

      switch (type) {
        case 'vpn_status':
          _handleVpnStatus(VpnStatusMessage.fromJson(json));
          break;
        case 'timer_update':
          _handleTimerUpdate(TimerUpdateMessage.fromJson(json));
          break;
        default:
          log(TAG, '未知消息类型: $type');
      }
    } catch (e) {
      log(TAG, '解析消息失败: $e');
    }
  }

  void _handleVpnStatus(VpnStatusMessage message) {
    final vpnError = VpnError.fromValue(message.status);
    log(TAG, 'VPN状态变化: ${vpnError.label}, message=${message.message}');
    // 根据状态码处理不同的VPN状态
    switch (vpnError) {
      case VpnError.idle:
        // disconnected
        _onVpnDisconnected();
        break;
      case VpnError.connecting:
        // connecting
        _onVpnConnecting();
        break;
      case VpnError.connected:
        // connected
        _onVpnConnected();
        break;
      case VpnError.error:
        // error
        _onVpnError();
        break;
      case VpnError.serviceDisconnected:
        // service disconnected
        _onVpnServiceDisconnected();
        break;
      case VpnError.permissionDenied:
        // permission denied
        _onVpnPermissionDenied();
        break;
    }
  }

  void _handleTimerUpdate(TimerUpdateMessage message) {
    log(
      TAG,
      '计时更新: time=${message.currentTime}, mode=${message.mode}, running=${message.isRunning}, paused=${message.isPaused}',
    );

    timer = _formatTime(message.currentTime);

    // 处理计时更新
    if (message.isRunning) {
      if (message.isPaused) {
        _onTimerPaused(message.currentTime, message.mode);
      } else {
        _onTimerRunning(message.currentTime, message.mode);
      }
    } else {
      _onTimerStopped();
    }
  }

  // VPN状态处理方法
  void _onVpnDisconnected() {
    log(TAG, 'VPN已断开连接');
    // 更新UI状态
    state = ConnectionState.disconnected;
    timer = "00:00:00";
    HapticFeedbackManager.connectionDisconnected();
    FeedbackBottomSheet.show();
  }

  void _onVpnConnecting() {
    log(TAG, 'VPN正在连接');
    // 显示连接中状态
    state = ConnectionState.connecting;
  }

  void _onVpnConnected() {
    log(TAG, 'VPN已连接');
    // 显示已连接状态
    state = ConnectionState.connected;
    HapticFeedbackManager.connectionSuccess();
  }

  void _onVpnError() {
    log(TAG, 'VPN连接错误');
    // 显示错误信息
    state = ConnectionState.disconnected;
    timer = "00:00:00";
    HapticFeedbackManager.connectionDisconnected();
  }

  void _onVpnServiceDisconnected() {
    log(TAG, 'VPN服务异常断开连接');
    // 显示错误信息
    state = ConnectionState.disconnected;
    timer = "00:00:00";
    HapticFeedbackManager.connectionDisconnected();
    // 可以显示错误提示
    ErrorDialog.show(message: 'VPN服务异常断开连接');
  }

  void _onVpnPermissionDenied() {
    log(TAG, 'VPN权限拒绝');
    // 显示权限拒绝状态
    state = ConnectionState.disconnected;
    HapticFeedbackManager.connectionDisconnected();
    // 可以显示错误提示
    ErrorDialog.show(message: '权限拒绝');
  }

  // 计时器状态处理方法
  void _onTimerRunning(int currentTime, int mode) {
    log(
      TAG,
      '计时器运行中: ${_formatTime(currentTime)}, 模式: ${mode == 0 ? "普通计时" : "倒计时"}',
    );
  }

  void _onTimerPaused(int currentTime, int mode) {
    log(
      TAG,
      '计时器已暂停: ${_formatTime(currentTime)}, 模式: ${mode == 0 ? "普通计时" : "倒计时"}',
    );
  }

  void _onTimerStopped() {
    log(TAG, '计时器已停止');
  }

  // 格式化时间显示
  String _formatTime(int timeMs) {
    final totalSeconds = (timeMs / 1000).abs().round();
    final days = totalSeconds ~/ 86400; // 86400 = 24 * 3600
    final hours = (totalSeconds % 86400) ~/ 3600;
    final minutes = (totalSeconds % 3600) ~/ 60;
    final seconds = totalSeconds % 60;

    if (days > 0) {
      return '$days days ${hours.toString().padLeft(2, '0')}:${minutes.toString().padLeft(2, '0')}:${seconds.toString().padLeft(2, '0')}';
    } else if (hours > 0) {
      return '${hours.toString().padLeft(2, '0')}:${minutes.toString().padLeft(2, '0')}:${seconds.toString().padLeft(2, '0')}';
    } else {
      return '00:${minutes.toString().padLeft(2, '0')}:${seconds.toString().padLeft(2, '0')}';
    }
  }
}
