import Foundation
import Security

/// 用于安全存储和检索敏感信息（如令牌）的 Keychain 帮助类
public class KeychainHelper {
    // Keychain 键名
    private enum KeychainKey: String {
        case accessToken = "com.memorywake.accessToken"
        case refreshToken = "com.memorywake.refreshToken"
    }
    
    /// 保存访问令牌到 Keychain
    public static func saveAccessToken(_ token: String) -> Bool {
        return save(token, for: .accessToken)
    }
    
    /// 从 Keychain 获取访问令牌
    public static func getAccessToken() -> String? {
        return get(for: .accessToken)
    }
    
    /// 保存刷新令牌到 Keychain
    public static func saveRefreshToken(_ token: String) -> Bool {
        return save(token, for: .refreshToken)
    }
    
    /// 从 Keychain 获取刷新令牌
    public static func getRefreshToken() -> String? {
        return get(for: .refreshToken)
    }
    
    /// 删除所有存储的令牌
    public static func clearTokens() {
        delete(for: .accessToken)
        delete(for: .refreshToken)
    }
    
    // MARK: - 私有方法
    
    private static func save(_ string: String, for key: KeychainKey) -> Bool {
        guard let data = string.data(using: .utf8) else { return false }
        
        let query: [String: Any] = [
            kSecClass as String: kSecClassGenericPassword,
            kSecAttrAccount as String: key.rawValue,
            kSecValueData as String: data
        ]
        
        // 先删除已存在的项目
        SecItemDelete(query as CFDictionary)
        
        // 添加新项目
        let status = SecItemAdd(query as CFDictionary, nil)
        return status == errSecSuccess
    }
    
    private static func get(for key: KeychainKey) -> String? {
        let query: [String: Any] = [
            kSecClass as String: kSecClassGenericPassword,
            kSecAttrAccount as String: key.rawValue,
            kSecReturnData as String: true,
            kSecMatchLimit as String: kSecMatchLimitOne
        ]
        
        var dataTypeRef: AnyObject?
        let status = SecItemCopyMatching(query as CFDictionary, &dataTypeRef)
        
        guard status == errSecSuccess, let data = dataTypeRef as? Data else {
            return nil
        }
        
        return String(data: data, encoding: .utf8)
    }
    
    private static func delete(for key: KeychainKey) {
        let query: [String: Any] = [
            kSecClass as String: kSecClassGenericPassword,
            kSecAttrAccount as String: key.rawValue
        ]
        
        SecItemDelete(query as CFDictionary)
    }
}
