import mysql.connector
from mysql.connector import Error
from typing import Dict, List, Optional, Any, Tuple

# -------------------------- 1. 纯连接构造者：仅创建连接，不处理任何操作 --------------------------
class MySQLConnectionBuilder:
    """MySQL连接构造者"""
    def __init__(self, host: str=None, port: int=3306, database: str=None, user: str=None, password: str=None, charset: str="utf8mb4", timeout: int=30):
        self.config = {
            "host": host,
            "port": port,
            "database": database,
            "user": user,
            "password": password,
            "charset": charset,
            "connection_timeout": timeout
        }

    # 链式配置
    def host(self, host: str) -> "MySQLConnectionBuilder":
        self.config["host"] = host
        return self
    
    def port(self, port: int) -> "MySQLConnectionBuilder":
        self.config["port"] = port
        return self
        
    def database(self, database: str) -> "MySQLConnectionBuilder":
        self.config["database"] = database
        return self

    def user(self, user: str) -> "MySQLConnectionBuilder":
        self.config["user"] = user
        return self
    
    def password(self, password: str) -> "MySQLConnectionBuilder":
        self.config["password"] = password
        return self

    def timeout(self, timeout: int) -> "MySQLConnectionBuilder":
        self.config["connection_timeout"] = timeout
        return self

    def build(self) -> Optional[mysql.connector.connection.MySQLConnection]:
        try:
            required = ["database", "user", "password"]
            if not all(self.config.get(k) for k in required):
                raise ValueError("缺少核心数据库配置")
            
            connection = mysql.connector.connect(**self.config)
            return connection if connection.is_connected() else None
        except Error as e:
            print(f"连接创建失败：{e}")
            return None

# -------------------------- 2. 连接管理器：封装通用check/close/CRUD逻辑 --------------------------
class MySQLConnectionManager:
    """连接管理器：封装通用的数据库操作逻辑，数据表类调用此类方法"""
    def __init__(self, dbconnection: mysql.connector.connection.MySQLConnection):
        self.connection = dbconnection  # 接收构造者创建的原生连接
        self.cursor = None

    # 通用：检查连接有效性
    def check(self) -> bool:
        if not self.connection or not self.connection.is_connected():
            print("❌ 数据库连接已失效")
            return False
        return True

    # 通用：关闭游标（所有操作后必调）
    def close_cursor(self) -> None:
        if self.cursor:
            self.cursor.close()
            self.cursor = None

    # 通用：查询单条数据（select one）
    def query(self, sql: str, params: Tuple = ()) -> Optional[Dict[str, Any]]:
        if not self.check():
            return None
        try:
            self.cursor = self.connection.cursor(dictionary=True)
            self.cursor.execute(sql, params)
            return self.cursor.fetchone()
        except Error as e:
            print(f"❌ 查询单条数据失败：{e}")
            return None
        finally:
            self.close_cursor()

    # 通用：查询多条数据（select all）
    def queryall(self, sql: str, params: Tuple = ()) -> List[Dict[str, Any]]:
        if not self.check():
            return []
        try:
            self.cursor = self.connection.cursor(dictionary=True)
            self.cursor.execute(sql, params)
            return self.cursor.fetchall() or []
        except Error as e:
            print(f"❌ 查询多条数据失败：{e}")
            return []
        finally:
            self.close_cursor()

    # 通用：增/删/改操作（insert/update/delete）
    def execute(self, sql: str, params: Tuple = ()) -> Tuple[bool, int]:
        """
        返回值：(操作是否成功, 影响行数)
        """
        if not self.check():
            return False, 0
        try:
            self.cursor = self.connection.cursor()
            self.cursor.execute(sql, params)
            self.connection.commit()
            return True, self.cursor.rowcount
        except Error as e:
            self.connection.rollback()
            print(f"❌ 执行增删改失败：{e}")
            return False, 0
        finally:
            self.close_cursor()

    # 管理器中新增批量插入方法
    def batch_execute(self, sql: str, params_list: List[Tuple]) -> Tuple[bool, int]:
        if not self.check():
            return False, 0
        try:
            self.cursor = self.connection.cursor()
            self.cursor.executemany(sql, params_list)
            self.connection.commit()
            return True, self.cursor.rowcount
        except Error as e:
            self.connection.rollback()
            print(f"批量执行失败：{e}")
            return False, 0
        finally:
            self.close_cursor()

    # 通用：关闭连接
    def close(self) -> None:
        self.close_cursor()
        if self.connection and self.connection.is_connected():
            self.connection.close()
            print("✅ 数据库连接已关闭")
        self.connection = None

    # 支持with语句
    def __enter__(self):
        return self

    def __exit__(self, exc_type, exc_val, exc_tb):
        self.close()

