import utils
from utils.mysql_helper import MySQLHelper
from datetime import datetime
from models.user_data import UserModel

class UserStore:
    def __init__(self):
        self._db_helper = MySQLHelper()

    def query_user_all_paginated(self, page: int, per_page: int, keyword: str = None):
        offset = (page - 1) * per_page
        sql_count = "SELECT COUNT(*) as count FROM sys_user WHERE is_del=%s"
        sql = "SELECT id,username,email,phone,name,last_login,delete_by,deleted_at,create_by,created_at,update_by,updated_at FROM sys_user WHERE is_del=%s"
        params_count = (0,)
        params = (0,)
        if keyword:
            sql_count += " AND (username LIKE %s OR email LIKE %s OR phone LIKE %s OR name LIKE %s)"
            sql += " AND (username LIKE %s OR email LIKE %s OR phone LIKE %s OR name LIKE %s)"
            keyword_params = (f"%{keyword}%", f"%{keyword}%", f"%{keyword}%", f"%{keyword}%")
            params_count += keyword_params
            params += keyword_params
        sql += " ORDER BY created_at DESC LIMIT %s OFFSET %s"
        params += (per_page, offset)
        with self._db_helper:
            result_count = self._db_helper.fetch_one(sql_count, params_count)
            count = result_count["count"] if result_count else 0
            result = self._db_helper.execute_query(sql, params)
            data = []
            if not result:
                return data, count
            for item in result:
                data.append(
                    UserModel(
                        user_id=item["id"],
                        username=item["username"],
                        email=item["email"],
                        phone=item["phone"],
                        name=item["name"],
                        last_login=item["last_login"],
                        delete_by=item["delete_by"],
                        deleted_at=item["deleted_at"],
                        create_by=item["create_by"],
                        created_at=item["created_at"],
                        update_by=item["update_by"],
                        updated_at=item["updated_at"]
                    ))
            return data, count

    def query_user_by_id(self, user_id: int) -> UserModel | None:
        sql = "SELECT id,username,password,email,phone,name,last_login,delete_by,deleted_at,create_by,created_at,update_by,updated_at FROM sys_user WHERE is_del=0 AND id = %s"
        params = (user_id,)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, params)
            if not result:
                return None
            user = UserModel(
                user_id=result["id"],
                username=result["username"],
                email=result["email"],
                phone=result["phone"],
                name=result["name"],
                last_login=result["last_login"],
                delete_by=result["delete_by"],
                deleted_at=result["deleted_at"],
                create_by=result["create_by"],
                created_at=result["created_at"],
                update_by=result["update_by"],
                updated_at=result["updated_at"]
            )
            user.set_password(result["password"])
            return user
    def query_user(self, keyword: str) -> UserModel | None:
        # 构建基础SQL
        base_sql = "SELECT id,username,password,email,phone,name,last_login,delete_by,deleted_at,create_by,created_at,update_by,updated_at FROM sys_user WHERE is_del=0"
        
        # 根据关键字类型构建查询条件
        if utils.is_email(keyword):
            sql = f"{base_sql} AND email = %s"
        elif utils.is_phone(keyword):
            sql = f"{base_sql} AND phone = %s"
        else:
            sql = f"{base_sql} AND username = %s"

        params = (keyword,)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, params)
            if not result:
                return None
            user = UserModel(
                user_id=result["id"],
                username=result["username"],
                email=result["email"],
                phone=result["phone"],
                name=result["name"],
                last_login=result["last_login"],
                delete_by=result["delete_by"],
                deleted_at=result["deleted_at"],
                create_by=result["create_by"],
                created_at=result["created_at"],
                update_by=result["update_by"],
                updated_at=result["updated_at"]
            )
            user.set_password(result["password"])
            return user
    def query_user_by_username(self, username: str) -> UserModel | None:
        sql = "SELECT id,username,email,phone,name FROM sys_user WHERE is_del=0 AND username = %s"
        params = (username,)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, params)
            if not result:
                return None
            user = UserModel(
                user_id=result["id"],
                username=result["username"],
                email=result["email"],
                phone=result["phone"],
                name=result["name"],
            )
            return user

    def insert_user(self, user_data: UserModel):
        sql = "INSERT INTO sys_user (username,password,email,phone,name,create_by,created_at,update_by,updated_at) VALUES (%s,%s,%s,%s,%s,%s,%s,%s,%s)"
        params = (
            user_data.username,
            user_data._password,
            user_data.email,
            user_data.phone,
            user_data.name,
            user_data.create_by,
            datetime.now(),
            user_data.update_by,
            datetime.now()
        )
        with self._db_helper:
            self._db_helper.execute_non_query(sql, params)

    def update_user(self, user_data: UserModel):
        sql = "UPDATE sys_user SET email=%s,phone=%s,name=%s,update_by=%s,updated_at=%s WHERE id=%s"
        params = (
            user_data.email,
            user_data.phone,
            user_data.name,
            user_data.update_by,
            datetime.now(),
            user_data.id
        )
        with self._db_helper:
            self._db_helper.execute_non_query(sql, params)

    def update_user_password(self, user_id: int, password: str):
        sql = "UPDATE sys_user SET password=%s,updated_at=%s WHERE id=%s"
        params = (password, datetime.now(), user_id)
        with self._db_helper:
            self._db_helper.execute_non_query(sql, params)

    def update_last_login(self, user_id: int):
        sql = "UPDATE sys_user SET last_login=%s WHERE id=%s"
        params = (datetime.now(), user_id)
        with self._db_helper:
            self._db_helper.execute_non_query(sql, params)

    def delete_user(self, user_id: int, delete_by: str=""):
        sql = "UPDATE sys_user SET is_del=1,delete_by=%s,deleted_at=%s WHERE id=%s"
        params = (delete_by, datetime.now(), user_id)
        with self._db_helper:
            self._db_helper.execute_non_query(sql, params)

    def check_username_exists(self, username: str, exclude_user_id: int = None) -> bool:
        sql = "SELECT COUNT(*) as count FROM sys_user WHERE is_del=0 AND username = %s"
        params = [username]
        if exclude_user_id:
            sql += " AND id != %s"
            params.append(exclude_user_id)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, tuple(params))
            return result["count"] > 0 if result else False

    def check_email_exists(self, email: str, exclude_user_id: int = None) -> bool:
        sql = "SELECT COUNT(*) as count FROM sys_user WHERE is_del=0 AND email = %s"
        params = [email]
        if exclude_user_id:
            sql += " AND id != %s"
            params.append(exclude_user_id)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, tuple(params))
            return result["count"] > 0 if result else False

    def check_phone_exists(self, phone: str, exclude_user_id: int = None) -> bool:
        sql = "SELECT COUNT(*) as count FROM sys_user WHERE is_del=0 AND phone = %s"
        params = [phone]
        if exclude_user_id:
            sql += " AND id != %s"
            params.append(exclude_user_id)
        with self._db_helper:
            result = self._db_helper.fetch_one(sql, tuple(params))
            return result["count"] > 0 if result else False