WaniKani Skip Vocab Lesson Button

Lets you skip having to do the lesson for a vocabulary item from its item page. Requires WKOF.

当前为 2023-11-10 提交的版本,查看 最新版本

// ==UserScript==
// @name         WaniKani Skip Vocab Lesson Button
// @namespace    tampermonkey
// @version      1.1.3
// @description  Lets you skip having to do the lesson for a vocabulary item from its item page. Requires WKOF.
// @author       LupoMikti
// @match        https://www.wanikani.com/vocabulary/*
// @run-at       document-end
// @connect      api.wanikani.com
// @license      MIT
// ==/UserScript==

// Modified from the WK lesson cherry picker script made by Alphaxion
    
(function() {
    'use strict';

    /* global wkof */

    const script_name = 'WaniKani Skip Lesson Button';
    if (!wkof) {
        if (confirm(script_name+' requires Wanikani Open Framework.\nDo you want to be forwarded to the installation instructions?'))
            window.location.href = 'https://community.wanikani.com/t/instructions-installing-wanikani-open-framework/28549';
        return;
    }

    const access_token_url = "https://www.wanikani.com/settings/personal_access_tokens";
    let level, vocab_text, learn_button, subject_id, assignment_id, settings;
    
    const modules = 'ItemData, Apiv2, Settings';
    wkof.include(modules);
    wkof.ready(modules).then(loadSettings).then(startup);

    function loadSettings() {
        return wkof.Settings.load('wkslb',{apikey: 'none'}).then(function(data) {
            settings = wkof.settings.wkslb;

            if (wkof.settings.wklcp) {
                settings.apikey = wkof.settings.wklcp.apikey;
                wkof.Settings.save('wkslb');
            }
        });
    }
    
    function startup() {
        if(!checkForApiKey()) return;
        installCSS();
        createButtons(document.body);
    }

    function checkForApiKey() {
        if (settings.apikey === 'none') {
            let givenkey = prompt('WK Skip Lesson Button: Please enter a valid WaniKani API Key with permission to start assignments.');
            if (givenkey !== null && wkof.Apiv2.is_valid_apikey_format(givenkey)) {
                settings.apikey = givenkey;
                wkof.Settings.save('wkslb');
                return true;
            }
            return false;
        }
        return true;
    }

    function installCSS() {
        let style =
        `<style id="wkskiplessoncss">
            .page-header__icon--jisho {
                background-color: #707070;
                width: 3em;
                color: var(--color-text-dark, --color-text);
            }
            
            .page-header__icon--lesson {
                background-color: var(--color-vocabulary);
                width: 6em;
                color: var(--color-text-dark, --color-text);
            }
        </style>`;

        document.head.insertAdjacentHTML('beforeend', style);
    }

    function createButtons(body) {
        level = body.querySelector('.page-header__icon--level').innerHTML;
        vocab_text = body.querySelector('.page-header__icon--vocabulary').innerHTML;

        // Bonus : add a link to jisho.org
        const jisho_link = 'https://jisho.org/search/' + vocab_text;
        body.querySelector('.page-header__icon--level').insertAdjacentHTML('beforebegin',
            `<a class="page-header__icon page-header__icon--jisho" href="${jisho_link}">JISHO</a>`);
        
        let config = {
            wk_items: {
                options: {assignments: true},
                filters: {
                    item_type: 'voc',
                    srs: 'init',
                    level: level
                }
            }
        };

        wkof.ItemData.get_items(config).then(function(items) {
            for (const item of items) {
                if(item.data.characters === vocab_text) {
                    subject_id = item.id;
                    buildSkipButton(body);
                    break;
                }
            }
        });
    }
    
    function buildSkipButton(body) {
        learn_button = body.querySelector('.page-header__title');
        learn_button.insertAdjacentHTML('afterbegin',
            `<a id="wkskiplessonbtn" class="page-header__icon page-header__icon--lesson" href="javascript:void(0)">Skip Lesson</a>`);
    
        learn_button.addEventListener('click', learnVocab);
    }
    
    async function learnVocab(ev) {
        let wkofoptions = {
            filters: {
                srs_stages: [0],
                subject_types: ['vocabulary', 'kana_vocabulary'],
                levels: level
            }
        };

        let results = await wkof.Apiv2.fetch_endpoint('assignments', wkofoptions);
        let didRetry = false;

        for (const assignment of results) {
            if (assignment.data.subject_id === subject_id) {
                assignment_id = assignment.id;
                try {
                    sendLearnRequest(settings.apikey);
                } catch (error) {
                    didRetry = true;
                    sendLearnRequest(wkof.Apiv2.key);
                }
                break;
            }
        }

        function sendLearnRequest(key) {
            fetch(`https://api.wanikani.com/v2/assignments/${assignment_id}/start`, {
                method: 'PUT',
                headers: {
                    "Authorization": "Bearer " + key,
                    "Wanikani-Revision": "20170710"
                },
                body: {
                    "started_at": new Date().toISOString()
                }
            }).then(function(response) {
                if(response.status !== 200) {
                    if (!didRetry) throw 'Bad Request';
                    if(confirm(`WK API answered : ${response.status} ${response.statusText}\nDo you want to enter a different API key?`)) {
                        settings.apikey = 'none';
                        wkof.Settings.save('wkslb');
                        window.location.href = access_token_url;
                    }
                }
                else {
                    if (didRetry) {
                        settings.apikey = wkof.Apiv2.key;
                        wkof.Settings.save('wkslb');
                    }
                    learn_button.removeEventListener('click', learnVocab);
                    learn_button.remove();
                }
            });
        }
    }

    window.addEventListener('turbo:before-render', function(e) {
        e.preventDefault();
        createButtons(e.detail.newBody);
        e.detail.resume();
    });
})();

QingJ © 2025

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