"""
User database model.
"""

from __future__ import annotations
from datetime import datetime
from typing import Optional

from sqlalchemy import String, Boolean, DateTime, Text, func
from sqlalchemy.ext.hybrid import hybrid_property
from sqlalchemy.orm import Mapped, mapped_column

from src.apps.base.models.base import Base


class User(Base):
    """
    User model for storing user account information.
    
    This model represents users in the system with basic authentication
    and profile information.
    """
    
    __tablename__ = "users"
    
    # Primary key
    id: Mapped[int] = mapped_column(primary_key=True, index=True, autoincrement=True)
    
    # Authentication fields
    email: Mapped[str] = mapped_column(String(255), unique=True, index=True, nullable=False)
    username: Mapped[str] = mapped_column(String(100), unique=True, index=True, nullable=False)
    hashed_password: Mapped[str] = mapped_column(String(255), nullable=False)
    
    # Profile information
    first_name: Mapped[Optional[str]] = mapped_column(String(100), nullable=True)
    last_name: Mapped[Optional[str]] = mapped_column(String(100), nullable=True)
    full_name: Mapped[Optional[str]] = mapped_column(String(200), nullable=True)
    
    # Account status
    is_active: Mapped[bool] = mapped_column(Boolean, default=True, nullable=False)
    is_verified: Mapped[bool] = mapped_column(Boolean, default=False, nullable=False)
    is_superuser: Mapped[bool] = mapped_column(Boolean, default=False, nullable=False)
    
    # Additional fields
    phone_number: Mapped[Optional[str]] = mapped_column(String(20), nullable=True)
    phone: Mapped[Optional[str]] = mapped_column(String(20), nullable=True)  # Alternative phone field name
    middle_name: Mapped[Optional[str]] = mapped_column(String(100), nullable=True)  # Middle name field
    user_id: Mapped[Optional[str]] = mapped_column(String(50), unique=True, index=True, nullable=True)  # External user ID
    bio: Mapped[Optional[str]] = mapped_column(Text, nullable=True)
    avatar_url: Mapped[Optional[str]] = mapped_column(String(500), nullable=True)
    deleted_at: Mapped[Optional[datetime]] = mapped_column(DateTime(timezone=True), nullable=True)  # Soft delete support
    
    # Timestamps
    created_at: Mapped[datetime] = mapped_column(DateTime(timezone=True), server_default=func.now(), nullable=False)
    updated_at: Mapped[datetime] = mapped_column(DateTime(timezone=True), server_default=func.now(), onupdate=func.now(), nullable=False)
    last_login: Mapped[Optional[datetime]] = mapped_column(DateTime(timezone=True), nullable=True)
    
    # Relationships - temporarily commented out to avoid circular import issues
    # TODO: Fix relationship configuration for distributed models
    # auth_sessions: Mapped[List["AuthSession"]] = relationship("AuthSession", back_populates="user", cascade="all, delete-orphan")
    

    @property
    def display_name(self) -> str:
        """Get display name, preferring full_name over username."""
        return self.full_name or self.username
    
    def update_full_name(self) -> None:
        """Update the full_name field based on first_name and last_name."""
        if self.first_name and self.last_name:
            self.full_name = f"{self.first_name} {self.last_name}"
        elif self.first_name:
            self.full_name = self.first_name
        elif self.last_name:
            self.full_name = self.last_name
        else:
            self.full_name = None

    @hybrid_property
    def is_user_active(self) -> bool:
        """
        Check if user is active.
        
        Returns:
            True if user is active, False otherwise
        """
        return self.is_active if hasattr(self, 'is_active') else True

    @hybrid_property  
    def is_user_verified(self) -> bool:
        """
        Check if user is verified.
        
        Returns:
            True if user is verified, False otherwise
        """
        return self.is_verified if hasattr(self, 'is_verified') else False