# models.py
from apps.core.models.base import SEOMixin
from apps.core.models.url_style import UrlStyle
from apps.core.utils.hash import hash_id
from django.contrib.auth import get_user_model
from django.db import models
from django.utils.translation import gettext_lazy as _

from .common import CreateCommon


class PlatformDownload(models.Model):
    """平台下载渠道配置"""
    download = models.ForeignKey(
        'Download',  # 确保与Download模型的正确关联
        on_delete=models.CASCADE,
        verbose_name=_('关联下载'),
        related_name='platform_downloads'  # 避免related_name冲突
    )
    config = models.JSONField(verbose_name='渠道配置',
                              help_text='''支持格式示例：
<div class="collapse">
<details  style="margin-top:10px">
<summary>AWS S3云存储</summary>
<pre>{
    "channel_type": "aws_s3",
    "bucket": "your-downloads-bucket",
    "region": "us-west-2",
    "access_key": "${ENV_AWS_ACCESS_KEY}",  // 建议通过环境变量注入‌
    "secret_key": "${ENV_AWS_SECRET_KEY}",
    "prefix": "v2.0/releases/"  // 可选路径前缀
}</pre>
</details>
<details  style="margin-top:10px">
<summary>阿里云OSS</summary>
<pre>{
    "channel_type": "aliyun_oss",
    "bucket": "app-download-center",
    "endpoint": "oss-cn-hangzhou.aliyuncs.com",
    "access_key_id": "${ENV_ALIYUN_KEY}",
    "access_key_secret": "${ENV_ALIYUN_SECRET}",
    "security_token": ""  // 临时访问凭证时使用
}
</pre>
</details>
<details  style="margin-top:10px">
<summary>FTP服务器</summary>
<pre>{
    "channel_type": "ftp",
    "host": "download.yourcompany.com",
    "port": 2121,  // 非默认端口需显式声明
    "path": "/public/releases/",
    "username": "${ENV_FTP_USER}",
    "password": "${ENV_FTP_PWD}",
    "passive_mode": true  // 被动传输模式
}
</pre>
</details>
<details  style="margin-top:10px">
<summary>华为云OBS</summary>
<pre>{
    "channel_type": "huawei_obs",
    "bucket": "mobile-app",
    "endpoint": "obs.cn-east-3.myhuaweicloud.com",
    "access_key": "${ENV_HW_ACCESS_KEY}",
    "secret_key": "${ENV_HW_SECRET_KEY}",
    "expires": 3600  // 签名有效期（秒）
}
</pre>
</details>
</div>''')

    @property
    def channel_type(self):
        return self.config.get("channel_type", "unknown")  # 动态解析字段

    class Meta:
        verbose_name = _('平台下载配置')
        verbose_name_plural = verbose_name

    def clean(self):
        """模型级参数验证"""

        super().clean()

    def __str__(self):
        return f"{self.channel_type} 配置"

    class Meta:
        verbose_name = _('平台下载配置')
        verbose_name_plural = verbose_name

    def clean(self):
        """模型级参数验证"""
        super().clean()

    def __str__(self):
        return f"{self.channel_type} 配置"


