Via Adblock 规则分析

解析Adblock规则,是否值得在Via浏览器上订阅,评分仅供娱乐,自行斟酌。

目前為 2025-03-22 提交的版本,檢視 最新版本

// ==UserScript==
// @name         Via Adblock 规则分析
// @namespace    https://viayoo.com/
// @version      1.12
// @description  解析Adblock规则,是否值得在Via浏览器上订阅,评分仅供娱乐,自行斟酌。
// @author       Grok & Via
// @match        *://*
// @license      MIT
// @grant        GM_registerMenuCommand
// @run-at       document-start
// ==/UserScript==

(function() {
    'use strict';
    console.log('Adblock Rule Analyzer 脚本已加载,URL:', location.href);

    // 注册(不可用)菜单项
    GM_registerMenuCommand("分析当前页面规则", analyzeCurrentPage);
    GM_registerMenuCommand("分析自定义链接规则", analyzeCustomLink);

    // 分析当前页面
    async function analyzeCurrentPage() {
        console.log('分析当前页面');
        let content;
        try {
            const response = await fetch(location.href);
            content = await response.text();
            console.log('当前页面内容获取成功,长度:', content.length);
        } catch (e) {
            alert('无法获取当前页面内容: ' + e.message);
            console.error('当前页面内容获取失败:', e);
            return;
        }
        analyzeContent(content, '当前页面');
    }

    // 分析自定义链接
    function analyzeCustomLink() {
        console.log('分析自定义链接');
        const url = prompt('请输入Adblock规则文件的直链(如 https://raw.githubusercontent.com/...)');
        if (!url || !url.trim()) {
            alert('未输入有效的链接');
            return;
        }

        fetch(url)
            .then(response => {
                if (!response.ok) throw new Error('网络请求失败,状态码: ' + response.status);
                return response.text();
            })
            .then(content => {
                console.log('自定义链接内容获取成功,长度:', content.length);
                analyzeContent(content, url);
            })
            .catch(e => {
                alert('无法获取链接内容: ' + e.message);
                console.error('自定义链接内容获取失败:', e);
            });
    }

    // 处理换行符,统一为 \n
    function normalizeNewlines(text) {
        return text.replace(/\r\n/g, '\n').replace(/\r/g, '\n');
    }

    // 通用分析函数
    function analyzeContent(content, source) {
        if (!content.startsWith('[Adblock') && !content.startsWith('![Adblock')) {
            alert('这不是一个Adblock规则文件(未找到[Adblock开头),来源: ' + source);
            console.log('非Adblock文件,来源:', source);
            return;
        }
        content = normalizeNewlines(content); // 在传递内容之前统一处理换行符
        const lines = content.split('\n')
            .filter(line => line.trim() !== '' && !line.trim().startsWith('!') && !line.trim().startsWith('['));

        const stats = {
            cssRules: {
                normal: 0,
                exception: 0
            },
            domainRules: 0,
            unsupported: 0,
            extendedRules: {
                scriptInject: 0,
                adguardScript: 0,
                htmlFilter: 0,
                cssInject: 0,
                other: 0
            }
        };

        // uBlock/AdGuard 扩展规则模式
        const extendedPatterns = {
            scriptInject: /(##|@#+)\+js\(/,
            adguardScript: /#@?%#/,
            htmlFilter: /\$\$/,
            cssInject: /#@?\$#/,
            other: /\$(\s*)(redirect|rewrite|csp|removeparam|badfilter|empty|generichide|match-case|object|object-subrequest|important|popup|document)|,(\s*)(redirect=|app=|replace=|csp=|denyallow=|permissions=)|:matches-path|:remove|redirect-rule/
        };

        lines.forEach(line => {
            const trimmed = line.trim();

            if (trimmed.startsWith('##') || trimmed.startsWith('###')) {
                if (extendedPatterns.scriptInject.test(trimmed)) {
                    stats.extendedRules.scriptInject++;
                    stats.unsupported++;
                } else {
                    stats.cssRules.normal++;
                }
            } else if (trimmed.startsWith('#@#') || trimmed.startsWith('#@##')) {
                if (extendedPatterns.scriptInject.test(trimmed)) {
                    stats.extendedRules.scriptInject++;
                    stats.unsupported++;
                } else {
                    stats.cssRules.exception++;
                }
            } else if (trimmed.startsWith('#')) {
                if (extendedPatterns.adguardScript.test(trimmed)) {
                    stats.extendedRules.adguardScript++;
                    stats.unsupported++;
                } else if (extendedPatterns.cssInject.test(trimmed)) {
                    stats.extendedRules.cssInject++;
                    stats.unsupported++;
                } else {
                    stats.unsupported++;
                }
            } else if (trimmed.startsWith('||')) {
                if (extendedPatterns.other.test(trimmed)) {
                    stats.extendedRules.other++;
                    stats.unsupported++;
                } else {
                    stats.domainRules++;
                }
            } else if (extendedPatterns.htmlFilter.test(trimmed)) {
                stats.extendedRules.htmlFilter++;
                stats.unsupported++;
            }
        });

        const totalCssRules = stats.cssRules.normal + stats.cssRules.exception;
        const totalExtendedRules = stats.extendedRules.scriptInject + stats.extendedRules.adguardScript +
            stats.extendedRules.htmlFilter + stats.extendedRules.cssInject +
            stats.extendedRules.other;

        let score = 0;

        // CSS规则评分(总分50)
        if (totalCssRules <= 7000) {
            score += 50;
        } else if (totalCssRules <= 9999) {
            score += 50 - ((totalCssRules - 7000) / 3000) * 25; // 线性递减
        } else {
            score += 25 - ((totalCssRules - 9999) / 5000) * 10; // 超出9999的柔性扣分
        }

        // 域名规则评分(总分40)
        if (stats.domainRules <= 100000) {
            score += 40;
        } else if (stats.domainRules <= 500000) {
            score += 40 - ((stats.domainRules - 100000) / 400000) * 20; // 新增档位
        } else if (stats.domainRules <= 2000000) {
            score += 20 - ((stats.domainRules - 500000) / 1500000) * 20;
        } else {
            score = Math.max(1, score - ((stats.domainRules - 2000000) / 500000) * 10); // 超大规则集额外扣分
        }

        // 扩展规则扣分(最多扣30分)
        if (totalExtendedRules > 500) {
            score -= 30; // 超过 500 条规则,直接扣满 30 分
        } else if (totalExtendedRules > 100) {
            score -= 10 + ((totalExtendedRules - 100) / 400) * 15;
            // 超过 100 条但不超过 500 条,根据比例扣分,最多扣 25 分
        } else if (totalExtendedRules > 0) {
            score += 0; // 保持现状,无扣分
        } else {
            score += 10; // 没有扩展规则,额外加 10 分
        }

        // 限制总分在 1 到 100 之间
        score = Math.max(1, Math.min(100, Math.round(score)));

        // 优化后的 CSS 性能评估
        let cssPerformance;
        if (totalCssRules <= 5000) {
            cssPerformance = '✅CSS规则数量正常,可以流畅运行';
        } else if (totalCssRules <= 7000) {
            cssPerformance = '❓CSS规则数量较多,可能会导致设备运行缓慢';
        } else if (totalCssRules < 9999) {
            cssPerformance = '⚠️CSS规则数量接近上限,可能明显影响设备性能';
        } else {
            cssPerformance = '🆘CSS规则数量过多,不建议订阅此规则';
        }

        // 优化后的域名规则评估
        let domainPerformance;
        if (stats.domainRules <= 100000) {
            domainPerformance = '✅域名规则数量正常,可以流畅运行';
        } else if (stats.domainRules <= 200000) {
            domainPerformance = '❓域名规则数量较多,但仍在可接受范围内';
        } else if (stats.domainRules <= 500000) {
            domainPerformance = '🆘域名规则数量过多,可能会导致内存溢出 (OOM)';
        } else {
            domainPerformance = '‼️域名规则数量极多,强烈不建议使用,可能严重影响性能';
        }

        const report = `
Adblock规则分析结果(来源: ${source}):
💯规则评级: ${score}/100
(CSS规则占比最大,独有规则减分,域名规则次要)
(评分仅供参考,具体以Via变动为主)
---------------------
📋CSS通用隐藏规则:
  常规规则 (##, ###): ${stats.cssRules.normal}
  例外规则 (#@#, #@##): ${stats.cssRules.exception}
  总CSS规则数: ${totalCssRules}
  性能评估: ${cssPerformance}
🔗域名规则 (||): ${stats.domainRules}
  性能评估: ${domainPerformance}
✋🏼uBlock/AdGuard 独有规则:
  脚本注入 (##+js): ${stats.extendedRules.scriptInject}
  AdGuard脚本 (#%#): ${stats.extendedRules.adguardScript}
  HTML过滤 ($$): ${stats.extendedRules.htmlFilter}
  CSS注入 (#$#): ${stats.extendedRules.cssInject}
  其他扩展规则 ($redirect等): ${stats.extendedRules.other}
  总计: ${totalExtendedRules}
👋不支持的规则: ${stats.unsupported}
🛠️总规则数: ${lines.length}
注:uBlock/AdGuard 独有规则在传统 Adblock Plus 中不受支持
        `;
        alert(report);
        console.log(report);
    }
})();

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址