Read Repo in Zread

在GitHub仓库页面添加按钮,快速跳转到Zread AI阅读器

目前為 2025-10-15 提交的版本,檢視 最新版本

// ==UserScript==
// @name            Read Repo in Zread
// @name:cn         在 Zread 中打开
// @namespace       https://greasyfork.org/zh-CN/scripts/552658
// @version         1.0
// @description     在GitHub仓库页面添加按钮,快速跳转到Zread AI阅读器
// @description:en  Add a button on GitHub repository pages to quickly navigate to the Zread AI reader page
// @author          Corlius
// @match           https://github.com/*/*
// @icon            https://zread.ai/favicon.ico
// @license         MIT
// @grant           none
// ==/UserScript==

(function() {
    'use strict';

    // 检查是否在仓库页面(而非用户/组织主页)
    function isRepoPage() {
        const pathParts = window.location.pathname.split('/').filter(part => part);
        // 路径应该至少包含用户名和仓库名,且不是用户主页
        return pathParts.length >= 2 &&
               !window.location.pathname.endsWith('.md') &&
               document.querySelector('[data-testid="repository-container"], .repository-content');
    }

    // 获取仓库信息
    function getRepoInfo() {
        const pathParts = window.location.pathname.split('/').filter(part => part);
        if (pathParts.length >= 2) {
            const owner = pathParts[0];
            const repo = pathParts[1];
            return { owner, repo };
        }
        return null;
    }

    // 创建Zread按钮
    function createZreadButton() {
        const repoInfo = getRepoInfo();
        if (!repoInfo) return null;

        // 创建按钮元素,使用与"Go to file"相同的结构
        const button = document.createElement('a');
        button.href = `https://zread.ai/${repoInfo.owner}/${repoInfo.repo}`;
        button.target = '_blank';
        button.rel = 'noopener noreferrer';
        
        // 使用GitHub原生的按钮样式类和属性
        button.className = 'prc-Button-ButtonBase-c50BI';
        button.setAttribute('data-loading', 'false');
        button.setAttribute('data-no-visuals', 'true');
        button.setAttribute('data-size', 'medium');
        button.setAttribute('data-variant', 'default');
        
        // 创建按钮内容容器
        const buttonContent = document.createElement('span');
        buttonContent.setAttribute('data-component', 'buttonContent');
        buttonContent.setAttribute('data-align', 'center');
        buttonContent.className = 'prc-Button-ButtonContent-HKbr-';
        
        // 创建文本标签
        const textLabel = document.createElement('span');
        textLabel.setAttribute('data-component', 'text');
        textLabel.className = 'prc-Button-Label-pTQ3x';
        textLabel.textContent = 'Zread';
        
        // 组装按钮结构
        buttonContent.appendChild(textLabel);
        button.appendChild(buttonContent);

        return button;
    }

    // 插入按钮到合适位置
    function insertButton() {
        if (!isRepoPage()) return;

        // 查找按钮容器 - GitHub的仓库操作按钮区域
        const buttonContainer = document.querySelector('[data-testid="repository-container"] .d-flex .d-flex:last-child') ||
                               document.querySelector('.repository-content .d-flex .d-flex:last-child') ||
                               document.querySelector('.pagehead-actions') ||
                               document.querySelector('.BtnGroup:last-of-type') ||
                               document.querySelector('.d-flex.gap-2');

        if (buttonContainer && !document.getElementById('zread-button')) {
            const zreadButton = createZreadButton();
            if (zreadButton) {
                zreadButton.id = 'zread-button';
                buttonContainer.appendChild(zreadButton);
                console.log('Zread按钮已添加');
            }
        }
    }

    // 监听页面变化(GitHub是SPA应用)
    let currentUrl = window.location.href;

    function handleUrlChange() {
        if (currentUrl !== window.location.href) {
            currentUrl = window.location.href;
            // URL变化时移除旧按钮
            const oldButton = document.getElementById('zread-button');
            if (oldButton) {
                oldButton.remove();
            }
            // 延迟一点时间等待页面渲染
            setTimeout(insertButton, 500);
        }
    }

    // 使用MutationObserver监听DOM变化
    const observer = new MutationObserver(function(mutations) {
        mutations.forEach(function(mutation) {
            if (mutation.type === 'childList') {
                handleUrlChange();
                insertButton();
            }
        });
    });

    // 监听整个document的变化
    observer.observe(document.body, {
        childList: true,
        subtree: true
    });

    // 页面加载完成后立即插入按钮
    if (document.readyState === 'loading') {
        document.addEventListener('DOMContentLoaded', insertButton);
    } else {
        setTimeout(insertButton, 100);
    }

    // 监听popstate事件(浏览器前进后退)
    window.addEventListener('popstate', function() {
        setTimeout(insertButton, 100);
    });

    console.log('Read Repo in Zread 用户脚本已加载');
})();