<?php

namespace XZD\AI\V5\Tools;

use XZD\AI\V5\Core\Logger;

class KnowledgeManager
{
    /** 搜索知识库 */
    public static function search(array $params, int $userId): ToolResult
    {
        global $wpdb;
        $table = $wpdb->prefix . 'xzd_ai_knowledge';
        $faqTable = $wpdb->prefix . 'xzd_ai_faq';
        $keyword = $params['keyword'] ?? '';
        $limit = min((int) ($params['limit'] ?? 10), 50);

        $knowledgeResults = [];
        $faqResults = [];

        if (empty($keyword)) {
            $knowledgeResults = $wpdb->get_results(
                "SELECT id, title, LEFT(content, 800) AS content, source_type, access_level, created_at FROM {$table} WHERE status = 'active' ORDER BY created_at DESC LIMIT {$limit}",
                ARRAY_A
            );
        } else {
            // 中文分词以提高搜索精度
            $tokenizer = new ChineseTokenizer();
            $tokens = $tokenizer->segment($keyword);
            $searchTokens = !empty($tokens) ? $tokens : [$keyword];

            // 多关键词 OR 查询知识库
            $conditions = [];
            $queryParams = [];
            foreach ($searchTokens as $token) {
                $like = '%' . $wpdb->esc_like($token) . '%';
                $conditions[] = '(title LIKE %s OR content LIKE %s)';
                $queryParams[] = $like;
                $queryParams[] = $like;
            }

            $where = implode(' OR ', $conditions);
            $queryParams[] = $limit;
            $sql = $wpdb->prepare(
                "SELECT id, title, LEFT(content, 800) AS content, source_type, access_level, created_at FROM {$table} WHERE status = 'active' AND ({$where}) LIMIT %d",
                ...$queryParams
            );
            $knowledgeResults = $wpdb->get_results($sql, ARRAY_A);

            // 分词后无结果，回退到原始关键词模糊搜索
            if (empty($knowledgeResults) && count($searchTokens) > 1) {
                $like = '%' . $wpdb->esc_like($keyword) . '%';
                $knowledgeResults = $wpdb->get_results($wpdb->prepare(
                    "SELECT id, title, LEFT(content, 800) AS content, source_type, access_level, created_at FROM {$table} WHERE status = 'active' AND (title LIKE %s OR content LIKE %s) LIMIT %d",
                    $like, $like, $limit
                ), ARRAY_A);
            }

            // 同时搜索FAQ表
            $faqConditions = [];
            $faqParams = [];
            foreach ($searchTokens as $token) {
                $like = '%' . $wpdb->esc_like($token) . '%';
                $faqConditions[] = '(question LIKE %s OR answer LIKE %s)';
                $faqParams[] = $like;
                $faqParams[] = $like;
            }
            $faqWhere = implode(' OR ', $faqConditions);
            $faqParams[] = $limit;
            $faqSql = $wpdb->prepare(
                "SELECT id, question AS title, answer AS content, 'faq' AS source_type, created_at FROM {$faqTable} WHERE status = 'active' AND ({$faqWhere}) LIMIT %d",
                ...$faqParams
            );
            $faqResults = $wpdb->get_results($faqSql, ARRAY_A);

            // FAQ也做回退搜索
            if (empty($faqResults) && count($searchTokens) > 1) {
                $like = '%' . $wpdb->esc_like($keyword) . '%';
                $faqResults = $wpdb->get_results($wpdb->prepare(
                    "SELECT id, question AS title, answer AS content, 'faq' AS source_type, created_at FROM {$faqTable} WHERE status = 'active' AND (question LIKE %s OR answer LIKE %s) LIMIT %d",
                    $like, $like, $limit
                ), ARRAY_A);
            }
        }

        // 权限过滤：根据用户角色过滤知识库结果
        $userRole = \XZD\AI\V5\Core\UserHelper::getRole($userId);
        $filteredKnowledge = [];
        foreach ($knowledgeResults ?: [] as &$item) {
            $level = $item['access_level'] ?? 'public';
            if ($level === 'public' || $userRole === 'admin') {
                $filteredKnowledge[] = $item;
                continue;
            }
            if ($level === 'logged_in' && $userRole === 'guest') {
                $item['content'] = '[此内容需要登录后查看]';
                $item['restricted'] = true;
                $filteredKnowledge[] = $item;
            } elseif ($level === 'vip' && !in_array($userRole, ['vip', 'admin'])) {
                $item['content'] = '[此内容为VIP专属，请升级后查看]';
                $item['restricted'] = true;
                $filteredKnowledge[] = $item;
            } elseif (str_starts_with($level, 'paid_')) {
                $postId = (int) substr($level, 5);
                $canAccess = false;
                if (function_exists('zibpay_is_paid')) {
                    try { $canAccess = zibpay_is_paid($postId, $userId); } catch (\Throwable $e) {}
                }
                if (!$canAccess && $userRole !== 'admin') {
                    $item['content'] = '[此内容需要付费购买后查看]';
                    $item['restricted'] = true;
                }
                $filteredKnowledge[] = $item;
            } else {
                $filteredKnowledge[] = $item;
            }
        }

        // 合并知识库结果和FAQ结果
        $allResults = array_merge($filteredKnowledge, $faqResults ?: []);

        return ToolResult::success(['results' => $allResults, 'count' => count($allResults),
            'knowledge_count' => count($filteredKnowledge),
            'faq_count' => count($faqResults ?: [])]);
    }

