Greasy Fork

PubMed快捷键

增加功能按钮,一键收藏PubMed文献到默认收藏夹或导出nbib文件

当前为 2024-02-24 提交的版本,查看 最新版本

// ==UserScript==
// @name         PubMed快捷键
// @version      2024.02.24
// @description  增加功能按钮,一键收藏PubMed文献到默认收藏夹或导出nbib文件
// @author       SpaceThing
// @license      GPL-3.0-or-later
// @match        https://pubmed.ncbi.nlm.nih.gov/*/
// @icon         https://www.google.com/s2/favicons?sz=64&domain=nih.gov
// @namespace    https://greasyfork.org/users/916402
// @grant        none
// ==/UserScript==
(function() {
    'use strict';

    // 获取默认收藏夹id
    window.haveId = false;
    // 获取nbib文件
    window.haveNbib = false;
    // 获取PMID
    window.pmid = document.querySelector('.current-id').innerText;
    // 获取标题
    window.title = document.querySelector('.heading-title').innerText;
    // 获取年份
    window.year = document.querySelector('#full-view-heading .cit').innerText.match(/\d+(?= )/);
    // 获取期刊
    window.journal = document.querySelector('#full-view-journal-trigger').innerText;
    // 获取作者
    window.authors = formatAuthors(document.querySelectorAll('#full-view-heading .full-name')[0].textContent);
    // 获取csrfmiddlewaretoken
    window.csrfmiddlewaretoken = document.querySelector('input[name=csrfmiddlewaretoken]').value;

    // 设置通用弹窗提示语
    window.loading = 'Loading...';
    window.timeout = 'Timeout, please try again.';
    window.fail = 'An unexpected error occurred, please try again.';
    window.login = 'Please log in first.';

    // 获取默认收藏夹id
    getCollections();
    function getCollections() {
        if (!window.haveId) {
            // 获取收藏夹列表
            var xhrCollections = new XMLHttpRequest();
            xhrCollections.open('GET', 'https://pubmed.ncbi.nlm.nih.gov/list-existing-collections/');
            xhrCollections.send();
            xhrCollections.onreadystatechange = function() {
                if (xhrCollections.readyState == 4) {
                    if (xhrCollections.status == 200) {
                        // 提取默认收藏夹的id
                        var response = xhrCollections.responseText;
                        var json = JSON.parse(response);
                        json.collections.forEach(function(collection) {
                            if (collection.name == "Favorites") {
                                window.collection_id = collection.id;
                                window.haveId = true;
                                window.success = 'New items were added to your collection. <a href="https://www.ncbi.nlm.nih.gov/myncbi/collections/' + window.collection_id + '/">Edit your collection.</a>';
                                console.log('Successfully retrieved Favorites id');
                            }
                        });
                    } else {
                        // 请求失败,打印错误信息
                        console.log('There has been a problem fetching favorites id');
                    };
                };
            };
        };
    };

    // 获取nbib文件
    getNbib();
    function getNbib() {
        if (!window.haveNbib) {
            var xhrNbib = new XMLHttpRequest();
            var nbib = 'https://api.ncbi.nlm.nih.gov/lit/ctxp/v1/pubmed/?format=medline&download=y&id=' + window.pmid;
            xhrNbib.responseType = 'blob';
            xhrNbib.open('GET', nbib);
            xhrNbib.send();
            xhrNbib.onreadystatechange = function() {
                if (xhrNbib.readyState == 4) {
                    if (xhrNbib.status == 200) {
                        // 储存nbib为blob
                        var blob = xhrNbib.response;
                        window.nibi_blob = window.URL.createObjectURL(blob);
                        var link = document.createElement('a');
                        link.className = 'nbib-link';
                        link.href = window.nibi_blob;
                        link.download = window.year + ', ' + window.authors + ', ' + window.title + '.nbib';
                        document.body.appendChild(link);
                        window.haveNbib = true;
                        console.log('Successfully retrieved nbib');
                    } else {
                        // 请求失败,打印错误信息
                        console.log('There has been a problem fetching nbib');
                        changePopup('nbib', window.fail);
                        setTimeout(function() {
                            closePopup('nbib');
                        },
                        10000);
                        clickClose();
                    };
                };
            };
        };
    };

    // 添加当前文献到默认收藏夹
    function addFavorites() {
        // 构造请求
        var data = 'article_ids=' + window.pmid + '&csrfmiddlewaretoken=' + window.csrfmiddlewaretoken + '&collection_id=' + window.collection_id;
        // 发送收藏请求
        var xhrFavorites = new XMLHttpRequest();
        xhrFavorites.open('POST', 'https://pubmed.ncbi.nlm.nih.gov/add-to-existing-collection/');
        xhrFavorites.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
        xhrFavorites.send(data);
        // 判断是否收藏成功,并提示任务状态
        xhrFavorites.onreadystatechange = function() {
            if (xhrFavorites.readyState == 4 && xhrFavorites.status == 200) {
                var response = xhrFavorites.responseText;
                var answer = '{"collection_id": "' + window.collection_id + '"}';
                if (response == answer) {
                    changePopup('favorites', window.success);
                } else {
                    changePopup('favorites', window.fail);
                };
            } else {
                changePopup('favorites', window.fail);
            };
            setTimeout(function() {
                closePopup('favorites');
            },
            10000);
            clickClose();
        };
    }

    // 创建遮罩层和弹窗
    function createPopup(note) {
        // 创建遮罩层
        var overlay = document.createElement('div');
        overlay.className = 'popup-overlay ' + note;
        overlay.style.position = 'fixed';
        overlay.style.width = '100%';
        overlay.style.height = '100%';
        overlay.style.zIndex = '10000';
        document.body.appendChild(overlay);
        // 创建弹窗
        var popup = document.createElement('div');
        popup.className = 'notification';
        popup.innerHTML = '<div class="popup-content noty_type__information uswdsTheme"></div>';
        overlay.appendChild(popup);
    };

    // 修改弹窗文本
    function changePopup(note, content) {
        var overlay = document.querySelector('.' + note);
        if (overlay) {
            overlay.querySelector('.popup-content').innerHTML = content;
        };
    };

    // 关闭弹窗
    function closePopup(note) {
        var overlay = document.querySelector('.' + note);
        if (overlay) {
            overlay.remove();
        };
    };

    // 点击关闭弹窗
    function clickClose() {
        var overlay = document.querySelector('.popup-overlay');
        if (overlay) {
            overlay.addEventListener('click',
            function() {
                if (event.target.classList.contains('popup-overlay')) {
                    var overlay = document.querySelector('.popup-overlay');
                    if (overlay) {
                        overlay.remove();
                    };
                };
            });
        };
    };

    // 格式化作者信息
    function formatAuthors(name) {
        // 将名字按空格和连接符分割成数组
        var parts = name.split(/[\s-]+/);
        // 如果只有一个部分,则直接返回
        if (parts.length == 1) {
            return name;
        };
        // 获取最后一个部分作为姓氏
        var lastName = parts.pop();
        // 获取其他部分作为名字,并将它们转换为首字母大写
        var firstName = parts.map(part => part.charAt(0).toUpperCase()).join('');
        return lastName + ' ' + firstName;
    }

    // 创建收藏和nbib按钮
    var place = document.querySelector('.collections-button-container');
    // 创建收藏按钮
    var favoritesButton = document.createElement('button');
    favoritesButton.className = 'collections-button';
    favoritesButton.innerHTML = '<span class="button-label">Favorites</span>';
    place.appendChild(favoritesButton);
    // 创建nbib按钮
    var nbibButton = document.createElement('button');
    nbibButton.className = 'collections-button';
    nbibButton.innerHTML = '<span class="button-label">nbib</span>';
    place.appendChild(nbibButton);

    // 收藏按钮点击事件
    favoritesButton.addEventListener('click',
    function() {
        // 显示弹窗
        createPopup('favorites');
        changePopup('favorites', window.loading);
        if (!window.haveId) {
            getCollections();
        };
        if (window.haveId) {
            addFavorites();
        } else {
            // 提示登录
            changePopup('favorites', window.login);
            clickClose();
        };
    });

    // nbib按钮点击事件
    nbibButton.addEventListener('click',
    function() {
        if (!window.haveNbib) {
            // 显示弹窗
            createPopup('nbib');
            changePopup('nbib', window.loading);
            getNbib();
            setTimeout(function() {
                changePopup('nbib', window.timeout);
                setTimeout(function() {
                    closePopup('nbib');
                },
                10000);
            },
            3000);
            clickClose();
        };
        if (window.haveNbib) {
            var link = document.querySelector('.nbib-link');
            link.click();
        };
    });
})();