// ==UserScript== // @name GitHub镜像加速 // @namespace http://tampermonkey.net/ // @version 1.0.1 // @description 自动检测GitHub连通性并重定向到镜像站点,支持文件下载加速 // @author Your Name // @match *://github.com/* // @match *://raw.githubusercontent.com/* // @match *://*.github.com/* // @grant GM_setValue // @grant GM_getValue // @grant GM_xmlhttpRequest // @grant GM_notification // @grant GM_registerMenuCommand // @grant GM_openInTab // @connect github.com // @connect raw.githubusercontent.com // @connect kkgithub.com // @connect bgithub.xyz // @connect gitclone.com // @connect github.ur1.fun // @connect moeyy.cn // @connect gh-proxy.com // @connect ghproxy.net // @connect ghp.ci // @connect toolwa.com // @connect ghproxy.homeboyc.cn // ==/UserScript== (function() { 'use strict'; // 默认配置 const defaultConfig = { enabled: true, autoMode: true, lastCheck: 0, isGitHubAccessible: true, checkInterval: 5 * 60 * 1000, // 检查间隔,默认5分钟 selectedMirror: 'kkgithub.com', mirrors: [ { name: 'BGitHub', url: 'bgithub.xyz' }, { name: 'KKGitHub', url: 'kkgithub.com' }, { name: 'GitClone', url: 'gitclone.com/github.com' }, { name: 'GitHub加速下载', url: 'github.ur1.fun' } ], fileProxies: [ { name: 'Moeyy', url: 'https://moeyy.cn/gh-proxy/' }, { name: 'GHProxy.com', url: 'https://gh-proxy.com/' }, { name: 'GHProxy.net', url: 'https://ghproxy.net/' }, { name: 'GHProxy.ci', url: 'https://ghp.ci/' }, { name: 'TOOLWA', url: 'http://toolwa.com/github/' }, { name: 'HomeBoyCi', url: 'https://ghproxy.homeboyc.cn/' } ], selectedFileProxy: 'https://moeyy.cn/gh-proxy/' }; // 获取配置 let config = GM_getValue('config', defaultConfig); // 检查GitHub可访问性 function checkGitHubAccessibility() { return new Promise((resolve) => { // 如果距离上次检查的时间不足checkInterval,则使用上次的结果 const now = Date.now(); if (now - config.lastCheck < config.checkInterval) { resolve(config.isGitHubAccessible); return; } // 更新上次检查时间 config.lastCheck = now; // 设置超时处理 const timeout = setTimeout(() => { config.isGitHubAccessible = false; GM_setValue('config', config); updateUI(); resolve(false); }, 3000); // 3秒超时 // 使用GM_xmlhttpRequest进行网络测试 GM_xmlhttpRequest({ method: 'HEAD', url: 'https://github.com/favicon.ico', timeout: 3000, onload: function(response) { clearTimeout(timeout); config.isGitHubAccessible = true; GM_setValue('config', config); updateUI(); console.log('GitHub 可访问,不需要使用镜像'); resolve(true); }, onerror: function(error) { clearTimeout(timeout); config.isGitHubAccessible = false; GM_setValue('config', config); updateUI(); console.log('GitHub 不可访问,将使用镜像', error); resolve(false); } }); }); } // 更新UI显示 function updateUI() { const status = document.getElementById('github-mirror-status'); if (status) { if (config.isGitHubAccessible) { status.textContent = 'GitHub 可正常访问'; status.className = 'github-mirror-status good'; } else { status.textContent = 'GitHub 无法访问,使用镜像'; status.className = 'github-mirror-status bad'; } } } // 添加状态显示元素 function addStatusElement() { const header = document.querySelector('.Header'); if (header && !document.getElementById('github-mirror-status')) { const status = document.createElement('div'); status.id = 'github-mirror-status'; status.className = 'github-mirror-status'; status.textContent = '检测中...'; header.appendChild(status); } } // 修改下载链接 function modifyDownloadLinks() { // 查找所有指向GitHub资源的链接 const links = document.querySelectorAll('a[href*="github.com"], a[href*="raw.githubusercontent.com"], a[href*="releases/download"]'); links.forEach(link => { const href = link.getAttribute('href'); // 检查是否为文件下载链接 if (isFileDownloadLink(href) && config.selectedFileProxy) { // 使用文件代理替换链接 link.setAttribute('original-href', href); link.setAttribute('href', `${config.selectedFileProxy}${href}`); link.setAttribute('data-gh-proxy', 'true'); // 添加视觉提示 link.style.color = '#1e88e5'; } }); } // 判断是否为文件下载链接 function isFileDownloadLink(url) { // 检查是否是常见的GitHub资源下载链接 const patterns = [ /github\.com\/.*\/releases\/download\//, /raw\.githubusercontent\.com\//, /github\.com\/.*\/archive\//, /github\.com\/.*\/blob\//, /codeload\.github\.com\// ]; return patterns.some(pattern => pattern.test(url)); } // 重定向到镜像站点 function redirectToMirror() { if (!config.enabled || (config.autoMode && config.isGitHubAccessible)) { return; } const currentUrl = window.location.href; const url = new URL(currentUrl); // 检查是否是原始的github.com域名 if (url.hostname === 'github.com' || url.hostname.endsWith('.github.com')) { // 构建新的镜像URL url.hostname = config.selectedMirror; window.location.href = url.toString(); } } // 注册菜单命令 function registerMenuCommands() { // 启用/禁用开关 GM_registerMenuCommand( config.enabled ? '禁用GitHub镜像加速' : '启用GitHub镜像加速', function() { config.enabled = !config.enabled; GM_setValue('config', config); GM_notification({ text: config.enabled ? '已启用GitHub镜像加速' : '已禁用GitHub镜像加速', timeout: 3000 }); } ); // 自动模式开关 GM_registerMenuCommand( config.autoMode ? '关闭自动检测模式' : '开启自动检测模式', function() { config.autoMode = !config.autoMode; GM_setValue('config', config); GM_notification({ text: config.autoMode ? '已开启自动检测模式' : '已关闭自动检测模式', timeout: 3000 }); } ); // 立即检测 GM_registerMenuCommand('立即检测GitHub连通性', function() { checkGitHubAccessibility(); }); // 打开设置页面 GM_registerMenuCommand('打开设置页面', function() { GM_openInTab('https://github.com/settings', { active: true }); }); } // 添加样式 function addStyles() { const style = document.createElement('style'); style.textContent = ` .github-mirror-status { padding: 5px 10px; border-radius: 4px; margin-left: 10px; font-size: 12px; font-weight: 500; background-color: #6a737d; color: white; } .github-mirror-status.good { background-color: #2ea44f; } .github-mirror-status.bad { background-color: #d73a49; } `; document.head.appendChild(style); } // 初始化 async function init() { // 添加样式 addStyles(); // 注册菜单命令 registerMenuCommands(); // 添加状态显示 addStatusElement(); // 检查GitHub可访问性 const isAccessible = await checkGitHubAccessibility(); // 如果需要,重定向到镜像站点 if (!isAccessible) { redirectToMirror(); } // 修改下载链接 modifyDownloadLinks(); // 设置定时检查 setInterval(checkGitHubAccessibility, config.checkInterval); // 监听DOM变化 const observer = new MutationObserver(function(mutations) { for (const mutation of mutations) { if (mutation.addedNodes.length) { modifyDownloadLinks(); } } }); observer.observe(document.body, { childList: true, subtree: true }); } // 启动脚本 init(); })();