import 'package:autosos_flutter/api/_api_client.dart';
import 'package:autosos_flutter/model/base_response.dart';
import 'package:autosos_flutter/model/misc.dart';
import 'package:autosos_flutter/model/payment.dart';
import 'package:autosos_flutter/model/user.dart';

/// 用户 / 认证 / 我的 相关 API
class UserApi {
  static final UserApi instance = UserApi._();
  UserApi._();

  final _http = ApiClient.instance.http;

  // ===== 登录相关 =====

  /// 账号密码登录
  Future<BaseResponse<LoginToken>> login({
    required String username,
    required String password,
    String? code,
    String? cid,
    String? wxOpenid,
    String? wxUnionid,
  }) async {
    final r = await _http.post('/v2/auth/get-access-token', {
      'type': 1,
      'username': username,
      'password': password,
      'code': code ?? '',
      'getui_cid': cid ?? '',
      'wx_openid': wxOpenid ?? '',
      'wx_unionid': wxUnionid ?? '',
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => LoginToken.fromJson(d as Map<String, dynamic>));
  }

  /// 发送短信验证码
  Future<BaseResponse<SmsResult>> sendSms(String mobile) async {
    final r = await _http.post('/v2/auth/send-sms', {'mobile': mobile});
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => SmsResult.fromJson(d as Map<String, dynamic>));
  }

