"""
Chat Service — Data Models.

سیستم چت داخلی پلتفرم (Modular Monolith — Microservice-Ready).
شامل: کانال، عضویت، پیام، پیوست، رسید خوانده‌شدن، حضور آنلاین.
"""
import uuid

from django.conf import settings
from django.db import models

from apps.core.tenant.models import TenantAwareModel


# ══════════════════════════════════════════════════════════════
# Enums
# ══════════════════════════════════════════════════════════════

class ChannelType(models.TextChoices):
    DIRECT = 'direct', 'خصوصی'
    GROUP = 'group', 'گروهی'
    PUBLIC = 'public', 'عمومی'
    PROJECT = 'project', 'پروژه'


class ChannelVisibility(models.TextChoices):
    PUBLIC = 'public', 'همه Tenant'
    PRIVATE = 'private', 'فقط اعضا'
    PROJECT = 'project', 'اعضای پروژه'


class MemberRole(models.TextChoices):
    OWNER = 'owner', 'مالک'
    ADMIN = 'admin', 'مدیر'
    MEMBER = 'member', 'عضو'
    GUEST = 'guest', 'مهمان'


class MemberStatus(models.TextChoices):
    ACTIVE = 'active', 'فعال'
    MUTED = 'muted', 'بی‌صدا'
    BANNED = 'banned', 'مسدود'
    LEFT = 'left', 'خارج شده'


class MessageType(models.TextChoices):
    TEXT = 'text', 'متن'
    FILE = 'file', 'فایل'
    IMAGE = 'image', 'تصویر'
    SYSTEM = 'system', 'سیستمی'


class PresenceStatus(models.TextChoices):
    ONLINE = 'online', 'آنلاین'
    AWAY = 'away', 'دور'
    BUSY = 'busy', 'مشغول'
    OFFLINE = 'offline', 'آفلاین'


# ══════════════════════════════════════════════════════════════
# Channel — کانال گفتگو
# ══════════════════════════════════════════════════════════════

class Channel(TenantAwareModel):
    """
    کانال گفتگو.
    Direct: بین دو نفر | Group: چند نفر | Public: عمومی tenant | Project: مرتبط با پروژه.
    """
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    name = models.CharField('نام کانال', max_length=200, blank=True, default='')
    slug = models.SlugField('نامک', max_length=200, blank=True, default='', allow_unicode=True)
    description = models.TextField('توضیحات', blank=True, default='')
    avatar = models.ImageField('تصویر', upload_to='chat/avatars/', blank=True, null=True)

    channel_type = models.CharField(
        'نوع کانال',
        max_length=20,
        choices=ChannelType.choices,
        default=ChannelType.GROUP,
    )
    visibility = models.CharField(
        'سطح دسترسی',
        max_length=20,
        choices=ChannelVisibility.choices,
        default=ChannelVisibility.PRIVATE,
    )

    # --- Generic source (project, task, ...) ---
    source_type = models.CharField(
        'نوع منبع',
        max_length=50,
        blank=True,
        default='',
        help_text='نوع entity مرتبط (project, task, ...)',
    )
    source_id = models.UUIDField(
        'شناسه منبع',
        null=True,
        blank=True,
        db_index=True,
    )

    # --- Settings ---
    max_members = models.PositiveIntegerField('حداکثر اعضا', default=500)
    is_archived = models.BooleanField('آرشیو شده', default=False)

    # --- Metadata ---
    created_by = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.SET_NULL,
        null=True,
        related_name='created_channels',
        verbose_name='ایجادکننده',
    )
    last_message_at = models.DateTimeField('آخرین پیام', null=True, blank=True)
    message_count = models.PositiveIntegerField('تعداد پیام', default=0)

    created_at = models.DateTimeField('تاریخ ایجاد', auto_now_add=True)
    updated_at = models.DateTimeField('تاریخ بروزرسانی', auto_now=True)

    class Meta:
        db_table = 'chat_channel'
        verbose_name = 'کانال'
        verbose_name_plural = 'کانال‌ها'
        ordering = ['-last_message_at', '-created_at']
        indexes = [
            models.Index(fields=['source_type', 'source_id']),
        ]

    def __str__(self):
        return self.name or f"DM-{self.id}"


# ══════════════════════════════════════════════════════════════
# ChannelMember — عضویت در کانال
# ══════════════════════════════════════════════════════════════

class ChannelMember(TenantAwareModel):
    """عضویت کاربر در کانال."""
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    channel = models.ForeignKey(
        Channel,
        on_delete=models.CASCADE,
        related_name='members',
        verbose_name='کانال',
    )
    user = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.CASCADE,
        related_name='chat_memberships',
        verbose_name='کاربر',
    )

    role = models.CharField(
        'نقش',
        max_length=20,
        choices=MemberRole.choices,
        default=MemberRole.MEMBER,
    )
    status = models.CharField(
        'وضعیت',
        max_length=20,
        choices=MemberStatus.choices,
        default=MemberStatus.ACTIVE,
    )

    # --- آخرین پیام خوانده‌شده ---
    last_read_message = models.ForeignKey(
        'Message',
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
        related_name='+',
        verbose_name='آخرین پیام خوانده‌شده',
    )
    last_read_at = models.DateTimeField('آخرین خوانده‌شدن', null=True, blank=True)
    unread_count = models.PositiveIntegerField('خوانده‌نشده', default=0)

    # --- Notification settings ---
    notifications_enabled = models.BooleanField('اعلان فعال', default=True)

    joined_at = models.DateTimeField('تاریخ عضویت', auto_now_add=True)
    updated_at = models.DateTimeField('تاریخ بروزرسانی', auto_now=True)

    class Meta:
        db_table = 'chat_channel_member'
        verbose_name = 'عضو کانال'
        verbose_name_plural = 'اعضای کانال'
        unique_together = [('channel', 'user')]
        ordering = ['joined_at']

    def __str__(self):
        return f"{self.user} @ {self.channel}"