class Download(CreateCommon, SEOMixin):
    """下载资源模型"""
    # 核心文件字段
    file = models.FileField(_('本地文件'),
                            blank=True,
                            upload_to='downloads/files/%Y/%m/%d/',
                            help_text=_('支持格式：ZIP/RAR/PDF/DOC'))
    file_size = models.PositiveIntegerField(_('文件大小'),
                                            default=0,
                                            editable=False,
                                            help_text=_('单位：字节'))
    file_type = models.CharField(_('文件类型'),
                                 max_length=50,
                                 editable=False,
                                 blank=True)

    # 软件属性
    software_language = models.CharField(_('软件语言'),
                                         max_length=50,
                                         default='简体中文',
                                         choices=[('简体中文', '简体中文'),
                                                  ('English', '英文'),
                                                  ('多语言', '多语言版')])
    version = models.CharField(_('版本号'), max_length=20, default='1.0.0')
    license_type = models.CharField(_('授权类型'),
                                    max_length=50,
                                    choices=[('免费', '免费版'), ('试用', '试用版'),
                                             ('商业', '商业授权')],
                                    default='免费')

    # 平台支持
    support_platforms = models.CharField(
        _('支持平台'),
        max_length=200,
        help_text='支持多选，用逗号分隔（例：windows,android）',
        blank=True)
    windows_version = models.CharField(_('Windows版本要求'),
                                       max_length=100,
                                       blank=True)
    macos_version = models.CharField(_('macOS版本要求'),
                                     max_length=100,
                                     blank=True)
    android_version = models.CharField(_('Android最低版本'),
                                       max_length=50,
                                       blank=True)

    # 下载信息
    official_website = models.URLField(_('官方网站'), blank=True)
    mirror_download = models.URLField(_('镜像下载'), blank=True)
    cloud_download = models.URLField(_('网盘下载'),
                                     blank=True,
                                     help_text='百度网盘/阿里云盘等链接')

    # 时间版本
    release_date = models.DateField(_('发布时间'), null=True, blank=True)
    update_log = models.TextField(_('更新日志'), blank=True)

    # 安全验证
    md5_hash = models.CharField(_('MD5校验码'), max_length=32, blank=True)
    sha256_hash = models.CharField(_('SHA256校验码'), max_length=64, blank=True)

    # 关联系统
    category = models.ForeignKey(
        'content.Category',
        on_delete=models.CASCADE,
        verbose_name=_('所属分类'),
        limit_choices_to={'content_type__model': 'download'},
    )
    related_tags = models.ManyToManyField('content.Tag',
                                          blank=True,
                                          verbose_name=_('关联标签'),
                                          related_name='downloads')
    filtered_tags = models.ManyToManyField("content.Tag",
                                           blank=True,
                                           related_name="filtered_downloads",
                                           verbose_name="动态匹配标签",
                                           help_text="通过标签标题模糊匹配关联的标签")

    # 统计字段
    download_count = models.PositiveIntegerField(_('下载次数'), default=0)

    editor = models.ForeignKey(  # 修复拼写错误
        get_user_model(),
        on_delete=models.SET_NULL,
        null=True,
        verbose_name="内容编辑",
        related_name="edited_download")

    class Meta:
        verbose_name = _('下载资源')
        verbose_name_plural = _('下载列表')
        ordering = ['-is_top', '-create_time']
        indexes = [
            # 复合索引（时间字段统一降序）
            models.Index(fields=['category', 'status', '-update_time'],
                         name='dl_cate_status_utime_desc'),
            models.Index(fields=['category', 'status', '-create_time'],
                         name='dl_cate_status_ctime_desc'),

            # 状态+降序时间组合
            models.Index(fields=['status', '-update_time'],
                         name='dl_status_utime_desc'),
            models.Index(fields=['status', '-create_time'],
                         name='dl_status_ctime_desc'),

            # 独立时间索引（显式降序）
            models.Index(fields=['-create_time'], name='dl_ctime_desc'),
            models.Index(fields=['-update_time'], name='dl_utime_desc'),

            # 业务索引（修正字段分隔符）
            models.Index(fields=['hits', 'status'], name='dl_hits_status'),
            models.Index(fields=['category', 'hits', 'status'],
                         name='dl_cate_hits_status'),
            models.Index(fields=['title'], name='dl_title'),
            models.Index(fields=['category', '-update_time', '-id'],
                         name='dl_cate_utime_id_desc'),
            models.Index(fields=['-update_time', '-id'],
                         name='dl_utime_id_desc'),
            models.Index(fields=['category'], name='dl_category_idx'),
        ]

    def save(self, *args, **kwargs):
        """自动计算文件属性"""
        if self.file:
            self.file_size = self.file.size
            self.file_type = self.file.name.split('.')[-1].upper()
        super().save(*args, **kwargs)

    def get_platform_list(self):
        """解析支持平台列表"""
        return [
            p.strip() for p in self.support_platforms.split(',') if p.strip()
        ]

    def __str__(self):
        return f"{self.title} v{self.version}"

    def get_absolute_url(self):
        '''
        变量为objects
        url_front=[('model', '模型路径（/model/123.html）'),
        ('slug', '单级Slug（/news/123.html）'),
        ('moreslug', '多级Slug（/news/sports/123.html）'),
        ('random', '随机字符（/jklfdsa/1.html）'),
        ('custom', '自定义路径（/mycategory/myarticle/1.shtml）')]
        '''
        #无论前端怎么变量都为tag
        urlconfig = UrlStyle.get_solo()
        prefix = 'download'
        if urlconfig.url_mid == 'hash':
            url_mid = hash_id(self.id)
        else:
            url_mid = self.id
        return f'/download/{url_mid}{urlconfig.url_suffix}'
