Greasy Fork

Greasy Fork is available in English.

123网盘链接检测助手

极速多链接并发检测,智能状态持久化显示,自动提取码填充,实时回复检测,

// ==UserScript==
// @name         123网盘链接检测助手
// @namespace    https://pan1.me
// @version      1.1.0
// @description  极速多链接并发检测,智能状态持久化显示,自动提取码填充,实时回复检测,
// @author       绘梦
// @license      CC BY-NC-ND 4.0
// @icon         data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iNjQiIGhlaWdodD0iNjQiIHZpZXdCb3g9IjAgMCA2NCA2NCIgZmlsbD0ibm9uZSIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KPHJlY3Qgd2lkdGg9IjY0IiBoZWlnaHQ9IjY0IiByeD0iMTIiIGZpbGw9IiMxODc1ZmYiLz4KPHN2ZyB4PSIxMiIgeT0iMTIiIHdpZHRoPSI0MCIgaGVpZ2h0PSI0MCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIj4KPHBhdGggZD0iTTggNGg4YzEuMSAwIDIgLjkgMiAydjEyYzAgMS4xLS45IDItMiAySDhjLTEuMSAwLTItLjktMi0yVjZjMC0xLjEuOS0yIDItMnoiIGZpbGw9IndoaXRlIi8+CjxwYXRoIGQ9Ik0xMiA4djgiIHN0cm9rZT0iIzE4NzVmZiIgc3Ryb2tlLXdpZHRoPSIyIiBzdHJva2UtbGluZWNhcD0icm91bmQiLz4KPHN2ZyB4PSIxOCIgeT0iMTgiIHdpZHRoPSI4IiBoZWlnaHQ9IjgiIHZpZXdCb3g9IjAgMCA4IDgiPgo8Y2lyY2xlIGN4PSI0IiBjeT0iNCIgcj0iMyIgZmlsbD0iIzEwYjk4MSIvPgo8L3N2Zz4KPC9zdmc+Cjwvc3ZnPg==
// @match        *//*/*
// @match        https://pan1.me/*
// @match        https://*.123pan.com/*
// @match        https://*.123865.com/*
// @match        https://*.123684.com/*
// @match        https://*.123yunpan.com/*
// @grant        GM_xmlhttpRequest
// @grant        GM_setValue
// @grant        GM_getValue
// @grant        GM_registerMenuCommand
// @connect      123pan.com
// @connect      123865.com
// @connect      123684.com
// @connect      123yunpan.com
// @connect      *
// @require      https://code.jquery.com/jquery-3.6.0.min.js
// @run-at       document-end
// ==/UserScript==

/*
 * 123网盘链接检测助手 v4.0.0
 *
 * 版权所有 (c) 2024 Your Name
 *
 * 本作品采用知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议进行许可。
 * 要查看该许可协议,可访问 http://creativecommons.org/licenses/by-nc-nd/4.0/
 *
 * 许可协议要点:
 * ✅ 署名 - 您必须给出适当的署名
 * ❌ 非商业性使用 - 您不得将本作品用于商业目的
 * ❌ 禁止演绎 - 您不得修改、转换或以此为基础创作
 *
 * 警告:未经授权的修改、商业使用或再分发将构成侵权行为
 */