  /// 手机验证码登录
  Future<BaseResponse<LoginToken>> loginBySms({
    required String mobile,
    required String code,
    String? cid,
  }) async {
    final r = await _http.post('/v2/auth/login-by-sms', {
      'mobile': mobile,
      'code': code,
      'cid': cid,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => LoginToken.fromJson(d as Map<String, dynamic>));
  }

  /// 微信登录（前端通过 fluwx 拿到 code，调后端）
  Future<BaseResponse<LoginToken>> loginByWx({
    required String wxCode,
    String? cid,
  }) async {
    final r = await _http.post('/v2/auth/login-by-wx', {
      'wx_code': wxCode,
      'cid': cid,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => LoginToken.fromJson(d as Map<String, dynamic>));
  }

  /// 绑定手机号
  Future<BaseResponse<bool>> bindPhone({
    required String mobile,
    required String code,
  }) async {
    final r = await _http.post('/v2/auth/bind-phone', {
      'mobile': mobile,
      'code': code,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 绑定微信
  Future<BaseResponse<bool>> bindWx({
    required String wxCode,
    required String mobile,
    required String code,
  }) async {
    final r = await _http.post('/v2/auth/bind-wx', {
      'wx_code': wxCode,
      'mobile': mobile,
      'code': code,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 退出登录
  Future<BaseResponse<bool>> logout() async {
    final r = await _http.post('/v2/auth/logout');
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  // ===== 我的 =====

  /// 用户信息
  Future<BaseResponse<UserInfo>> info() async {
    final r = await _http.get('/v2/user/info');
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => UserInfo.fromJson(d as Map<String, dynamic>));
  }

  /// 完善资料
  Future<BaseResponse<UserInfo>> perfectInfo(Map<String, dynamic> data) async {
    final r = await _http.post('/v2/user/perfect', data);
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => UserInfo.fromJson(d as Map<String, dynamic>));
  }

  /// 上传身份证照片
  Future<BaseResponse<List<String>>> uploadIdCards(List<String> paths) async {
    final r = await _http.post('/v2/user/upload-id', {'paths': paths});
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => (d as List).cast<String>());
  }

  /// 个人认证
  Future<BaseResponse<bool>> authPersonal({
    required String name,
    required String idCard,
    required String idCardFront,
    required String idCardBack,
  }) async {
    final r = await _http.post('/v2/user/auth-personal', {
      'name': name,
      'id_card': idCard,
      'id_card_front': idCardFront,
      'id_card_back': idCardBack,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 企业认证
  Future<BaseResponse<bool>> authEnterprise({
    required String companyName,
    required String licenseNo,
    required String licenseImg,
    String? legalPerson,
    String? legalIdCard,
    String? legalIdFront,
    String? legalIdBack,
  }) async {
    final r = await _http.post('/v2/user/auth-enterprise', {
      'company_name': companyName,
      'license_no': licenseNo,
      'license_img': licenseImg,
      'legal_person': legalPerson,
      'legal_id_card': legalIdCard,
      'legal_id_front': legalIdFront,
      'legal_id_back': legalIdBack,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 司机认证
  Future<BaseResponse<bool>> authDriver({
    required String driverNo,
    required String driverLicense,
    String? drivingLicenseFront,
    String? drivingLicenseBack,
  }) async {
    final r = await _http.post('/v2/user/auth-driver', {
      'driver_no': driverNo,
      'driver_license': driverLicense,
      'driving_license_front': drivingLicenseFront,
      'driving_license_back': drivingLicenseBack,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 提现申请
  Future<BaseResponse<bool>> applyWithdrawal({
    required double amount,
    required String bankAccount,
    String? realName,
  }) async {
    final r = await _http.post('/v2/user/withdraw', {
      'amount': amount,
      'bank_account': bankAccount,
      'real_name': realName,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 提现记录
  Future<BaseResponse<PageResult<WithdrawalRecord>>> withdrawalRecords({
    int page = 1,
    int size = 20,
  }) async {
    final r = await _http.get('/v2/user/withdraw-records', {
      'page': page,
      'size': size,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => PageResult.fromJson(d as Map<String, dynamic>,
            (e) => WithdrawalRecord.fromJson(e as Map<String, dynamic>)));
  }

  /// 金额明细
  Future<BaseResponse<PageResult<AmountItem>>> amountList({
    int page = 1,
    int size = 20,
  }) async {
    final r = await _http.get('/v2/user/amount-list', {
      'page': page,
      'size': size,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => PageResult.fromJson(d as Map<String, dynamic>,
            (e) => AmountItem.fromJson(e as Map<String, dynamic>)));
  }

  /// 充值
  Future<BaseResponse<Recharge>> recharge({
    required double amount,
    required String payMethod,
  }) async {
    final r = await _http.post('/v2/user/recharge', {
      'amount': amount,
      'pay_method': payMethod,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => Recharge.fromJson(d as Map<String, dynamic>));
  }

  /// 反馈
  Future<BaseResponse<bool>> submitFeedback({
    required String content,
    String? contact,
    List<String>? images,
  }) async {
    final r = await _http.post('/v2/user/feedback', {
      'content': content,
      'contact': contact,
      'images': images,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 消息中心
  Future<BaseResponse<PageResult<MessengerItem>>> messages({
    int page = 1,
    int size = 20,
  }) async {
    final r = await _http.get('/v2/user/messages', {
      'page': page,
      'size': size,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => PageResult.fromJson(d as Map<String, dynamic>,
            (e) => MessengerItem.fromJson(e as Map<String, dynamic>)));
  }

  /// 标记消息已读
  Future<BaseResponse<bool>> readMessage(int id) async {
    final r = await _http.post('/v2/user/message/read', {'id': id});
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }

  /// 服务类型列表
  Future<BaseResponse<List<ServiceType>>> serviceTypes() async {
    final r = await _http.get('/v2/order/service-types');
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => (d as List).map((e) => ServiceType.fromJson(e as Map<String, dynamic>)).toList());
  }

  /// 检查更新
  Future<BaseResponse<AppUpdate>> checkUpdate() async {
    final r = await _http.get('/v2/app/check-update');
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => AppUpdate.fromJson(d as Map<String, dynamic>));
  }

  /// 心跳
  Future<BaseResponse<bool>> heartbeat({
    double? lat,
    double? lng,
    required int onlineTime,
  }) async {
    final r = await _http.post('/v2/user/heartbeat', {
      'lat': lat,
      'lng': lng,
      'online_time': onlineTime,
    });
    return BaseResponse.fromJson(r as Map<String, dynamic>,
        (d) => d as bool);
  }
}
