import 'package:auto_route/auto_route.dart';
import 'package:dio/dio.dart';
import 'package:eitc_erm_dental_flutter/app_router.gr.dart';
import 'package:eitc_erm_dental_flutter/funcs.dart';
import 'package:eitc_erm_dental_flutter/http/api_exception.dart';
import 'package:eitc_erm_dental_flutter/http/api_response.dart';
import 'package:eitc_erm_dental_flutter/http/gzkj_response.dart';
import 'package:eitc_erm_dental_flutter/http/token_interceptor.dart';
import 'package:eitc_erm_dental_flutter/main.dart';
import 'package:pretty_dio_logger/pretty_dio_logger.dart';

class Http {
  static Http? _instance;

  static Http get instance => _instance ??= Http._();

  late Dio _dio;

  Http._() {
    _dio = Dio(BaseOptions(
      //本地开发
      //baseUrl: "http://192.168.3.142:8081",
      //测试服
      //baseUrl: "http://39.105.121.97:8081",
      //生产环境
      baseUrl: "http://106.74.15.131:8081",
      connectTimeout: const Duration(seconds: 10),
      sendTimeout: Duration.zero,
      receiveTimeout: Duration.zero,
    ));
    _dio.interceptors.addAll([
      TokenInterceptor(),
      PrettyDioLogger(
          requestHeader: true, requestBody: true, responseHeader: true),
    ]);
  }

  ///返回dio对象
  Dio get dio => _dio;

  Future<T?> request<T>(Future<ApiResponse<T>> func) async {
    try {
      ApiResponse<T> response = await func;
      if (response.isSuccess) {
        return response.data;
      }
      //401:Token失效,403:无效的Token
      if (response.code == 401 || response.code == 403) {
        //清除数据
        logoutClearData();
        if (navigatorKey.currentState != null &&
            navigatorKey.currentState!.mounted) {
          logd("token失效,跳转到登录页面");
          popAllRoutes(navigatorKey.currentState!.context);
          navigatorKey.currentState!.context
              .pushRoute(LoginRoute(cancelable: false));
          showToast(text: getS().tokenInvalidHint);
          return response.data;
        }
      }
      throw ApiException(response.code, response.msg);
    } catch (e) {
      if (e is! ApiException) {
        loge("请求异常", error: e);
      }
      throw ApiException.from(e);
    }
  }

  ///上传
  Future<ApiResponse<T>> upload<T>(String path,
      {Object? data,
      Map<String, dynamic>? queryParameters,
      Options? options,
      CancelToken? cancelToken,
      ProgressCallback? onSendProgress,
      ProgressCallback? onReceiveProgress,
      required T Function(Object? json) fromJsonT}) async {
    Response response = await _dio.post(path,
        data: data,
        queryParameters: queryParameters,
        options: options,
        cancelToken: cancelToken,
        onSendProgress: onSendProgress,
        onReceiveProgress: onReceiveProgress);

    return ApiResponse.fromJson(response.data, fromJsonT);
  }

  ///上传到国中康健接口
  Future<GzkjResponse<T>> uploadGzkj<T>(String path,
      {Object? data,
      Map<String, dynamic>? queryParameters,
      Options? options,
      CancelToken? cancelToken,
      ProgressCallback? onSendProgress,
      ProgressCallback? onReceiveProgress,
      required T Function(Object? json) fromJsonT}) async {
    Response response = await _dio.post(path,
        data: data,
        queryParameters: queryParameters,
        options: options,
        cancelToken: cancelToken,
        onSendProgress: onSendProgress,
        onReceiveProgress: onReceiveProgress);
    return GzkjResponse.fromJson(response.data, fromJsonT);
  }

  ///下载
  Future<Response<dynamic>> download<T>(
    String urlPath,
    dynamic savePath, {
    ProgressCallback? onReceiveProgress,
    Map<String, dynamic>? queryParameters,
    CancelToken? cancelToken,
    bool deleteOnError = true,
    String lengthHeader = Headers.contentLengthHeader,
    Object? data,
    Options? options,
  }) async {
    return _dio.download(urlPath, savePath,
        onReceiveProgress: onReceiveProgress,
        queryParameters: queryParameters,
        cancelToken: cancelToken,
        deleteOnError: deleteOnError,
        lengthHeader: lengthHeader,
        data: data,
        options: options);
  }
}
