<?php

namespace Kylin\WordFilter\Models;

use Kylin\Core\Models\BaseModel;

/**
 * 词库版本模型
 *
 * 管理词库版本记录，用于增量同步和版本回滚。
 *
 * @property int    $id
 * @property string $version        版本号
 * @property int    $total_words    总词数
 * @property array  $category_stats 分类统计
 * @property string $checksum       校验和
 * @property string $change_summary 变更摘要
 * @property string $published_at   发布时间
 */
class WordFilterVersion extends BaseModel
{
    protected $table = 'kylin_word_filter_versions';

    protected $fillable = [
        'version',
        'total_words',
        'category_stats',
        'checksum',
        'change_summary',
        'published_at',
    ];

    protected $casts = [
        'total_words' => 'integer',
        'category_stats' => 'array',
        'published_at' => 'datetime',
    ];

    /**
     * 是否已发布
     */
    public function isPublished(): bool
    {
        return $this->published_at !== null;
    }

    /**
     * 获取最新已发布版本
     */
    public static function latestPublished(): ?self
    {
        return static::whereNotNull('published_at')
            ->orderByDesc('version')
            ->first();
    }

    /**
     * 根据版本号查找
     */
    public static function findByVersion(string $version): ?self
    {
        return static::where('version', $version)->first();
    }

    /**
     * 获取指定版本之后的增量变更
     *
     * @return array{added: int, removed: int, changed_categories: array}
     */
    public function diffFrom(self $olderVersion): array
    {
        $olderStats = $olderVersion->category_stats ?? [];
        $currentStats = $this->category_stats ?? [];

        $added = 0;
        $removed = 0;
        $changedCategories = [];

        foreach ($currentStats as $code => $count) {
            $oldCount = $olderStats[$code] ?? 0;
            if ($count > $oldCount) {
                $added += $count - $oldCount;
                $changedCategories[$code] = ['added' => $count - $oldCount];
            } elseif ($count < $oldCount) {
                $removed += $oldCount - $count;
                $changedCategories[$code] = ['removed' => $oldCount - $count];
            }
        }

        // 检查在旧版本中存在但新版本中已移除的分类
        foreach ($olderStats as $code => $count) {
            if (! isset($currentStats[$code])) {
                $removed += $count;
                $changedCategories[$code] = ['removed' => $count];
            }
        }

        return [
            'added' => $added,
            'removed' => $removed,
            'changed_categories' => $changedCategories,
        ];
    }
}