# ══════════════════════════════════════════════════════════════
# Message — پیام
# ══════════════════════════════════════════════════════════════

class Message(TenantAwareModel):
    """پیام در کانال."""
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    channel = models.ForeignKey(
        Channel,
        on_delete=models.CASCADE,
        related_name='messages',
        verbose_name='کانال',
    )
    sender = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.SET_NULL,
        null=True,
        related_name='chat_messages',
        verbose_name='فرستنده',
    )

    # --- Content ---
    message_type = models.CharField(
        'نوع پیام',
        max_length=20,
        choices=MessageType.choices,
        default=MessageType.TEXT,
    )
    content = models.TextField('محتوا', blank=True, default='')

    # --- Reply / Quote ---
    reply_to = models.ForeignKey(
        'self',
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
        related_name='replies',
        verbose_name='پاسخ به',
    )

    # --- Edit / Delete ---
    is_edited = models.BooleanField('ویرایش شده', default=False)
    edited_at = models.DateTimeField('تاریخ ویرایش', null=True, blank=True)
    is_deleted = models.BooleanField('حذف شده', default=False)
    deleted_at = models.DateTimeField('تاریخ حذف', null=True, blank=True)

    # --- Metadata ---
    metadata = models.JSONField('متادیتا', default=dict, blank=True)

    created_at = models.DateTimeField('تاریخ ایجاد', auto_now_add=True)

    class Meta:
        db_table = 'chat_message'
        verbose_name = 'پیام'
        verbose_name_plural = 'پیام‌ها'
        ordering = ['created_at']
        indexes = [
            models.Index(fields=['channel', 'created_at']),
        ]

    def __str__(self):
        text = self.content[:50] if self.content else f"[{self.message_type}]"
        return f"{self.sender}: {text}"


# ══════════════════════════════════════════════════════════════
# MessageAttachment — پیوست پیام
# ══════════════════════════════════════════════════════════════

class MessageAttachment(TenantAwareModel):
    """پیوست فایل به پیام (یکپارچه با File Service)."""
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    message = models.ForeignKey(
        Message,
        on_delete=models.CASCADE,
        related_name='attachments',
        verbose_name='پیام',
    )
    stored_file_id = models.UUIDField(
        'شناسه فایل',
        help_text='ارجاع به StoredFile در File Service',
    )

    # --- Cache metadata for quick display ---
    file_name = models.CharField('نام فایل', max_length=500)
    file_size = models.BigIntegerField('حجم', default=0)
    mime_type = models.CharField('نوع', max_length=255, blank=True, default='')

    created_at = models.DateTimeField('تاریخ ایجاد', auto_now_add=True)

    class Meta:
        db_table = 'chat_message_attachment'
        verbose_name = 'پیوست پیام'
        verbose_name_plural = 'پیوست‌های پیام'
        ordering = ['created_at']

    def __str__(self):
        return self.file_name


# ══════════════════════════════════════════════════════════════
# MessageReadReceipt — رسید خوانده‌شدن
# ══════════════════════════════════════════════════════════════

class MessageReadReceipt(TenantAwareModel):
    """رسید خوانده‌شدن پیام توسط کاربر."""
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    message = models.ForeignKey(
        Message,
        on_delete=models.CASCADE,
        related_name='read_receipts',
        verbose_name='پیام',
    )
    user = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.CASCADE,
        related_name='read_receipts',
        verbose_name='کاربر',
    )
    read_at = models.DateTimeField('تاریخ خوانده‌شدن', auto_now_add=True)

    class Meta:
        db_table = 'chat_message_read_receipt'
        verbose_name = 'رسید خوانده‌شدن'
        verbose_name_plural = 'رسیدهای خوانده‌شدن'
        unique_together = [('message', 'user')]

    def __str__(self):
        return f"{self.user} read {self.message_id}"


# ══════════════════════════════════════════════════════════════
# UserPresence — وضعیت حضور آنلاین
# ══════════════════════════════════════════════════════════════

class UserPresence(TenantAwareModel):
    """وضعیت حضور آنلاین کاربر."""
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    user = models.OneToOneField(
        settings.AUTH_USER_MODEL,
        on_delete=models.CASCADE,
        related_name='presence',
        verbose_name='کاربر',
    )
    status = models.CharField(
        'وضعیت',
        max_length=20,
        choices=PresenceStatus.choices,
        default=PresenceStatus.OFFLINE,
    )
    last_seen = models.DateTimeField('آخرین حضور', auto_now=True)
    custom_status = models.CharField('وضعیت سفارشی', max_length=200, blank=True, default='')

    class Meta:
        db_table = 'chat_user_presence'
        verbose_name = 'حضور کاربر'
        verbose_name_plural = 'حضور کاربران'

    def __str__(self):
        return f"{self.user}: {self.status}"
