import 'dart:convert';
import 'dart:typed_data';
import 'package:crypto/crypto.dart';
import 'package:encrypt/encrypt.dart' as encrypt;

/// AES加密解密工具类
/// 算法：AES-256-CBC
/// 填充：PKCS7
/// 密钥生成：SHA-256(keyStr) → 32字节
/// IV生成：SHA-256(MD5(nonce) + keyStr) → 取前16字节
class KRAesUtil {
  /// 生成密钥（使用SHA-256）
  static encrypt.Key _generateKey(String keyStr) {
    final keyBytes = sha256.convert(utf8.encode(keyStr)).bytes;
    return encrypt.Key(Uint8List.fromList(keyBytes));
  }

  /// 生成IV（使用MD5 + SHA-256）
  static encrypt.IV _generateIv(String ivStr, String keyStr) {
    // 首先用MD5处理ivStr
    final md5Hash = md5.convert(utf8.encode(ivStr)).bytes;

    // 将MD5结果转换为十六进制字符串
    final md5Hex = _hexEncode(md5Hash);

    // 拼接 md5Hex + keyStr
    final combinedKey = md5Hex + keyStr;

    // 对拼接后的字符串做SHA-256
    final finalHash = sha256.convert(utf8.encode(combinedKey)).bytes;

    // 取前16字节作为IV
    return encrypt.IV(Uint8List.fromList(finalHash.sublist(0, 16)));
  }

  /// 将字节数组转换为十六进制字符串
  static String _hexEncode(List<int> bytes) {
    return bytes.map((byte) => byte.toRadixString(16).padLeft(2, '0')).join('');
  }

  /// 加密数据
  ///
  /// 参数:
  /// - plainText: 要加密的明文
  /// - keyStr: 加密密钥
  ///
  /// 返回:
  /// - Map包含两个字段: data(加密后的Base64字符串), time(ISO8601时间戳)
  static Map<String, String> encryptData(String plainText, String keyStr) {
    // 生成时间戳
    final nonce = DateTime.now().toIso8601String();

    // 生成密钥和IV
    final key = _generateKey(keyStr);
    final iv = _generateIv(nonce, keyStr);

    // 创建加密器 (AES-256-CBC with PKCS7 padding)
    final encrypter = encrypt.Encrypter(
      encrypt.AES(key, mode: encrypt.AESMode.cbc, padding: 'PKCS7'),
    );

    // 加密
    final encrypted = encrypter.encrypt(plainText, iv: iv);

    return {
      'data': encrypted.base64,
      'time': nonce,
    };
  }

  /// 解密数据
  ///
  /// 参数:
  /// - encryptedData: 加密后的Base64字符串
  /// - nonce: 时间戳
  /// - keyStr: 解密密钥
  ///
  /// 返回:
  /// - 解密后的明文字符串
  static String decryptData(String encryptedData, String nonce, String keyStr) {
    // 生成密钥和IV
    final key = _generateKey(keyStr);
    final iv = _generateIv(nonce, keyStr);

    // 创建解密器 (AES-256-CBC with PKCS7 padding)
    final encrypter = encrypt.Encrypter(
      encrypt.AES(key, mode: encrypt.AESMode.cbc, padding: 'PKCS7'),
    );

    // 解密
    final decrypted = encrypter.decrypt64(encryptedData, iv: iv);

    return decrypted;
  }

  /// 加密JSON对象
  ///
  /// 参数:
  /// - jsonData: 要加密的JSON对象
  /// - keyStr: 加密密钥
  ///
  /// 返回:
  /// - Map包含两个字段: data(加密后的Base64字符串), time(ISO8601时间戳)
  static Map<String, String> encryptJson(Map<String, dynamic> jsonData, String keyStr) {
    final plainText = jsonEncode(jsonData);
    return encryptData(plainText, keyStr);
  }

  /// 解密JSON对象
  ///
  /// 参数:
  /// - encryptedData: 加密后的Base64字符串
  /// - nonce: 时间戳
  /// - keyStr: 解密密钥
  ///
  /// 返回:
  /// - 解密后的JSON对象
  static Map<String, dynamic> decryptJson(String encryptedData, String nonce, String keyStr) {
    final decrypted = decryptData(encryptedData, nonce, keyStr);
    return jsonDecode(decrypted) as Map<String, dynamic>;
  }
}