    /** 添加 FAQ */
    public static function addFaq(array $params, int $userId): ToolResult
    {
        global $wpdb;
        $table = $wpdb->prefix . 'xzd_ai_faq';
        $wpdb->insert($table, [
            'question'  => $params['question'] ?? '',
            'answer'    => $params['answer'] ?? '',
            'category'  => $params['category'] ?? '',
            'sort_order' => (int) ($params['sort_order'] ?? 0),
            'status'    => 'active',
            'created_at' => current_time('mysql'),
            'updated_at' => current_time('mysql'),
        ]);
        return ToolResult::success(['id' => $wpdb->insert_id], 'FAQ 已添加');
    }

    /** 删除 FAQ */
    public static function deleteFaq(array $params, int $userId): ToolResult
    {
        global $wpdb;
        $id = (int) ($params['faq_id'] ?? 0);
        $wpdb->delete($wpdb->prefix . 'xzd_ai_faq', ['id' => $id]);
        return ToolResult::success(null, 'FAQ 已删除');
    }

    /** 重建知识库索引 */
    public static function rebuildIndex(array $params, int $userId): ToolResult
    {
        global $wpdb;
        $table = $wpdb->prefix . 'xzd_ai_knowledge';
        $chunkTable = $wpdb->prefix . 'xzd_ai_knowledge_chunks';

        // 事务保护：重建失败则回滚
        $wpdb->query('START TRANSACTION');
        try {
            // 清空旧分块
            $wpdb->query("DELETE FROM {$chunkTable} WHERE 1=1");

            // 重新对每条知识库内容分块
            $rows = $wpdb->get_results("SELECT id, title, content FROM {$table} WHERE status = 'active'", ARRAY_A);
            $totalChunks = 0;

            foreach ($rows as $row) {
                $chunks = self::chunkContent($row['content'], 500);
                $i = 0;
                foreach ($chunks as $chunk) {
                    $wpdb->insert($chunkTable, [
                        'knowledge_id' => $row['id'],
                        'chunk_index'  => $i++,
                        'content'      => $chunk,
                        'created_at'   => current_time('mysql'),
                    ]);
                    $totalChunks++;
                }
                $wpdb->update($table, ['chunk_count' => $i, 'updated_at' => current_time('mysql')], ['id' => $row['id']]);
            }

            $wpdb->query('COMMIT');
        } catch (\Throwable $e) {
            $wpdb->query('ROLLBACK');
            Logger::error('knowledge_rebuild_index', '索引重建失败: ' . $e->getMessage());
            return ToolResult::error('索引重建失败，数据已回滚');
        }

        return ToolResult::success(['documents' => count($rows), 'chunks' => $totalChunks], '索引重建完成');
    }

    private static function chunkContent(string $text, int $maxLen): array
    {
        $chunks = [];
        $len = mb_strlen($text);
        for ($i = 0; $i < $len; $i += $maxLen) {
            $chunks[] = mb_substr($text, $i, $maxLen);
        }
        return $chunks;
    }
}