(function() {
    'use strict';

    // 配置参数 - 极速检测版
    const CONFIG = {
        // 高速链接检测模式
        linkPattern: /https?:\/\/(?:www\.)?[a-z0-9]*123[a-z0-9]*\.com\/s\/[A-Za-z0-9\-_]+/g,
        extractCodeRegex: /(?:提取码|密码|pwd)[::=\s]*([A-Za-z0-9]{4,8})/i,
        maxConcurrentChecks: Infinity, // 无限并发,极速处理所有链接
        requestTimeout: 500,    // 缩短超时时间
        retryAttempts: 0,        // 取消重试,直接失败
        // 缓存配置(24小时缓存)
        cacheExpireTime: 24 * 60 * 60 * 1000,
        // 同域检测配置
        sameDomainDetection: true,
        realtimeDetection: true,
        detectionInterval: 2000  // 减少实时检测频率,避免资源浪费
    };

    // 状态标记样式
    const STATUS_STYLES = {
        valid: 'color: #28a745; font-weight: bold; background: #d4edda; padding: 2px 6px; border-radius: 3px;',
        invalid: 'color: #dc3545; text-decoration: line-through; background: #f8d7da; padding: 2px 6px; border-radius: 3px;',
        processing: 'color: #fd7e14; background: #fff3cd; padding: 2px 6px; border-radius: 3px;',
        encrypted: 'color: #6f42c1; background: #e2e3f0; padding: 2px 6px; border-radius: 3px;',
        error: 'color: #868e96; background: #f8f9fa; padding: 2px 6px; border-radius: 3px;',
        unknown: 'color: #6c757d; background: #e9ecef; padding: 2px 6px; border-radius: 3px;'
    };

    // 用户代理列表(随机化)
    const USER_AGENTS = [
        'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
        'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36',
        'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
        'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:120.0) Gecko/20100101 Firefox/120.0'
    ];

    // 统一的全局状态管理(避免变量分散)
    const GlobalState = {
        // 链接检测状态
        checkedLinks: new Set(),
        linkStatusMap: new Map(),
        isScanning: false,
        activeRequests: 0,

        // 同域检测状态
        sameDomainDetector: null,
        detectionTimer: null,

        // 回复功能状态
        replyState: { tried: false, inProgress: false },
        autoReplyEnabled: GM_getValue('autoReplyEnabled', true), // 默认开启

        // 缓存状态
        pageContentCache: null,
        lastContentCheck: 0,

        // 智能缓存系统(24小时有效)
        linkCache: new Map(),

        // 反爬虫机制状态
        antiCrawler: {
            lastReplyTime: 0,
            replyCount: 0,
            sessionStartTime: Date.now()
        },

        // 防重复回复机制
        replyHistory: {
            usedTexts: new Set(),        // 已使用的回复文案
            pageUrls: new Set(),         // 已回复的页面URL
            maxHistorySize: 100          // 最大历史记录数量
        },

        // 调试模式
        debugMode: false,

        // 重置所有状态
        reset() {
            this.checkedLinks.clear();
            this.linkStatusMap.clear();
            this.linkCache.clear();
            this.isScanning = false;
            this.activeRequests = 0;
            this.replyState = { tried: false, inProgress: false };
            this.pageContentCache = null;
            this.lastContentCheck = 0;
        },

        // 缓存管理方法
        getCachedResult(url) {
            const cached = this.linkCache.get(url);
            if (cached && (Date.now() - cached.timestamp < CONFIG.cacheExpireTime)) {
                Log.debug('🎯 使用缓存结果:', url);
                return cached;
            }
            return null;
        },

        setCachedResult(url, status, method = 'unknown') {
            this.linkCache.set(url, {
                status: status,
                method: method,
                timestamp: Date.now()
            });

            // 限制缓存大小(最多100个)
            if (this.linkCache.size > 100) {
                const oldestKey = this.linkCache.keys().next().value;
                this.linkCache.delete(oldestKey);
            }
        }
    };


    // 初始化菜单
    function initMenu() {
        // 注册菜单项
        GM_registerMenuCommand(
            GlobalState.autoReplyEnabled ? '🔴 关闭自动回复' : '🟢 开启自动回复',
            toggleAutoReply,
            'a'
        );

        // 添加状态信息菜单
        GM_registerMenuCommand(
            '📊 查看回复统计',
            showReplyStats,
            's'
        );

        Log.info(`自动回复状态: ${GlobalState.autoReplyEnabled ? '已开启' : '已关闭'}`);
    }

    // 切换自动回复状态
    function toggleAutoReply() {
        GlobalState.autoReplyEnabled = !GlobalState.autoReplyEnabled;
        GM_setValue('autoReplyEnabled', GlobalState.autoReplyEnabled);

        // 重新注册菜单以更新显示
        location.reload(); // 简单的重新加载来更新菜单显示

        Log.info(`自动回复已${GlobalState.autoReplyEnabled ? '开启' : '关闭'}`);
    }

    // 显示回复统计
    function showReplyStats() {
        const stats = GlobalState.antiCrawler;
        const sessionTime = Math.floor((Date.now() - stats.sessionStartTime) / 1000 / 60); // 分钟

        const history = GlobalState.replyHistory;
        alert(`📊 回复统计信息:

🔄 自动回复状态: ${GlobalState.autoReplyEnabled ? '已开启' : '已关闭'}
📝 本次会话回复次数: ${stats.replyCount}
⏱️ 本次会话时长: ${sessionTime} 分钟
🕐 上次回复时间: ${stats.lastReplyTime ? new Date(stats.lastReplyTime).toLocaleTimeString() : '无'}
🔒 已使用文案数量: ${history.usedTexts.size}
📄 已回复页面数量: ${history.pageUrls.size}

💡 提示: 智能防重复机制,自定义+平台文案混合,0-2秒极速回复`);
    }

    // 核心功能立即启动(不依赖控制面板)
    function init() {
        // 初始化菜单
        initMenu();

        // 立即启动独立的实时回复检测(最高优先级)
        startRealtimeReplyDetection();

        // 启动定期清理机制(防内存泄漏)
        startPeriodicCleanup();

        // 立即启动核心检测功能 - 统一检测系统
        try {
            // 启动统一的实时检测系统(合并所有检测逻辑)
            startUnifiedDetection();

            // 立即扫描现有链接(仅执行一次)- 极速模式
            const existingLinks = findPanLinks();
            if (existingLinks.length > 0) {
                Log.info(`发现 ${existingLinks.length} 个链接,极速检测启动`);
                // 全部链接立即并发检测,无延迟
                existingLinks.forEach(checkLink);
            }

            if (isOn123PanSite()) {
                initAutoFillExtractCode();
                if (CONFIG.sameDomainDetection) {
                    initSameDomainDetection();
                }
            }

            console.log('✅ 核心检测功能已独立启动 - 无UI模式');
        } catch (error) {
            console.error('❌ 核心功能启动失败:', error);
        }

    }

    // 彻底修复的链接查找(防重复识别)
    function findPanLinks() {
        const links = [];
        const foundUrls = new Set(); // 严格去重

        // 1. 优先查找a标签链接
        const aLinks = document.querySelectorAll('a[href]');
        aLinks.forEach(link => {
            if (isPanLink(link.href)) {
                const normalizedUrl = normalizeUrl(link.href);
                if (!foundUrls.has(normalizedUrl)) {
                    foundUrls.add(normalizedUrl);

                    // 为现有a标签链接也自动附加提取码
                    enhanceExistingLink(link);

                    links.push(link);
                }
            }
        });

        // 2. 查找并转换纯文本链接为可点击链接
        const textNodes = getTextNodes(document.body);
        textNodes.forEach(node => {
            // 检查文本节点是否在a标签内
            if (node.parentElement && node.parentElement.closest('a[href]')) {
                return; // 跳过已在a标签中的文本
            }

            const matches = node.textContent.match(CONFIG.linkPattern);
            if (matches) {
                matches.forEach(url => {
                    const normalizedUrl = normalizeUrl(url);
                    if (!foundUrls.has(normalizedUrl)) {
                        foundUrls.add(normalizedUrl);

                        // 创建真实的可点击a标签
                        const clickableLink = createClickableLink(url, node);
                        if (clickableLink) {
                            links.push(clickableLink);
                        }
                    }
                });
            }
        });

        return links;
    }

    // URL标准化(去除参数差异)
    function normalizeUrl(url) {
        try {
            const urlObj = new URL(url);
            return `${urlObj.protocol}//${urlObj.host}${urlObj.pathname}`;
        } catch (e) {
            return url.split('?')[0]; // 简单去参数
        }
    }

    // 创建可点击的链接(替换纯文本,自动附加提取码)
    function createClickableLink(url, textNode) {
        try {
            const parent = textNode.parentElement;
            if (!parent) return null;

            // 查找周围的提取码
            const extractCode = findExtractCodeNearElement(textNode);

            // 如果找到提取码且URL中没有密码参数,则自动附加
            let finalUrl = url;
            if (extractCode && !url.includes('pwd=')) {
                const separator = url.includes('?') ? '&' : '?';
                finalUrl = `${url}${separator}pwd=${extractCode}`;
                console.log(`为链接自动附加提取码: ${finalUrl}`);
            }

            // 创建可点击的a标签
            const linkElement = document.createElement('a');
            linkElement.href = finalUrl;
            linkElement.textContent = url; // 显示原始URL,但实际跳转带提取码
            linkElement.target = '_blank'; // 新标签页打开
            linkElement.rel = 'noopener noreferrer'; // 安全性
            linkElement.style.cssText = `
                color: #007bff;
                text-decoration: underline;
                cursor: pointer;
                word-break: break-all;
                padding: 2px 4px;
                border-radius: 3px;
                background-color: rgba(0, 123, 255, 0.1);
                transition: background-color 0.2s ease;
            `;

            // 添加悬停效果
            linkElement.addEventListener('mouseenter', () => {
                linkElement.style.backgroundColor = 'rgba(0, 123, 255, 0.2)';
            });

            linkElement.addEventListener('mouseleave', () => {
                linkElement.style.backgroundColor = 'rgba(0, 123, 255, 0.1)';
            });

            // 替换文本节点中的URL为可点击链接
            const textContent = textNode.textContent;
            const urlIndex = textContent.indexOf(url);

            if (urlIndex !== -1) {
                // 分割文本:前部分 + 链接 + 后部分
                const beforeText = textContent.substring(0, urlIndex);
                const afterText = textContent.substring(urlIndex + url.length);

                // 创建文档片段
                const fragment = document.createDocumentFragment();

                // 添加前部分文本
                if (beforeText) {
                    fragment.appendChild(document.createTextNode(beforeText));
                }

                // 添加可点击链接
                fragment.appendChild(linkElement);

                // 添加后部分文本
                if (afterText) {
                    fragment.appendChild(document.createTextNode(afterText));
                }

                // 替换原文本节点
                parent.replaceChild(fragment, textNode);

                return linkElement;
            }

            return null;
        } catch (e) {
            console.warn('创建可点击链接失败:', e);
            return null;
        }
    }

    // 获取所有文本节点
    function getTextNodes(element) {
        const textNodes = [];
        const walker = document.createTreeWalker(
            element,
            NodeFilter.SHOW_TEXT,
            {
                acceptNode: function(node) {
                    // 跳过script、style等标签
                    const parent = node.parentElement;
                    if (parent && ['SCRIPT', 'STYLE', 'NOSCRIPT'].includes(parent.tagName)) {
                        return NodeFilter.FILTER_REJECT;
                    }
                    // 只处理包含123链接的文本节点
                    if (CONFIG.linkPattern.test(node.textContent)) {
                        return NodeFilter.FILTER_ACCEPT;
                    }
                    return NodeFilter.FILTER_REJECT;
                }
            }
        );

        let node;
        while (node = walker.nextNode()) {
            textNodes.push(node);
        }
        return textNodes;
    }

    // 精简的链接验证
    function isPanLink(url) {
        return CONFIG.linkPattern.test(url);
    }

    // 检测是否在123网盘站点
    function isOn123PanSite() {
        const hostname = window.location.hostname.toLowerCase();
        return /123[a-z0-9]*\.com$/.test(hostname);
    }

    // ==================== 一比一复刻的专业检测系统 ====================

    // 同域检测配置(完全复刻参考脚本)
    const SAME_ORIGIN_CONFIG = {
        // 123网盘相关域名(扩展支持更多子域名)
        domains: [
            '123pan.com',      // 官方主域名
            '123865.com',      // 常见子域名
            '123684.com',      // 常见子域名
            '123912.com',      // 新发现的子域名
            '123yunpan.com',   // 云盘子域名
            '123netdisk.com',  // 网盘子域名
            '123disk.com',     // 磁盘子域名
            '123file.com',     // 文件子域名
            '123share.com'     // 分享子域名
        ],
        // 支持同域检测的页面路径
        supportedPaths: ['/s/', '/share/', '/home/share/']
    };

    // 精简日志管理器(防重复版)
    const Log = {
        _lastMessages: new Map(),
        _maxCacheSize: 50,

        // 智能防重复日志输出
        _logWithDedupe(level, icon, ...args) {
            const message = args.join(' ');
            const now = Date.now();

            // 对于包含数字的消息(如"发现 X 个链接"),使用特殊处理
            if (/发现\s+\d+\s+个/.test(message) || /检测完成/.test(message)) {
                // 多链接相关日志允许更频繁输出
                const key = `${level}:${message.replace(/\d+/g, 'N')}`;
                if (this._lastMessages.has(key)) {
                    const lastTime = this._lastMessages.get(key);
                    if (now - lastTime < 2000) return; // 2秒内不重复
                }
                this._lastMessages.set(key, now);
            } else {
                // 其他日志保持5秒去重
                const key = `${level}:${message}`;
                if (this._lastMessages.has(key)) {
                    const lastTime = this._lastMessages.get(key);
                    if (now - lastTime < 5000) return;
                }
                this._lastMessages.set(key, now);
            }

            // 限制缓存大小
            if (this._lastMessages.size > this._maxCacheSize) {
                const oldestKey = this._lastMessages.keys().next().value;
                this._lastMessages.delete(oldestKey);
            }

            console.log(icon, ...args);
        },

        info: (...args) => Log._logWithDedupe('info', 'ℹ️', ...args),
        success: (...args) => Log._logWithDedupe('success', '✅', ...args),
        warn: (...args) => Log._logWithDedupe('warn', '⚠️', ...args),
        error: (...args) => Log._logWithDedupe('error', '❌', ...args),
        debug: (...args) => GlobalState.debugMode && Log._logWithDedupe('debug', '🔍', ...args),

        // 分组日志(减少使用)
        group: (name, collapsed = true) => GlobalState.debugMode && console[collapsed ? 'groupCollapsed' : 'group'](`🔍 [${name}]`),
        groupEnd: () => GlobalState.debugMode && console.groupEnd()
    };

    // 专业的123网盘页面状态检测器(一比一复刻)
    function detectPanPageStatus(doc) {
        const body = doc.body;
        const text = body.textContent;
        const detectedElements = [];

        // 检测元素可见性
        function checkElementVisibility(element) {
            if (!element) return false;
            const style = doc.defaultView.getComputedStyle(element);
            if (style.display === 'none' || style.visibility === 'hidden' || style.opacity === '0') {
                return false;
            }
            return true;
        }

        // 1. 优先检测"提取文件"按钮(最可靠的有效页面标志)
        const buttons = body.querySelectorAll('button');
        for (const button of buttons) {
            const buttonText = button.textContent || '';
            if ((buttonText.includes('提取文件') || buttonText.includes('取文件') || buttonText.includes('extract')) && checkElementVisibility(button)) {
                detectedElements.push('提取文件按钮');
                return {
                    status: '有效页面(提取文件)',
                    isValid: true,
                    needsPassword: false,
                    confidence: 0.98,
                    detectedElements
                };
            }
        }

        // 1.5. 检测下载按钮和保存按钮(高置信度有效特征)
        for (const button of buttons) {
            const buttonText = button.textContent || '';
            if ((buttonText.includes('下载') || buttonText.includes('保存至云盘') || buttonText.includes('浏览器下载')) && checkElementVisibility(button)) {
                detectedElements.push('下载/保存按钮');
                return {
                    status: '有效页面(下载)',
                    isValid: true,
                    needsPassword: false,
                    confidence: 0.96,
                    detectedElements
                };
            }
        }

        // 2. 检测失效页面特征(增强版)
        const invalidTextPatterns = [
            '分享链接已失效', '分享链接不存在', '分享已过期', '链接已失效',
            '文件不存在', '文件已被删除', '分享不存在', '资源不存在',
            'share not found', 'file not found', 'link expired'
        ];

        for (const pattern of invalidTextPatterns) {
            if (text.includes(pattern)) {
                detectedElements.push(`失效文本: ${pattern}`);
                return {
                    status: '失效页面',
                    isValid: false,
                    needsPassword: false,
                    confidence: 0.95,
                    detectedElements
                };
            }
        }

        // 检测失效页面的CSS类名和元素
        const invalidSelectors = ['.shareWeb404', '.error-page', '.not-found', '.expired'];
        for (const selector of invalidSelectors) {
            const element = body.querySelector(selector);
            if (element && checkElementVisibility(element)) {
                detectedElements.push(`失效元素: ${selector}`);
                return {
                    status: '失效页面',
                    isValid: false,
                    needsPassword: false,
                    confidence: 0.95,
                    detectedElements
                };
            }
        }

        // 3. 检测提取码输入页面
        const passwordInput = body.querySelector('input[type="password"]');
        if (passwordInput && checkElementVisibility(passwordInput)) {
            detectedElements.push('密码输入框');
            return {
                status: '提取码输入页面',
                isValid: true,
                needsPassword: true,
                confidence: 0.92,
                detectedElements
            };
        }

        if (text.includes('请输入提取码')) {
            detectedElements.push('提取码提示文本');
            return {
                status: '提取码输入页面',
                isValid: true,
                needsPassword: true,
                confidence: 0.90,
                detectedElements
            };
        }

        // 4. 检测文件列表页面(多重特征评分)
        let fileListScore = 0;
        const fileListFeatures = [
            { selector: '.file-list', score: 0.4, name: 'file-list元素' },
            { selector: '.ant-table', score: 0.4, name: 'ant-table元素' },
            { selector: '.ant-table-wrapper', score: 0.4, name: 'ant-table-wrapper元素' },
            { selector: '.file-item', score: 0.3, name: 'file-item元素' },
            { text: '文件大小', score: 0.3, name: '文件大小文本' },
            { text: '修改时间', score: 0.3, name: '修改时间文本' },
            { text: '下载', score: 0.2, name: '下载文本' },
            { text: '预览', score: 0.2, name: '预览文本' },
            { text: '保存至云盘', score: 0.3, name: '保存至云盘文本' },
            { text: '浏览器下载', score: 0.3, name: '浏览器下载文本' },
            { text: '文件列表', score: 0.3, name: '文件列表文本' }
        ];

        for (const feature of fileListFeatures) {
            if (feature.selector) {
                const element = body.querySelector(feature.selector);
                if (element && checkElementVisibility(element)) {
                    fileListScore += feature.score;
                    detectedElements.push(feature.name);
                }
            } else if (feature.text && text.includes(feature.text)) {
                fileListScore += feature.score;
                detectedElements.push(feature.name);
            }
        }

        if (fileListScore >= 0.6) {
            return {
                status: '文件列表页面',
                isValid: true,
                needsPassword: false,
                confidence: Math.min(0.95, 0.7 + fileListScore * 0.2),
                detectedElements
            };
        }

        // 5. 检测其他有效页面特征
        const contentLayoutPage = body.querySelector('.content-layout-page');
        if (contentLayoutPage && checkElementVisibility(contentLayoutPage)) {
            detectedElements.push('content-layout-page元素');
            return {
                status: '有效页面(布局)',
                isValid: true,
                needsPassword: false,
                confidence: 0.85,
                detectedElements
            };
        }

        // 6. 默认状态
        return {
            status: '未知状态',
            isValid: false,
            needsPassword: false,
            confidence: 0.3,
            detectedElements: ['无关键元素']
        };
    }

    // 增强页面分析 - 高精度多层检测(优化版)
    function enhancedPageAnalysis(html, doc) {
        const htmlLower = html.toLowerCase();
        const textContent = doc.body ? doc.body.textContent : '';
        const detectedElements = [];

        Log.debug('增强分析开始,HTML长度:', html.length, '文本长度:', textContent.length);

        // 1. 优先检测最明确的有效页面特征(提升精度)

        // 检测"提取文件"按钮 - 最可靠的有效标志
        if (htmlLower.includes('提取文件') || htmlLower.includes('extract') || htmlLower.includes('取文件')) {
            detectedElements.push('提取文件按钮文本');
            return {
                status: '有效页面(提取文件)',
                isValid: true,
                needsPassword: false,
                confidence: 0.98,
                detectedElements
            };
        }

        // 2. 检测失效页面的明确特征(扩展模式)
        const invalidPatterns = [
            '分享链接已失效', '分享链接不存在', '链接已失效', '文件不存在',
            '分享已过期', 'share not found', 'file not found', '404'
        ];

        for (const pattern of invalidPatterns) {
            if (htmlLower.includes(pattern.toLowerCase())) {
                detectedElements.push(`失效特征: ${pattern}`);
                return {
                    status: '失效页面',
                    isValid: false,
                    needsPassword: false,
                    confidence: 0.95,
                    detectedElements
                };
            }
        }

        // 3. 检测密码输入页面(增强精度)
        const passwordPatterns = [
            '请输入提取码', '输入提取码', '提取码', 'access code', 'password'
        ];

        for (const pattern of passwordPatterns) {
            if (htmlLower.includes(pattern.toLowerCase())) {
                detectedElements.push(`密码特征: ${pattern}`);
                return {
                    status: '提取码输入页面',
                    isValid: true,
                    needsPassword: true,
                    confidence: 0.92,
                    detectedElements
                };
            }
        }

        // 4. 检测文件列表页面的多重特征(评分系统)
        let fileListScore = 0;
        const fileListPatterns = [
            { pattern: '文件大小', score: 0.3 },
            { pattern: '修改时间', score: 0.3 },
            { pattern: 'file-list', score: 0.4 },
            { pattern: 'ant-table', score: 0.3 },
            { pattern: '下载', score: 0.2 },
            { pattern: '预览', score: 0.2 },
            { pattern: '保存至云盘', score: 0.3 },
            { pattern: 'content-layout-page', score: 0.3 }
        ];

        for (const { pattern, score } of fileListPatterns) {
            if (htmlLower.includes(pattern.toLowerCase())) {
                fileListScore += score;
                detectedElements.push(`文件列表特征: ${pattern}`);
            }
        }

        if (fileListScore >= 0.6) {
            return {
                status: '文件列表页面',
                isValid: true,
                needsPassword: false,
                confidence: Math.min(0.95, 0.7 + fileListScore * 0.2),
                detectedElements
            };
        }

        // 5. 检测其他有效页面特征
        const validPatterns = [
            '分享文件', '共享文件', '文件分享', 'shared file', 'file share'
        ];

        for (const pattern of validPatterns) {
            if (htmlLower.includes(pattern.toLowerCase())) {
                detectedElements.push(`有效特征: ${pattern}`);
                return {
                    status: '有效页面(分享)',
                    isValid: true,
                    needsPassword: false,
                    confidence: 0.85,
                    detectedElements
                };
            }
        }

        // 6. 如果没有明确特征,返回null让专业检测器处理
        Log.debug('增强分析未找到明确特征,交由专业检测器处理');
        return null;
    }

    // 同域检测函数(一比一复刻)
    async function checkLinkBySameOrigin(shareUrl, extractCode = '') {
        return new Promise((resolve) => {
            let resolved = false;

            // 设置3秒超时(极速模式)
            const timeout = setTimeout(() => {
                if (!resolved) {
                    resolved = true;
                    Log.debug('同域检测超时');
                    resolve(null);
                }
            }, 3000);

            const targetUrl = extractCode ? `${shareUrl}?pwd=${extractCode}` : shareUrl;
            Log.debug('同域检测请求:', targetUrl);

            GM_xmlhttpRequest({
                method: 'GET',
                url: targetUrl,
                headers: {
                    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
                    'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
                    'Referer': 'https://www.123pan.com/'
                },
                timeout: 3000,
                onload: function(response) {
                    if (resolved) return;
                    clearTimeout(timeout);
                    resolved = true;

                    try {
                        Log.debug('GM_xmlhttpRequest加载完成,状态:', response.status);

                        if (response.status !== 200) {
                            Log.debug('HTTP状态错误:', response.status);
                            resolve(null);
                            return;
                        }

                        const html = response.responseText;
                        Log.debug('成功获取目标页面HTML,长度:', html.length);

                        // 检查HTML内容是否足够
                        if (html.length < 100) {
                            Log.warn('HTML内容过少,可能是重定向页面');
                            resolve(null);
                            return;
                        }

                        // 创建虚拟DOM进行分析
                        const parser = new DOMParser();
                        const doc = parser.parseFromString(html, 'text/html');

                        // 增强HTML分析 - 模拟实时检测器逻辑
                        const enhancedResult = enhancedPageAnalysis(html, doc);

                        // 如果增强分析有结果,使用增强结果;否则使用专业检测器
                        const detectionResult = enhancedResult || detectPanPageStatus(doc);

                        Log.debug('使用', enhancedResult ? '增强分析' : '专业检测器', '进行检测');

                        let isValid = detectionResult.isValid;
                        let needsPassword = detectionResult.needsPassword;
                        let confidence = detectionResult.confidence;

                        Log.debug('专业页面检测结果:', {
                            状态: detectionResult.status,
                            有效: isValid,
                            需要密码: needsPassword,
                            置信度: confidence,
                            检测到的元素: detectionResult.detectedElements
                        });

                        // 记录成功集成专业检测器的日志
                        Log.success('✅ 同域检测 + GM_xmlhttpRequest + 专业检测器工作正常!');

                        const result = {
                            isValid,
                            needsPassword,
                            confidence,
                            source: 'same_origin_xhr'
                        };

                        Log.debug(`同域检测完成: 有效=${isValid}, 需密码=${needsPassword}, 置信度=${confidence}`);

                        // 记录检测成功统计
                        const successLog = `📊 同域检测成功 | 状态: ${detectionResult.status} | 置信度: ${confidence} | 元素: ${detectionResult.detectedElements.join(',')}`;
                        Log.info(successLog);

                        resolve(result);

                    } catch (error) {
                        Log.debug('同域检测解析失败:', error.message);
                        resolve(null);
                    }
                },
                onerror: function(error) {
                    if (!resolved) {
                        clearTimeout(timeout);
                        resolved = true;
                        Log.debug('GM_xmlhttpRequest请求失败:', error);
                        Log.info('⚠️ 网络请求失败,同域检测不可用');
                        resolve(null);
                    }
                },
                ontimeout: function() {
                    if (!resolved) {
                        clearTimeout(timeout);
                        resolved = true;
                        Log.debug('GM_xmlhttpRequest请求超时');
                        resolve(null);
                    }
                }
            });
        });
    }

    // 判断是否为同域链接
    function isSameOriginLink(url) {
        try {
            const urlObj = new URL(url);
            const hostname = urlObj.hostname.toLowerCase();

            // 检查是否为123网盘域名
            return SAME_ORIGIN_CONFIG.domains.some(domain => hostname.includes(domain));
        } catch (e) {
            return false;
        }
    }

    // 智能检测策略:综合多种方案(一比一复刻核心逻辑)
    async function smartDetectLink(shareUrl, extractCode = '') {
        try {
            Log.group('智能检测');
            Log.info('开始检测:', shareUrl);

            // 精简检测策略,同域优先
            const strategies = [];

            // 优先级1: 同域检测(123网盘链接可尝试)
            Log.debug('检查是否可使用同域检测:', shareUrl);
            const canUseSameOrigin = isSameOriginLink(shareUrl);
            Log.info('同域检测可用:', canUseSameOrigin);

            if (canUseSameOrigin) {
                strategies.push({ name: 'same_origin', func: checkLinkBySameOrigin });
                Log.info('✅ 123网盘链接,使用GM_xmlhttpRequest进行同域检测');
            } else {
                Log.info('❌ 非123网盘链接,跳过同域检测');
            }

            // 优先级2: 传统页面检测作为兜底
            strategies.push({ name: 'traditional', func: checkLinkByTraditional });

            // 依次执行检测策略
            for (const strategy of strategies) {
                try {
                    Log.debug(`尝试检测策略: ${strategy.name}`);
                    const result = await strategy.func(shareUrl, extractCode);

                    if (result && result.confidence > 0.5) {
                        Log.success(`✅ ${strategy.name} 检测成功:`, result);
                        Log.groupEnd();
                        return result;
                    } else {
                        Log.debug(`⚠️ ${strategy.name} 检测失败或置信度过低`);
                    }
                } catch (error) {
                    Log.error(`❌ ${strategy.name} 检测出错:`, error.message);
                }
            }

            // 所有策略都失败
            Log.warn('⚠️ 所有检测策略都失败');
            Log.groupEnd();

            return {
                isValid: false,
                needsPassword: false,
                confidence: 0.1,
                source: 'fallback'
            };

        } catch (error) {
            Log.error('智能检测出错:', error);
            Log.groupEnd();
            return null;
        }
    }

    // 传统检测方法(增强准确性)
    async function checkLinkByTraditional(shareUrl, extractCode = '') {
        return new Promise((resolve) => {
            const fullUrl = extractCode ? `${shareUrl}?pwd=${extractCode}` : shareUrl;

            GM_xmlhttpRequest({
                method: 'GET',
                url: fullUrl,
                timeout: 3000, // 极速3秒超时
                headers: {
                    'User-Agent': USER_AGENTS[Math.floor(Math.random() * USER_AGENTS.length)],
                    'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
                    'Referer': 'https://www.123pan.com/'
                },
                onload: function(response) {
                    try {
                        Log.debug('传统检测响应状态:', response.status);

                        if (response.status !== 200) {
                            resolve({
                                isValid: false,
                                needsPassword: false,
                                confidence: 0.8,
                                source: 'traditional_xhr_error'
                            });
                            return;
                        }

                        const html = response.responseText;
                        Log.debug('传统检测HTML长度:', html.length);

                        // 使用增强页面分析
                        const parser = new DOMParser();
                        const doc = parser.parseFromString(html, 'text/html');
                        const enhancedResult = enhancedPageAnalysis(html, doc);

                        if (enhancedResult) {
                            Log.debug('传统检测使用增强分析结果');
                            resolve({
                                isValid: enhancedResult.isValid,
                                needsPassword: enhancedResult.needsPassword,
                                confidence: Math.max(0.6, enhancedResult.confidence - 0.1), // 略降置信度
                                source: 'traditional_enhanced'
                            });
                        } else {
                            // 回退到基础分析
                            const status = analyzePageStatus(html, response.status, true);
                            resolve({
                                isValid: status === 'valid',
                                needsPassword: status === 'encrypted',
                                confidence: status === 'valid' ? 0.7 : (status === 'invalid' ? 0.8 : 0.3),
                                source: 'traditional_basic'
                            });
                        }
                    } catch (error) {
                        Log.error('传统检测解析失败:', error);
                        resolve(null);
                    }
                },
                onerror: () => {
                    Log.debug('传统检测网络错误');
                    resolve(null);
                },
                ontimeout: () => {
                    Log.debug('传统检测超时');
                    resolve(null);
                }
            });
        });
    }

    // ==================== 同域检测功能模块 ====================

    // 初始化同域检测
    function initSameDomainDetection() {
        console.log('启动同域检测功能');

        // 创建同域检测器
        GlobalState.sameDomainDetector = new SameDomainDetector();

        // 实时检测已在startUnifiedDetection中启动,无需重复

    }

    // 同域检测器类
    class SameDomainDetector {
        constructor() {
            this.detectedLinks = new Map();
            this.isDetecting = false;
        }

        // 检测单个链接(供外部调用)
        async detectSingleLink(linkElement) {
            if (!linkElement) return;

            const linkInfo = {
                url: linkElement.href,
                element: linkElement,
                isCurrentPage: linkElement.href === window.location.href
            };

            console.log(`同域检测单个链接: ${linkInfo.url}`);
            await this.detectLink(linkInfo);
        }

        // 检测当前页面状态(实时页面元素检测)
        detectCurrentPageStatus() {
            console.log('实时页面元素检测');

            // 直接分析当前页面DOM元素
            const currentStatus = this.analyzeCurrentPage();
            console.log(`当前页面状态: ${currentStatus}`);

            // 更新当前页面状态显示
            this.updateCurrentPageStatus(currentStatus);

            return currentStatus;
        }

        // 更新当前页面状态显示
        updateCurrentPageStatus(status) {
            // 查找或创建页面状态指示器
            let indicator = document.querySelector('.current-page-status');
            if (!indicator) {
                indicator = document.createElement('div');
                indicator.className = 'current-page-status';
                indicator.style.cssText = `
                    position: fixed; top: 60px; right: 20px; z-index: 9998;
                    padding: 4px 8px; border-radius: 4px; font-size: 12px;
                    box-shadow: 0 2px 4px rgba(0,0,0,0.1);
                `;
                document.body.appendChild(indicator);
            }

            indicator.textContent = `页面状态: ${this.getStatusText(status)}`;
            indicator.style.cssText += this.getStatusStyle(status);
            indicator.title = `实时检测: ${this.getStatusTitle(status)}`;
        }

        // 检测链接是否需要同域处理
        shouldUseSameDomainDetection(url) {
            try {
                const urlObj = new URL(url);
                const currentHost = window.location.hostname.toLowerCase();
                const targetHost = urlObj.hostname.toLowerCase();

                // 同域且都是123网盘域名
                return currentHost === targetHost && /123[a-z0-9]*\.com$/.test(currentHost);
            } catch (e) {
                return false;
            }
        }

        // 检测单个链接(同域优化版)
        async detectLink(linkInfo) {
            const { url, element, isCurrentPage } = linkInfo;

            try {
                console.log(`同域检测链接: ${url}`);

                // 同域链接直接分析当前页面DOM
                if (this.shouldUseSameDomainDetection(url)) {
                    const status = this.analyzeCurrentPage();
                    this.updateLinkStatus(url, status, element);
                    console.log(`同域检测完成: ${url} -> ${status}`);
                    return;
                }

                // 非同域链接标记为需要跨域检测
                console.log(`非同域链接,需要跨域检测: ${url}`);
                this.updateLinkStatus(url, 'unknown', element);

            } catch (error) {
                console.error(`同域检测失败: ${url}`, error);
                this.updateLinkStatus(url, 'error', element);
            }
        }

        // 分析当前页面状态
        analyzeCurrentPage() {
            const bodyText = document.body.textContent;
            return analyzePageStatus(bodyText, 200, true);
        }


        // 更新链接状态
        updateLinkStatus(url, status, element) {
            this.detectedLinks.set(url, status);

            if (element) {
                // 为链接添加状态标记
                this.addStatusIndicator(element, status);
            }

            console.log(`链接状态更新: ${url} -> ${status}`);
        }

        // 添加状态指示器
        addStatusIndicator(element, status) {
            // 移除现有状态指示器
            const existing = element.parentNode.querySelector('.same-domain-status');
            if (existing) {
                existing.remove();
            }

            // 创建新的状态指示器
            const indicator = document.createElement('span');
            indicator.className = 'same-domain-status';
            indicator.textContent = this.getStatusText(status);
            indicator.style.cssText = `
                margin-left: 6px; font-size: 10px; padding: 1px 4px; border-radius: 2px;
                ${this.getStatusStyle(status)}
            `;
            indicator.title = `同域检测: ${this.getStatusTitle(status)}`;

            element.parentNode.insertBefore(indicator, element.nextSibling);
        }

        // 获取状态文本
        getStatusText(status) {
            const statusMap = {
                'valid': '✓同域有效',
                'invalid': '✗同域失效',
                'encrypted': '🔒同域加密',
                'error': '⚠同域错误',
                'timeout': '⏱同域超时',
                'unknown': '❓同域未知'
            };
            return statusMap[status] || '❓';
        }

        // 获取状态样式
        getStatusStyle(status) {
            const styleMap = {
                'valid': 'color: #28a745; background: #d4edda;',
                'invalid': 'color: #dc3545; background: #f8d7da;',
                'encrypted': 'color: #6f42c1; background: #e2e3f0;',
                'error': 'color: #868e96; background: #f8f9fa;',
                'timeout': 'color: #fd7e14; background: #fff3cd;',
                'unknown': 'color: #6c757d; background: #f8f9fa;'
            };
            return styleMap[status] || 'color: #6c757d; background: #f8f9fa;';
        }

        // 获取状态标题
        getStatusTitle(status) {
            const titleMap = {
                'valid': '同域检测有效',
                'invalid': '同域检测失效',
                'encrypted': '同域检测需要密码',
                'error': '同域检测错误',
                'timeout': '同域检测超时',
                'unknown': '同域检测未知状态'
            };
            return titleMap[status] || '未知状态';
        }


        // 延迟函数
        delay(ms) {
            return new Promise(resolve => setTimeout(resolve, ms));
        }
    }

    // 统一的检测系统(合并所有检测逻辑,避免重复)
    function startUnifiedDetection() {
        if (GlobalState.detectionTimer) {
            clearInterval(GlobalState.detectionTimer);
        }

        Log.info('启动统一检测系统');

        // 统一检测循环(合并实时检测、DOM监控、同域检测)
        GlobalState.detectionTimer = setInterval(() => {
            try {
                // 扫描新出现的链接(防重复)
                const currentLinks = findPanLinks();
                const newLinks = currentLinks.filter(link =>
                    !GlobalState.checkedLinks.has(normalizeUrl(link.href))
                );

                if (newLinks.length > 0) {
                    Log.info(`发现 ${newLinks.length} 个新链接`);
                    // 极速模式:立即并发检测所有新链接
                    newLinks.forEach(checkLink);
                }

                // 同域页面状态检测(仅在123网盘)
                if (GlobalState.sameDomainDetector && isOn123PanSite()) {
                    GlobalState.sameDomainDetector.detectCurrentPageStatus();
                }
            } catch (error) {
                Log.error('统一检测出错:', error);
            }
        }, CONFIG.detectionInterval);

        // 同时启动DOM变化监听(替代多个观察器)
        startDOMChangeObserver();

        Log.success('统一检测系统已启动');
    }

    // 统一的DOM变化观察器(替代多个分散的观察器)
    function startDOMChangeObserver() {
        let lastScanTime = 0;
        const SCAN_COOLDOWN = 1000; // 1秒冷却时间,适合多链接页面

        const unifiedObserver = new MutationObserver((mutations) => {
            // 检查变化是否由脚本自身引起 - 修复误判逻辑
            const isScriptChange = mutations.some(mutation => {
                return Array.from(mutation.addedNodes).some(node => {
                    return node.nodeType === 1 &&
                           (node.classList?.contains('link-status') ||
                            node.classList?.contains('same-domain-status') ||
                            node.classList?.contains('current-page-status'));
                });
            });

            // 检查链接删除,同步清理状态标记
            mutations.forEach(mutation => {
                Array.from(mutation.removedNodes).forEach(node => {
                    if (node.nodeType === 1) {
                        // 如果删除的是链接,清理对应状态标记
                        if (node.tagName === 'A' && isPanLink(node.href)) {
                            const normalizedUrl = normalizeUrl(node.href);
                            clearLinkStatus(normalizedUrl);
                            GlobalState.checkedLinks.delete(normalizedUrl);
                        }
                        // 检查删除节点的子链接
                        const innerLinks = node.querySelectorAll ? node.querySelectorAll('a[href]') : [];
                        innerLinks.forEach(link => {
                            if (isPanLink(link.href)) {
                                const normalizedUrl = normalizeUrl(link.href);
                                clearLinkStatus(normalizedUrl);
                                GlobalState.checkedLinks.delete(normalizedUrl);
                            }
                        });
                    }
                });
            });

            if (isScriptChange) return;

            // 冷却时间检查
            const now = Date.now();
            if (now - lastScanTime < SCAN_COOLDOWN) return;

            // 检查新增的链接
            const newLinks = [];
            mutations.forEach(mutation => {
                Array.from(mutation.addedNodes).forEach(node => {
                    if (node.nodeType === 1) {
                        // 检查节点本身是否是链接
                        if (node.tagName === 'A' && isPanLink(node.href)) {
                            const normalizedUrl = normalizeUrl(node.href);
                            if (!GlobalState.checkedLinks.has(normalizedUrl)) {
                                newLinks.push(node);
                            }
                        }
                        // 检查节点内部的链接
                        const innerLinks = node.querySelectorAll ? node.querySelectorAll('a[href]') : [];
                        innerLinks.forEach(link => {
                            if (isPanLink(link.href)) {
                                const normalizedUrl = normalizeUrl(link.href);
                                if (!GlobalState.checkedLinks.has(normalizedUrl)) {
                                    newLinks.push(link);
                                }
                            }
                        });
                        // 检查文本节点中的链接 - 极速处理
                        const text = node.textContent || '';
                        if (CONFIG.linkPattern.test(text)) {
                            // 立即处理,无延迟
                            const textNodes = getTextNodes(node);
                            textNodes.forEach(textNode => {
                                const matches = textNode.textContent.match(CONFIG.linkPattern);
                                if (matches) {
                                    matches.forEach(url => {
                                        const normalizedUrl = normalizeUrl(url);
                                        if (!GlobalState.checkedLinks.has(normalizedUrl)) {
                                            const clickableLink = createClickableLink(url, textNode);
                                            if (clickableLink) {
                                                newLinks.push(clickableLink);
                                            }
                                        }
                                    });
                                }
                            });
                        }
                    }
                });
            });

            // 批量检测新发现的链接
            if (newLinks.length > 0) {
                lastScanTime = now;
                Log.info(`DOM变化发现 ${newLinks.length} 个新链接`);
                // 极速模式:立即检测所有新链接,无延迟
                newLinks.forEach(checkLink);
            }
        });

        unifiedObserver.observe(document.body, {
            childList: true,
            subtree: true
        });

        Log.success('DOM变化观察器已启动');
    }

    // 定期清理机制(防内存泄漏)- 改为智能清理
    function startPeriodicCleanup() {
        setInterval(() => {
            try {
                // 清理过期的日志缓存
                if (Log._lastMessages && Log._lastMessages.size > 30) {
                    const now = Date.now();
                    for (const [key, timestamp] of Log._lastMessages.entries()) {
                        if (now - timestamp > 300000) { // 5分钟过期
                            Log._lastMessages.delete(key);
                        }
                    }
                }

                // 清理过期的链接缓存
                const now = Date.now();
                let cleanedCount = 0;
                for (const [url, cache] of GlobalState.linkCache.entries()) {
                    if (now - cache.timestamp > CONFIG.cacheExpireTime) {
                        GlobalState.linkCache.delete(url);
                        cleanedCount++;
                    }
                }

                // 智能清理孤立的状态标记(与链接生命周期同步)
                clearOrphanedStatus();

                if (cleanedCount > 0) {
                    Log.debug(`清理了 ${cleanedCount} 个过期缓存`);
                }
            } catch (error) {
                Log.error('定期清理出错:', error);
            }
        }, 60000); // 1分钟清理一次,频率提高以保持同步

        Log.debug('智能清理机制已启动');
    }

    // 停止实时检测(已集成到cleanup中,此函数保留备用)
    function stopRealtimeDetection() {
        if (GlobalState.detectionTimer) {
            clearInterval(GlobalState.detectionTimer);
            GlobalState.detectionTimer = null;
            Log.debug('停止实时检测');
        }
    }


    // 统一的提取码查找函数(消除重复逻辑)
    function findExtractCodeNearElement(element) {
        try {
            // 1. 从元素本身查找
            if (element.textContent) {
                const match = element.textContent.match(CONFIG.extractCodeRegex);
                if (match && match[1]) {
                    console.log(`从元素找到提取码: ${match[1]}`);
                    return match[1];
                }
            }

            // 2. 从父元素查找
            const parent = element.parentElement;
            if (parent) {
                const parentText = parent.textContent;
                const match = parentText.match(CONFIG.extractCodeRegex);
                    if (match && match[1]) {
                    console.log(`从父元素找到提取码: ${match[1]}`);
                        return match[1];
                    }
                }

            // 3. 从祖先元素查找
            let ancestor = parent;
            for (let i = 0; i < 3 && ancestor; i++) {
                ancestor = ancestor.parentElement;
                if (ancestor) {
                    const ancestorText = ancestor.textContent;
                    const match = ancestorText.match(CONFIG.extractCodeRegex);
                    if (match && match[1]) {
                        console.log(`从祖先元素找到提取码: ${match[1]}`);
                        return match[1];
                    }
                }
            }

            // 4. 查找相邻元素(仅对文本节点)
            if (element.nodeType === Node.TEXT_NODE && parent) {
                const siblings = Array.from(parent.childNodes || []);
                const nodeIndex = siblings.indexOf(element);

                for (let i = Math.max(0, nodeIndex - 2); i <= Math.min(siblings.length - 1, nodeIndex + 2); i++) {
                    const sibling = siblings[i];
                    if (sibling && sibling.nodeType === Node.TEXT_NODE && sibling !== element) {
                        const match = sibling.textContent.match(CONFIG.extractCodeRegex);
                        if (match && match[1]) {
                            console.log(`从相邻节点找到提取码: ${match[1]}`);
                            return match[1];
                        }
                    }
                }
            }

            return null;
        } catch (e) {
            console.warn('查找提取码时出错:', e);
            return null;
        }
    }

    // 增强现有的a标签链接,自动附加提取码
    function enhanceExistingLink(linkElement) {
        try {
            const originalUrl = linkElement.href;

            // 如果链接已经包含密码参数,跳过
            if (originalUrl.includes('pwd=')) {
                return;
            }

            // 查找周围的提取码
            const extractCode = findExtractCodeNearElement(linkElement);

            if (extractCode) {
                const separator = originalUrl.includes('?') ? '&' : '?';
                const enhancedUrl = `${originalUrl}${separator}pwd=${extractCode}`;

                // 更新链接href
                linkElement.href = enhancedUrl;
                console.log(`为现有链接附加提取码: ${enhancedUrl}`);

                // 添加视觉提示
                linkElement.title = `链接已自动附加提取码: ${extractCode}`;
                linkElement.style.borderBottom = '2px dotted #28a745';
            }
        } catch (e) {
            console.warn('增强链接时出错:', e);
        }
    }




    // 智能清理孤立状态标记(只清理没有对应链接的标记)
    function clearOrphanedStatus() {
        const existingLinks = new Set();
        // 收集所有存在的链接
        document.querySelectorAll('a[href]').forEach(link => {
            if (isPanLink(link.href)) {
                existingLinks.add(normalizeUrl(link.href));
            }
        });

        // 清理没有对应链接的状态标记
        let cleanedCount = 0;
        GlobalState.linkStatusMap.forEach((element, url) => {
            if (!existingLinks.has(url)) {
                if (element && element.parentNode) {
                    element.remove();
                }
                GlobalState.linkStatusMap.delete(url);
                GlobalState.checkedLinks.delete(url);
                cleanedCount++;
            }
        });

        if (cleanedCount > 0) {
            Log.debug(`清理了 ${cleanedCount} 个孤立状态标记`);
        }
    }

    // 精简的独立扫描函数(不依赖控制面板)
    function scanLinks() {
        if (GlobalState.isScanning) {
            console.log('扫描进行中,跳过');
            return;
        }

        GlobalState.isScanning = true;
        console.log('🔍 开始独立扫描');

        try {
            // 在123网盘站点优先使用同域检测
            if (isOn123PanSite() && GlobalState.sameDomainDetector) {
                console.log('使用同域页面检测');
                GlobalState.sameDomainDetector.detectCurrentPageStatus();
                GlobalState.isScanning = false;
                return;
            }

            // 查找所有链接
            const links = findPanLinks();
            const newLinks = links.filter(link => !GlobalState.checkedLinks.has(normalizeUrl(link.href)));

            if (newLinks.length === 0) {
                GlobalState.isScanning = false;
                console.log('没有发现新链接');
                return;
            }

            console.log(`发现 ${newLinks.length} 个新链接,极速并发检测`);

            // 极速模式:立即并发检测所有新链接
            newLinks.forEach(checkLink);

        } catch (error) {
            console.error('扫描链接时出错:', error);
            GlobalState.isScanning = false;
        }
    }

    // 极速检测函数 - 缓存优先 + 无限并发
    async function checkLink(linkElement) {
        // 无限并发模式:移除并发限制,所有链接立即处理

        const linkUrl = linkElement.href;
        const normalizedUrl = normalizeUrl(linkUrl);

        // 防重复检测
        if (GlobalState.checkedLinks.has(normalizedUrl)) {
            return;
        }

        // 🎯 优先检查缓存
        const cached = GlobalState.getCachedResult(normalizedUrl);
        if (cached) {
            updateLinkStatus(linkElement, cached.status);
            GlobalState.checkedLinks.add(normalizedUrl);
            Log.debug(`缓存命中: ${cached.status}`);
            return;
        }

        GlobalState.checkedLinks.add(normalizedUrl);
        updateLinkStatus(linkElement, 'processing');
        // 无限并发模式:不需要计数activeRequests

        try {
            // 获取提取码
            const extractCode = getExtractCode(linkElement);

            // 使用智能检测系统
            const result = await smartDetectLink(linkUrl, extractCode);

            if (result) {
                // 转换检测结果为状态
                let status;
                if (result.isValid) {
                    status = result.needsPassword ? 'encrypted' : 'valid';
                } else {
                    status = 'invalid';
                }

                // 💾 缓存高置信度结果
                if (result.confidence >= 0.7) {
                    GlobalState.setCachedResult(normalizedUrl, status, result.source || 'smart');
                }

                // 多链接场景显示进度
                const checkedCount = GlobalState.checkedLinks.size;
                Log.debug(`检测完成 (${checkedCount}): ${status} (${result.confidence})`);
                updateLinkStatus(linkElement, status);
            } else {
                Log.debug('检测失败');
                updateLinkStatus(linkElement, 'error');
            }
        } catch (error) {
            Log.error('检测出错:', error);
            updateLinkStatus(linkElement, 'error');
        }
        // 无限并发模式:不需要减少activeRequests计数

        // 检查扫描是否完成
        checkScanComplete();
    }


    // 检查扫描是否完成(无限并发版)
    function checkScanComplete() {
        // 无限并发模式:扫描完成由其他逻辑控制,这里只记录统计信息
        const totalChecked = GlobalState.checkedLinks.size;
        const cacheHits = GlobalState.linkCache.size;
        Log.debug(`当前进度 - 已检测: ${totalChecked} 个链接, 缓存: ${cacheHits} 个`);
    }

    // 统一的页面状态分析函数(消除重复逻辑)
    function analyzePageStatus(content, statusCode = 200, isTextContent = true) {
        const text = isTextContent ? content.toLowerCase() : content;

        // 检测有效标识
        if (text.includes('content-layout-page') ||
            text.includes('file-list-container') ||
            text.includes('ant-table-wrapper') ||
            text.includes('保存至云盘') ||
            text.includes('浏览器下载') ||
            text.includes('文件列表')) {
            console.log('检测到有效页面标识');
            return 'valid';
        }

        // 检测文件信息标识
        if ((text.includes('修改时间') && text.includes('大小')) ||
            (text.includes('共') && text.includes('项') && !text.includes('共0项'))) {
            console.log('检测到文件信息');
            return 'valid';
        }

        // 检测明确的失效标识
        if (text.includes('分享链接已失效') ||
            text.includes('分享页面不存在') ||
            text.includes('sharewebloading') ||
            text.includes('文件已被删除') ||
            text.includes('分享已过期') ||
            text.includes('链接失效') ||
            text.includes('链接已失效') ||
            text.includes('分享不存在') ||
            text.includes('资源不存在')) {
            console.log('检测到失效页面');
            return 'invalid';
        }

        // 检测加密状态
        if (text.includes('请输入提取码') ||
            text.includes('提取码错误') ||
            text.includes('密码错误')) {
            console.log('检测到加密页面');
            return 'encrypted';
        }

        // 基于内容长度和结构判断(仅对文本内容)
        if (isTextContent && statusCode === 200) {
            if (text.length > 15000 || text.includes('ant-table')) {
                console.log('基于内容判断为有效');
                return 'valid';
            }
            if (text.length < 3000) {
                console.log('内容过短,可能失效');
                return 'invalid';
            }
            // 中等长度内容,尝试更多特征检测
            if (text.includes('123pan') || text.includes('网盘') || text.includes('分享')) {
                console.log('基于关键词判断为有效');
                return 'valid';
            }
        }

        // HTTP错误状态
        if (statusCode >= 400) {
            console.log('HTTP错误状态,判断为失效');
            return 'invalid';
        }

        console.log('无法确定状态,默认为有效');
        return 'valid'; // 默认为有效,避免过多unknown状态
    }



    // 统一的状态显示(确保唯一标记)
    function updateLinkStatus(linkElement, status) {
        const normalizedUrl = normalizeUrl(linkElement.href);

        // 检查是否已有状态标记
        if (GlobalState.linkStatusMap.has(normalizedUrl)) {
            const existingElement = GlobalState.linkStatusMap.get(normalizedUrl);
            if (existingElement && existingElement.parentNode) {
                // 直接更新现有标记
                existingElement.textContent = getStatusText(status);
                existingElement.style.cssText = `margin-right: 6px; font-size: 11px; ${STATUS_STYLES[status]}`;
                existingElement.title = getStatusTitle(status);
                return;
            }
            // 清理无效引用
            GlobalState.linkStatusMap.delete(normalizedUrl);
        }

        // 彻底清除该URL的所有状态标记
        clearLinkStatus(normalizedUrl);

        // 创建新的状态标记
        const statusElement = document.createElement('span');
        statusElement.className = 'link-status';
        statusElement.style.cssText = `margin-right: 6px; font-size: 11px; ${STATUS_STYLES[status]}`;
        statusElement.textContent = getStatusText(status);
        statusElement.title = getStatusTitle(status);
        statusElement.dataset.normalizedUrl = normalizedUrl;

        // 统一插入位置:链接最前方(现在都是真实a标签)
        if (linkElement.parentNode) {
            linkElement.parentNode.insertBefore(statusElement, linkElement);
        }

        // 记录状态元素
        GlobalState.linkStatusMap.set(normalizedUrl, statusElement);
    }

    // 清除指定URL的所有状态标记(使用标准化URL)
    function clearLinkStatus(normalizedUrl) {
        // 清除记录中的状态
        if (GlobalState.linkStatusMap.has(normalizedUrl)) {
            const element = GlobalState.linkStatusMap.get(normalizedUrl);
            if (element && element.parentNode) {
                element.remove();
            }
            GlobalState.linkStatusMap.delete(normalizedUrl);
        }

        // 清除页面中所有相关状态标记
        document.querySelectorAll('.link-status').forEach(el => {
            if (el.dataset.normalizedUrl === normalizedUrl) {
                el.remove();
            }
        });
    }


    // 精简的状态文本
    function getStatusText(status) {
        const statusMap = {
            'valid': '✔ 有效',
            'invalid': '✖ 失效',
            'processing': '⏳ 检测中',
            'encrypted': '🔒 需密码',
            'error': '⚠ 错误',
            'unknown': '❓ 未知'
        };
        return statusMap[status] || '❓ 未知';
    }

    function getStatusTitle(status) {
        const titleMap = {
            'valid': '链接有效',
            'invalid': '链接失效',
            'processing': '检测中...',
            'encrypted': '需要提取码',
            'error': '检测错误',
            'unknown': '状态未知'
        };
        return titleMap[status] || '未知状态';
    }

    // 精简的提取码获取
    function getExtractCode(linkElement) {
        // 从URL参数获取
        try {
            const url = new URL(linkElement.href);
            if (url.searchParams.has('pwd')) {
                return url.searchParams.get('pwd');
            }
        } catch (e) {}

        // 从周围文本获取
        const parent = linkElement.closest('div') || linkElement.parentElement;
        if (parent) {
            const match = parent.textContent.match(CONFIG.extractCodeRegex);
            if (match && match[1]) {
                return match[1];
            }
        }

        return null;
    }

    // 自动填充提取码功能
    function initAutoFillExtractCode() {
        console.log('启动自动填充提取码功能');

        // 查找密码输入框
        const passwordInput = findPasswordInput();
        if (!passwordInput) {
            console.log('未找到密码输入框,5秒后重试');
            setTimeout(initAutoFillExtractCode, 5000);
            return;
        }

        // 查找提取码
        const extractCode = findExtractCodeFromPage();
        if (!extractCode) {
            console.log('未找到提取码');
            return;
        }

        // 自动填充
        autoFillPassword(passwordInput, extractCode);
    }

    // 查找密码输入框
    function findPasswordInput() {
        // 常见的密码输入框选择器
        const selectors = [
            'input[type="password"]',
            'input[placeholder*="密码"]',
            'input[placeholder*="提取码"]',
            'input[placeholder*="访问密码"]',
            '.ant-input[type="password"]',
            '.password-input',
            '#password',
            '.pwd-input'
        ];

        for (const selector of selectors) {
            const input = document.querySelector(selector);
            if (input && input.offsetParent !== null) { // 确保元素可见
                console.log(`找到密码输入框: ${selector}`);
                return input;
            }
        }

        return null;
    }

    // 从页面查找提取码
    function findExtractCodeFromPage() {
        // 从当前页面URL获取
        try {
            const urlParams = new URLSearchParams(window.location.search);
            if (urlParams.has('pwd')) {
                const code = urlParams.get('pwd');
                console.log(`从URL获取提取码: ${code}`);
                return code;
            }
        } catch (e) {}

        // 从页面文本中提取
        const pageText = document.body.textContent || '';
        const match = pageText.match(CONFIG.extractCodeRegex);
        if (match && match[1]) {
            console.log(`从页面文本获取提取码: ${match[1]}`);
            return match[1];
        }

        // 从来源页面获取(通过document.referrer)
        if (document.referrer) {
            try {
                const referrerUrl = new URL(document.referrer);
                if (referrerUrl.hostname.includes('pan1.me')) {
                    // 如果是从pan1.me跳转来的,尝试从referrer获取提取码
                    console.log('来源页面是pan1.me,尝试获取提取码');
                    return null; // 这里可以进一步扩展
                }
            } catch (e) {}
        }

        return null;
    }

    // 自动填充密码
    function autoFillPassword(input, password) {
        console.log(`准备填充提取码: ${password}`);

        try {
            // 聚焦输入框
            input.focus();

            // 清空现有内容
            input.value = '';

            // 填充密码
            input.value = password;

            // 触发输入事件(兼容React等框架)
            const events = ['input', 'change', 'keyup'];
            events.forEach(eventType => {
                const event = new Event(eventType, { bubbles: true });
                input.dispatchEvent(event);
            });

            console.log('提取码填充完成');

            // 查找并点击确认按钮
            setTimeout(() => {
                const submitButton = findSubmitButton();
                if (submitButton) {
                    console.log('找到确认按钮,准备自动提交');
                    submitButton.click();
                    console.log('已自动点击确认按钮');
                } else {
                    console.log('未找到确认按钮');
                }
            }, 500);

        } catch (error) {
            console.error('填充提取码时发生错误:', error);
        }
    }

    // 查找提交按钮
    function findSubmitButton() {
        const selectors = [
            'button[type="submit"]',
            'button:contains("确认")',
            'button:contains("提交")',
            'button:contains("访问")',
            '.ant-btn-primary',
            '.submit-btn',
            '.confirm-btn'
        ];

        for (const selector of selectors) {
            const button = document.querySelector(selector);
            if (button && button.offsetParent !== null) {
                return button;
            }
        }

        // 通过按钮文本查找
        const buttons = document.querySelectorAll('button');
        for (const button of buttons) {
            const text = button.textContent.trim();
            if (['确认', '提交', '访问', '确定', '进入'].includes(text)) {
                return button;
            }
        }

        return null;
    }


    // ==================== 自动回复功能模块 ====================

    // 智能回复文案库(自定义+平台文案混合)
    const REPLY_TEXTS = {
        // 自定义文案(原创内容)
        custom: [
            "好东西,先mark一下!",
            "这个必须收藏,感谢楼主!",
            "正好需要,楼主好人!",
            "资源不错,已下载,谢谢!",
            "找了很久,终于找到了!",
            "楼主威武,必须支持!",
            "这个太实用了,感谢分享!",
            "好资源,已保存,谢谢楼主!",
            "内容很棒,学习了!",
            "感谢楼主的无私分享!",
            "这个资源很给力,收藏!",
            "楼主辛苦了,内容很赞!",
            "正是我需要的,太感谢了!",
            "好东西要分享,支持楼主!",
            "资源质量很高,必须点赞!"
        ],
        // 平台常见文案(保留部分经典)
        platform: [
            "感谢楼主分享,内容很实用,收藏了~",
            "这个资源看起来很棒,谢谢分享!",
            "刚好需要这类内容,太及时了,感谢!",
            "之前一直在找类似的,谢谢分享👍",
            "内容不错,已保存,感谢整理~",
            "这个很有帮助,谢谢啦!",
            "支持一下,内容很精彩",
            "感谢分享,学到了不少",
            "收藏了,慢慢研究,谢谢~",
            "内容对我很有帮助,谢谢!"
        ],
        // 简短回复(混合风格)
        short: [
            "谢谢!",
            "收藏!",
            "赞!",
            "支持!",
            "好的!",
            "不错!",
            "感谢!",
            "给力!",
            "👍",
            "🔥"
        ],
        // 表情回复(增加趣味性)
        emoji: [
            "👍👍👍",
            "🔥🔥🔥",
            "💯💯💯",
            "❤️❤️❤️",
            "🎉🎉🎉",
            "✨✨✨",
            "👏👏👏",
            "🙏🙏🙏"
        ]
    };

    // 核心检测关键词(只保留最常用的)
    const REPLY_TRIGGER = '您好,本帖含有特定内容,请回复后再查看';

    // 反爬虫机制配置
    const ANTI_CRAWLER_CONFIG = {
        // 回复间隔控制(秒)
        minInterval: 0,      // 最小间隔0秒
        maxInterval: 5,      // 最大间隔5秒

        // 行为模拟延迟(毫秒)- 灵活模式
        readingTime: [100, 500],      // 模拟阅读时间 0.1-0.5秒
        typingTime: [50, 200],        // 模拟打字时间 0.05-0.2秒

        // 频率控制
        maxRepliesPerHour: 20,        // 每小时最多回复20次
        maxRepliesPerDay: 100,        // 每天最多回复100次

        // 随机行为
        skipProbability: 0.1,         // 10%概率跳过回复(模拟人类不总是回复)

        // 用户行为模拟
        enableMouseMove: true,        // 启用鼠标移动模拟
        enableScrolling: false,       // 禁用滚动模拟(不下拉页面)
        enableFocusBlur: true,        // 启用焦点切换模拟
        enableTypingSimulation: false // 禁用打字模拟(极速模式)
    };

    // 智能回复文案选择器(防重复+混合文案)
    function getRandomReplyText() {
        const weights = {
            'custom': 0.7,     // 70%概率选择自定义文案(优先使用)
            'platform': 0.15,  // 15%概率选择平台文案
            'short': 0.1,      // 10%概率选择简短回复
            'emoji': 0.05      // 5%概率选择表情回复
        };

        const history = GlobalState.replyHistory;
        let attempts = 0;
        let selectedText = '';

        // 最多尝试20次找到未使用的文案
        while (attempts < 20) {
            // 根据权重随机选择分类
            const random = Math.random();
            let accumulated = 0;
            let selectedCategory = 'custom';

            for (const [category, weight] of Object.entries(weights)) {
                accumulated += weight;
                if (random <= accumulated) {
                    selectedCategory = category;
                    break;
                }
            }

            // 从选中分类随机选择文案
            const texts = REPLY_TEXTS[selectedCategory];
            const randomIndex = Math.floor(Math.random() * texts.length);
            selectedText = texts[randomIndex];

            // 检查是否已使用过
            if (!history.usedTexts.has(selectedText)) {
                // 添加到已使用列表
                history.usedTexts.add(selectedText);

                // 限制历史记录大小
                if (history.usedTexts.size > history.maxHistorySize) {
                    const firstItem = history.usedTexts.values().next().value;
                    history.usedTexts.delete(firstItem);
                }

                Log.info(`✅ 选择回复分类: ${selectedCategory}, 文案: "${selectedText}"`);
                console.log(`🎯 文案选择详情: 类别=${selectedCategory}, 权重=${weights[selectedCategory]}, 文案="${selectedText}"`);
                return selectedText;
            }

            attempts++;
        }

        // 如果20次都找不到未使用的文案,清空历史记录重新开始
        if (attempts >= 20) {
            Log.info('回复文案历史记录已满,清空重新开始');
            history.usedTexts.clear();

            // 重新选择
            const categories = Object.keys(REPLY_TEXTS);
            const randomCategory = categories[Math.floor(Math.random() * categories.length)];
            const texts = REPLY_TEXTS[randomCategory];
            selectedText = texts[Math.floor(Math.random() * texts.length)];
            history.usedTexts.add(selectedText);
        }

        Log.debug(`最终选择文案: ${selectedText}`);
        return selectedText;
    }

    // 反爬虫检查(增加防重复机制)
    function shouldSkipReply() {
        const now = Date.now();
        const stats = GlobalState.antiCrawler;
        const history = GlobalState.replyHistory;
        const currentUrl = window.location.href;

        // 检查是否禁用自动回复
        if (!GlobalState.autoReplyEnabled) {
            Log.info('自动回复已禁用,跳过回复');
            return true;
        }

        // 检查当前页面是否已经回复过
        if (history.pageUrls.has(currentUrl)) {
            Log.info('当前页面已回复过,跳过重复回复');
            return true;
        }

        // 随机跳过(模拟人类行为)
        if (Math.random() < ANTI_CRAWLER_CONFIG.skipProbability) {
            Log.info('随机跳过回复(模拟人类行为)');
            return true;
        }

        // 检查回复间隔(0秒间隔时跳过检查)
        if (stats.lastReplyTime > 0 && ANTI_CRAWLER_CONFIG.minInterval > 0) {
            const timeSinceLastReply = now - stats.lastReplyTime;
            const minInterval = ANTI_CRAWLER_CONFIG.minInterval * 1000;

            if (timeSinceLastReply < minInterval) {
                Log.info(`回复间隔过短,需等待 ${Math.ceil((minInterval - timeSinceLastReply) / 1000)} 秒`);
                return true;
            }
        }

        // 检查每小时频率限制
        const oneHourAgo = now - 60 * 60 * 1000;
        if (stats.lastReplyTime > oneHourAgo && stats.replyCount >= ANTI_CRAWLER_CONFIG.maxRepliesPerHour) {
            Log.info('已达到每小时回复限制');
            return true;
        }

        return false;
    }

    // 用户行为模拟(无滚动版)
    async function simulateUserBehavior() {
        Log.debug('开始用户行为模拟(无滚动)');

        // 简化的鼠标移动(不等待)
        if (ANTI_CRAWLER_CONFIG.enableMouseMove) {
            simulateMouseMovement();
        }

        // 极简的阅读时间
        const readingTime = randomBetween(ANTI_CRAWLER_CONFIG.readingTime[0], ANTI_CRAWLER_CONFIG.readingTime[1]);
        Log.debug(`阅读时间: ${readingTime}ms`);
        await delay(readingTime);

        // 焦点切换(如果启用)
        if (ANTI_CRAWLER_CONFIG.enableFocusBlur) {
            simulateFocusBlur();
        }

        // 明确跳过页面滚动
        Log.debug('用户行为模拟完成(已跳过页面滚动)');
    }

    // 模拟鼠标移动
    function simulateMouseMovement() {
        const moveCount = randomBetween(2, 5);
        for (let i = 0; i < moveCount; i++) {
            setTimeout(() => {
                const x = randomBetween(100, window.innerWidth - 100);
                const y = randomBetween(100, window.innerHeight - 100);

                const event = new MouseEvent('mousemove', {
                    clientX: x,
                    clientY: y,
                    bubbles: true
                });
                document.dispatchEvent(event);
            }, i * randomBetween(200, 800));
        }
        Log.debug('模拟鼠标移动完成');
    }

    // 模拟页面滚动(已禁用)
    async function simulateScrolling() {
        // 滚动功能已禁用,不执行任何滚动操作
        Log.debug('页面滚动已禁用,跳过滚动模拟');
        return;
    }

    // 模拟焦点切换
    function simulateFocusBlur() {
        // 模拟窗口失焦和重新获得焦点
        window.dispatchEvent(new Event('blur'));
        setTimeout(() => {
            window.dispatchEvent(new Event('focus'));
        }, randomBetween(100, 500));
        Log.debug('模拟焦点切换完成');
    }

    // 生成随机数
    function randomBetween(min, max) {
        return Math.floor(Math.random() * (max - min + 1)) + min;
    }

    // 延迟函数
    function delay(ms) {
        return new Promise(resolve => setTimeout(resolve, ms));
    }

    // 极速内容检测(最优化)
    function needsReply() {
        // 使用innerHTML是最快的文本搜索方式
        return document.body.innerHTML.includes('本帖含有特定内容,请回复后再查看');
    }

    // 独立的实时回复检测系统(不依赖控制面板)
    function startRealtimeReplyDetection() {
        console.log('🚀 启动独立实时回复检测系统');

        // 立即检测一次
        if (needsReply() && !GlobalState.replyState.tried) {
            console.log('🔍 立即发现回复触发条件');
            initAutoReply();
        }

        // 创建实时监控定时器
        const replyDetectionTimer = setInterval(() => {
            try {
                // 如果已经尝试过回复,停止检测
                if (GlobalState.replyState.tried) {
                    clearInterval(replyDetectionTimer);
                    console.log('✅ 回复检测完成,停止监控');
                    return;
                }

                // 检测回复触发条件
                if (needsReply()) {
                    console.log('🔍 实时检测到回复触发条件');
                    clearInterval(replyDetectionTimer);
                    initAutoReply();
                }
            } catch (error) {
                console.error('实时回复检测出错:', error);
            }
        }, 500); // 500ms检测间隔,确保快速响应

        // DOM变化监听器 - 立即响应新内容
        const replyObserver = new MutationObserver((mutations) => {
            // 如果已经尝试过回复,停止监听
            if (GlobalState.replyState.tried) {
                replyObserver.disconnect();
                return;
            }

            mutations.forEach(mutation => {
                if (mutation.type === 'childList') {
                    mutation.addedNodes.forEach(node => {
                        if (node.nodeType === 1) {
                            const text = node.textContent || '';
                            if (text.includes('本帖含有特定内容,请回复后再查看')) {
                                console.log('🔍 DOM监听检测到回复触发条件');
                                replyObserver.disconnect();
                                clearInterval(replyDetectionTimer);
                                initAutoReply();
                            }
                        }
                    });
                }
            });
        });

        // 开始监听DOM变化
        replyObserver.observe(document.body, {
            childList: true,
            subtree: true
        });

        console.log('✅ 实时回复检测系统已启动');
    }

    // 智能回复初始化(集成反爬虫机制)
    async function initAutoReply() {
        if (GlobalState.replyState.tried || GlobalState.replyState.inProgress) return;

        if (!needsReply()) {
            GlobalState.replyState.tried = true;
            return;
        }

        // 反爬虫检查
        if (shouldSkipReply()) {
            GlobalState.replyState.tried = true;
            return;
        }

        console.log('🤖 智能回复启动(反爬虫模式)');
        GlobalState.replyState.tried = true;
        GlobalState.replyState.inProgress = true;

        try {
            // 模拟用户行为
            await simulateUserBehavior();

            // 添加0-5秒的随机延迟
            const randomDelay = randomBetween(0, ANTI_CRAWLER_CONFIG.maxInterval * 1000);
            if (randomDelay > 0) {
                Log.debug(`随机延迟: ${randomDelay}ms`);
                await delay(randomDelay);
            }

            // 执行回复
            await executeAutoReply();
        } catch (error) {
            Log.error('自动回复执行失败:', error);
            GlobalState.replyState.inProgress = false;
        }
    }

    // 增强的回复元素查找
    function findReplyElements() {
        let replyBox, submitBtn;

        // 优先查找文本输入框(避免快速回复)
        const textInputSelectors = [
            'textarea[name="message"]',
            'textarea[name="content"]',
            'textarea[placeholder*="回复"]',
            'textarea[placeholder*="内容"]',
            'textarea',
            'input[type="text"][name="message"]',
            'input[type="text"][name="content"]'
        ];

        // 快速回复选择器(备用)
        const quickReplySelectors = [
            'select[name="quick_reply_message"]',
            'select[name="message"]',
            'select'
        ];

        // 优先查找文本输入框
        for (const selector of textInputSelectors) {
            const element = document.querySelector(selector);
            if (element && element.offsetParent !== null) {
                replyBox = element;
                Log.debug('找到文本输入框:', selector);
                break;
            }
        }

        // 如果没找到文本框,再找快速回复框
        if (!replyBox) {
            for (const selector of quickReplySelectors) {
                const element = document.querySelector(selector);
                if (element && element.offsetParent !== null) {
                    replyBox = element;
                    Log.debug('找到快速回复框:', selector);
                    break;
                }
            }
        }

        // 查找提交按钮
        const submitSelectors = [
            'button[type="submit"]',
            'input[type="submit"]',
            'button[value="提交"]',
            'button[value="回复"]',
            'button[value="发表"]'
        ];

        for (const selector of submitSelectors) {
            submitBtn = document.querySelector(selector);
            if (submitBtn && submitBtn.offsetParent !== null) break;
        }

        // 如果没找到,尝试通过文本查找按钮
        if (!submitBtn) {
            const buttons = document.querySelectorAll('button');
            for (const btn of buttons) {
                if (/回复|发表|提交|发送/i.test(btn.textContent) && btn.offsetParent !== null) {
                    submitBtn = btn;
                    break;
                }
            }
        }

        const isQuickReply = replyBox && replyBox.tagName === 'SELECT';
        Log.info('回复元素查找结果:', {
            replyBox: replyBox ? replyBox.tagName + (replyBox.name ? `[name="${replyBox.name}"]` : '') : '未找到',
            submitBtn: submitBtn ? submitBtn.textContent || submitBtn.value : '未找到',
            isQuickReply
        });

        return { replyBox, submitBtn, isQuickReply };
    }

    // 智能执行自动回复(集成反爬虫机制)
    async function executeAutoReply() {
        const { replyBox, submitBtn, isQuickReply } = findReplyElements();

        if (!replyBox || !submitBtn) {
            console.log('❌ 未找到回复元素');
            GlobalState.replyState.inProgress = false;
            return;
        }

        await performReply(replyBox, submitBtn, isQuickReply);
    }

    // 智能回复操作(集成反爬虫机制)
    async function performReply(replyBox, submitBtn, isQuickReply = false) {
        try {
            Log.info('🤖 开始智能回复过程');

            // 灵活思考时间
            await delay(randomBetween(50, 200));

            // 强制使用我们的自定义文案,不使用平台快速回复
            const replyText = getRandomReplyText();

            if (isQuickReply && replyBox.tagName === 'SELECT') {
                // 检查是否有自定义选项,如果没有就寻找文本输入框
                Log.debug('检测到快速回复框,尝试寻找文本输入框');

                // 寻找文本输入框
                const textInputs = [
                    document.querySelector('textarea[name="message"]'),
                    document.querySelector('textarea[name="content"]'),
                    document.querySelector('textarea'),
                    document.querySelector('input[type="text"]'),
                    document.querySelector('input[name="message"]')
                ].filter(el => el && el.offsetParent !== null);

                if (textInputs.length > 0) {
                    // 找到文本输入框,使用自定义文案
                    const textBox = textInputs[0];
                    textBox.focus();
                    textBox.value = replyText;
                    textBox.dispatchEvent(new Event('input', { bubbles: true }));
                    textBox.dispatchEvent(new Event('change', { bubbles: true }));
                    Log.info('✅ 使用文本框填充自定义文案:', replyText);
                } else {
                    // 没找到文本框,随机选择快速回复选项(避免总是第一个)
                    const options = Array.from(replyBox.options).filter((opt, idx) => idx > 0 && opt.value); // 跳过第一个空选项
                    if (options.length > 0) {
                        const randomOption = options[Math.floor(Math.random() * options.length)];
                        replyBox.value = randomOption.value;
                        replyBox.dispatchEvent(new Event('change', { bubbles: true }));
                        Log.info('✅ 随机选择快速回复选项:', randomOption.textContent);
                    } else {
                        // 兜底:选择第二个选项(避免第一个)
                        replyBox.selectedIndex = replyBox.options.length > 1 ? 1 : 0;
                        replyBox.dispatchEvent(new Event('change', { bubbles: true }));
                        Log.debug('兜底选择快速回复选项');
                    }
                }
            } else {
                // 传统文本输入框:使用智能文案选择器
                if (ANTI_CRAWLER_CONFIG.enableTypingSimulation) {
                    // 模拟逐字打字
                    await simulateTyping(replyBox, replyText);
                } else {
                    // 极速模式:直接填充文本
                    replyBox.focus();
                    replyBox.value = replyText;
                    replyBox.dispatchEvent(new Event('input', { bubbles: true }));
                    replyBox.dispatchEvent(new Event('change', { bubbles: true }));
                    Log.info('✅ 极速填充自定义文案:', replyText);
                }
            }

            // 灵活提交检查
            const submitDelay = randomBetween(100, 300);
            Log.debug(`灵活提交检查: ${submitDelay}ms`);
            await delay(submitDelay);

            // 提交回复
            submitBtn.click();
            Log.success('✅ 智能回复已提交');

            // 更新统计信息
            updateReplyStats();

            // 重置状态
            GlobalState.replyState.inProgress = false;

        } catch (error) {
            Log.error('❌ 智能回复失败:', error);
            GlobalState.replyState.inProgress = false;
        }
    }

    // 极速打字模拟(几乎无延迟)
    async function simulateTyping(inputElement, text) {
        Log.debug(`极速打字: ${text}`);

        // 先聚焦到输入框
        inputElement.focus();
        inputElement.value = '';

        // 极速模式:直接输入完整文本,只在关键点添加微小延迟
        const chunks = Math.ceil(text.length / 5); // 分成5个块
        for (let i = 0; i < chunks; i++) {
            const endIndex = Math.min((i + 1) * 5, text.length);
            inputElement.value = text.substring(0, endIndex);

            // 触发输入事件
            inputElement.dispatchEvent(new Event('input', { bubbles: true }));

            // 每5个字符只延迟5-15ms
            if (i < chunks - 1) {
                await delay(randomBetween(5, 15));
            }
        }

        // 最终触发change事件
        inputElement.dispatchEvent(new Event('change', { bubbles: true }));
        Log.debug('极速打字完成');
    }

    // 更新回复统计(增加页面记录)
    function updateReplyStats() {
        const now = Date.now();
        const currentUrl = window.location.href;
        const history = GlobalState.replyHistory;

        // 更新回复统计
        GlobalState.antiCrawler.lastReplyTime = now;
        GlobalState.antiCrawler.replyCount += 1;

        // 记录已回复的页面
        history.pageUrls.add(currentUrl);

        // 限制页面历史记录大小
        if (history.pageUrls.size > history.maxHistorySize) {
            const firstUrl = history.pageUrls.values().next().value;
            history.pageUrls.delete(firstUrl);
        }

        Log.info(`📊 回复统计更新: 总计 ${GlobalState.antiCrawler.replyCount} 次回复`);
        Log.debug(`🔒 页面防重复: 已记录 ${history.pageUrls.size} 个页面`);
    }

    // 温和的资源清理函数(只清理内存,保留DOM状态)
    function cleanup() {
        Log.info('清理脚本内部资源');

        // 停止检测定时器
        if (GlobalState.detectionTimer) {
            clearInterval(GlobalState.detectionTimer);
            GlobalState.detectionTimer = null;
        }

        // 清理同域检测器
        if (GlobalState.sameDomainDetector) {
            GlobalState.sameDomainDetector.isDetecting = false;
            GlobalState.sameDomainDetector = null;
        }

        // 清理Log缓存
        if (Log._lastMessages) {
            Log._lastMessages.clear();
        }

        // 只清理内部状态,保留DOM元素和状态映射
        GlobalState.isScanning = false;
        // 无限并发模式:不需要重置activeRequests
        GlobalState.replyState = { tried: false, inProgress: false };

        // 注意:不调用GlobalState.reset(),避免清空linkStatusMap和checkedLinks
        // 这样状态标记可以继续显示直到链接真正消失

        Log.success('内部资源清理完成,状态标记保持显示');
    }

    // 页面卸载时清理资源
    window.addEventListener('beforeunload', cleanup);

    // 早期回复检测(脚本加载时立即执行)
    (function immediateReplyDetection() {
        // 脚本加载时立即检测
        if (document.readyState !== 'loading' && needsReply()) {
            console.log('⚡ 脚本加载时发现回复触发条件');
            initAutoReply();
        }
    })();

    // 初始化其他功能
    init();

    // 验证功能独立性的测试函数
    window.testRealtimeDetection = function() {
        console.log('🧪 测试实时检测功能');
        const testResults = {
            realtimeDetection: !!GlobalState.detectionTimer,
            earlyMonitoring: true, // 已在页面加载时启动
            dynamicObserver: true, // 已在init中启动
            independentFromPanel: true, // 已完全独立
            cacheSystem: GlobalState.linkCache.size >= 0,
            smartDetection: typeof smartDetectLink === 'function'
        };

        console.log('✅ 实时检测功能测试结果:', testResults);

        const allPassed = Object.values(testResults).every(result => result === true);
        console.log(allPassed ? '🎉 所有功能正常' : '⚠️ 部分功能异常');

        return testResults;
    };

    // 测试链接检测功能
    window.testLinkDetection = function(testUrl) {
        if (!testUrl) {
            testUrl = prompt('请输入测试链接:') || 'https://www.123pan.com/s/test123';
        }

        console.log('🧪 测试链接检测:', testUrl);

        if (isPanLink(testUrl)) {
            console.log('✅ 链接格式验证通过');
            // 创建测试链接元素
            const testLink = document.createElement('a');
            testLink.href = testUrl;
            testLink.textContent = testUrl;

            // 立即检测
            checkLink(testLink);
            console.log('✅ 检测已启动');
        } else {
            console.log('❌ 不是有效的123网盘链接');
        }
    };

    // 测试自动回复功能
    window.testAutoReply = function() {
        console.log('🧪 测试智能自动回复功能');
        const testResults = {
            realtimeDetection: typeof startRealtimeReplyDetection === 'function',
            replyDetection: needsReply(),
            replyEnabled: GlobalState.autoReplyEnabled,
            antiCrawlerCheck: !shouldSkipReply(),
            replyElements: (() => {
                const { replyBox, submitBtn } = findReplyElements();
                return { hasReplyBox: !!replyBox, hasSubmitBtn: !!submitBtn };
            })(),
            replyState: GlobalState.replyState,
            antiCrawlerStats: GlobalState.antiCrawler,
            smartTextSelection: typeof getRandomReplyText === 'function'
        };

        console.log('✅ 智能自动回复功能测试结果:', testResults);

        if (testResults.replyDetection) {
            console.log('🔍 检测到回复触发条件');
            if (testResults.replyEnabled && testResults.antiCrawlerCheck) {
                console.log('✅ 反爬虫检查通过,可以测试回复');
                if (confirm('是否立即测试智能自动回复?\n\n将模拟真实用户行为:\n- 随机选择回复文案\n- 模拟鼠标移动和滚动\n- 模拟逐字打字\n- 智能延迟控制')) {
                    GlobalState.replyState = { tried: false, inProgress: false };
                    initAutoReply();
                }
            } else if (!testResults.replyEnabled) {
                console.log('⚠️ 自动回复已禁用,请在菜单中开启');
            } else {
                console.log('⚠️ 反爬虫机制阻止回复(间隔限制或频率限制)');
            }
        } else {
            console.log('ℹ️ 当前页面无回复触发条件');
        }

        return testResults;
    };

    // 测试灵活回复时间
    window.testSpeedReply = function() {
        console.log('🚀 测试灵活回复时间');

        const startTime = Date.now();

        // 模拟各个步骤的时间
        const readingTime = randomBetween(ANTI_CRAWLER_CONFIG.readingTime[0], ANTI_CRAWLER_CONFIG.readingTime[1]);
        const randomDelay = randomBetween(0, ANTI_CRAWLER_CONFIG.maxInterval * 1000);
        const thinkTime = randomBetween(50, 200);
        const submitDelay = randomBetween(100, 300);
        const typingTime = ANTI_CRAWLER_CONFIG.enableTypingSimulation ? randomBetween(50, 200) : 0;

        const totalTime = readingTime + randomDelay + thinkTime + submitDelay + typingTime;

        console.log('⚡ 灵活回复时间分析:');
        console.log(`  阅读时间: ${readingTime}ms (${(readingTime/1000).toFixed(3)}秒)`);
        console.log(`  随机延迟: ${randomDelay}ms (${(randomDelay/1000).toFixed(3)}秒)`);
        console.log(`  思考时间: ${thinkTime}ms (${(thinkTime/1000).toFixed(3)}秒)`);
        console.log(`  打字时间: ${typingTime}ms (${(typingTime/1000).toFixed(3)}秒) - ${ANTI_CRAWLER_CONFIG.enableTypingSimulation ? '启用' : '禁用'}`);
        console.log(`  提交延迟: ${submitDelay}ms (${(submitDelay/1000).toFixed(3)}秒)`);
        console.log(`  📊 预计总时间: ${totalTime}ms (${(totalTime/1000).toFixed(3)}秒)`);
        console.log(`  🎯 目标范围: 0.1-5.0秒`);

        // 测试文案选择
        console.log('\n📝 文案选择测试(70%自定义文案):');
        for (let i = 0; i < 5; i++) {
            const text = getRandomReplyText();
            console.log(`  ${i + 1}. "${text}"`);
        }

        return {
            readingTime,
            randomDelay,
            thinkTime,
            submitDelay,
            typingTime,
            totalTime: totalTime / 1000,
            isWithinRange: totalTime >= 100 && totalTime <= 5000
        };
    };

    // 测试回复元素查找
    window.testReplyElements = function() {
        console.log('🔍 测试回复元素查找');

        const { replyBox, submitBtn, isQuickReply } = findReplyElements();

        console.log('📋 查找结果:');
        console.log('  回复框:', replyBox ? {
            标签: replyBox.tagName,
            名称: replyBox.name || '无',
            ID: replyBox.id || '无',
            类名: replyBox.className || '无',
            占位符: replyBox.placeholder || '无',
            是否可见: replyBox.offsetParent !== null
        } : '❌ 未找到');

        console.log('  提交按钮:', submitBtn ? {
            标签: submitBtn.tagName,
            文本: submitBtn.textContent || submitBtn.value,
            类型: submitBtn.type || '无',
            是否可见: submitBtn.offsetParent !== null
        } : '❌ 未找到');

        console.log('  快速回复:', isQuickReply ? '是' : '否');

        // 测试文案生成
        if (replyBox) {
            console.log('\n📝 文案生成测试:');
            for (let i = 0; i < 3; i++) {
                const text = getRandomReplyText();
                console.log(`  ${i + 1}. "${text}"`);
            }
        }

        // 显示页面上所有可能的输入元素
        console.log('\n🔍 页面上所有输入元素:');
        const allInputs = document.querySelectorAll('input, textarea, select');
        allInputs.forEach((el, idx) => {
            if (el.offsetParent !== null) {
                console.log(`  ${idx + 1}. ${el.tagName}[name="${el.name || '无'}"][type="${el.type || '无'}"] - "${el.placeholder || el.textContent?.substring(0, 20) || '无文本'}"`);
            }
        });

        return { replyBox, submitBtn, isQuickReply };
    };

    // 测试反爬虫机制
    window.testAntiCrawler = function() {
        console.log('🧪 测试反爬虫机制');
        const config = ANTI_CRAWLER_CONFIG;
        const stats = GlobalState.antiCrawler;

        console.log('⚙️ 反爬虫配置:', config);
        console.log('📊 当前统计:', stats);
        console.log('🔄 回复状态:', GlobalState.autoReplyEnabled ? '已开启' : '已关闭');
        console.log('⏰ 下次可回复时间:', stats.lastReplyTime && config.minInterval > 0 ?
            new Date(stats.lastReplyTime + config.minInterval * 1000).toLocaleTimeString() :
            '立即可用');

        // 测试文案选择
        console.log('📝 随机文案测试(自定义+平台混合):');
        for (let i = 0; i < 5; i++) {
            console.log(`  ${i + 1}. ${getRandomReplyText()}`);
        }

        // 显示防重复状态
        const history = GlobalState.replyHistory;
        console.log('🔒 防重复状态:');
        console.log(`  已使用文案: ${history.usedTexts.size}/${history.maxHistorySize}`);
        console.log(`  已回复页面: ${history.pageUrls.size}/${history.maxHistorySize}`);
        console.log(`  当前页面已回复: ${history.pageUrls.has(window.location.href) ? '是' : '否'}`);

        return {
            config,
            stats,
            enabled: GlobalState.autoReplyEnabled,
            canReply: !shouldSkipReply()
        };
    };

    console.log('🚀 123网盘链接检测助手 v4.0.0 已启动!');
    console.log('⚡ 核心功能:无限并发检测、状态持久化显示、自动提取码');
    console.log('🔧 技术特性:GM_xmlhttpRequest同域优化、智能缓存、实时DOM监控');
    console.log('🤖 静默回复:菜单开关控制、0.1-5秒总延迟、智能防重复、70%自定义文案、无页面滚动');
    console.log('💡 测试命令: testReplyElements() 或 testSpeedReply() 或 testAutoReply() 或 testAntiCrawler()');
    console.log('📋 菜单功能:右键脚本图标 → 开启/关闭自动回复、查看回复统计');
    console.log('ℹ️ 无UI设计,完全后台运行,支持超大批量链接场景');

})();