AO3 Multi-Page Batch Loader

Automatically loads a batch of pages. Page 1 shows 1-10, Page 2 shows 11-20, etc.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey, Greasemonkey или Violentmonkey.

Для установки этого скрипта вам необходимо установить расширение, такое как Tampermonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Userscripts.

Чтобы установить этот скрипт, сначала вы должны установить расширение браузера, например Tampermonkey.

Чтобы установить этот скрипт, вы должны установить расширение — менеджер скриптов.

(у меня уже есть менеджер скриптов, дайте мне установить скрипт!)

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

(у меня уже есть менеджер стилей, дайте мне установить скрипт!)

// ==UserScript==
// @name         AO3 Multi-Page Batch Loader
// @namespace    http://tampermonkey.net/
// @version      1.0
// @description  Automatically loads a batch of pages. Page 1 shows 1-10, Page 2 shows 11-20, etc.
// @author       Gemini
// @match        https://archiveofourown.org/admin/tag_wranglers*
// @match        https://archiveofourown.org/tags/*/wrangle*
// @license      MIT
// ==/UserScript==

(async function() {
    'use strict';

    // --- Configuration ---
    const BATCH_SIZE = 10;
    const REQUEST_DELAY = 400;

    // 1. Determine the current base page from URL
    const urlParams = new URLSearchParams(window.location.search);
    let currentPage = parseInt(urlParams.get('page')) || 1;

    // 2. Calculate the range of pages to fetch
    // Logic: Page 1 triggers loading of pages 2 through 10.
    //        Page 2 triggers loading of pages 11 through 20.
    const startPage = (currentPage === 1) ? 2 : (currentPage - 1) * BATCH_SIZE + 1;
    const endPage = currentPage * BATCH_SIZE;

    const tableBody = document.querySelector("table tbody");
    if (!tableBody) return;

    // 3. Create a floating status indicator
    const statusDiv = document.createElement('div');
    statusDiv.style = "position:fixed; bottom:20px; right:20px; background:rgba(0,0,0,0.8); color:white; padding:10px; z-index:9999; border-radius:5px; font-size:12px; font-family: sans-serif;";
    document.body.appendChild(statusDiv);

    console.log(`🚀 Base page: ${currentPage}. Batch loading up to page ${endPage}...`);

    for (let i = startPage; i <= endPage; i++) {
        statusDiv.innerText = `Loading page ${i} of ${endPage}...`;

        const fetchParams = new URLSearchParams(window.location.search);
        fetchParams.set('page', i);
        const targetUrl = `${window.location.pathname}?${fetchParams.toString()}`;

        try {
            const response = await fetch(targetUrl);
            const text = await response.text();
            const parser = new DOMParser();
            const doc = parser.parseFromString(text, 'text/html');
            const newRows = doc.querySelectorAll("table tbody tr");

            // Stop if no more data is found
            if (newRows.length === 0) {
                statusDiv.innerText = "No more data found.";
                setTimeout(() => statusDiv.remove(), 2000);
                break;
            }

            // Append new rows to the existing table
            newRows.forEach(row => tableBody.appendChild(row));

        } catch (e) {
            console.error(`Failed to load page ${i}:`, e);
            statusDiv.style.background = "red";
            statusDiv.innerText = `Error loading page ${i}`;
        }

        // Rate-limiting delay
        await new Promise(r => setTimeout(r, REQUEST_DELAY));
    }

    statusDiv.innerText = `✅ Batch load complete (up to page ${endPage})`;
    setTimeout(() => statusDiv.remove(), 3000);

})();