童话翻译

拦截指定路径的请求,修改内容并返回

// ==UserScript==
// @name         童话翻译
// @version      1.03
// @description  拦截指定路径的请求,修改内容并返回
// @author       红凯
// @match        https://otogi-rest.otogi-frontier.com/*
// @grant        GM_xmlhttpRequest
// @namespace https://gf.qytechs.cn/users/1408925
// ==/UserScript==

(function () {
    const open = XMLHttpRequest.prototype.open;
    const send = XMLHttpRequest.prototype.send;

    XMLHttpRequest.prototype.open = function (method, url, async, user, password) {
        this._interceptedUrl = url;
        return open.apply(this, arguments);
    };

    XMLHttpRequest.prototype.open = function (method, url, async, user, password) {
        if (url.includes("Assets/font")) {
            console.log("[重定向字体]");
            const newURL = "https://pub-8c5e69e127a7478d9f9bec549ff7d8d5.r2.dev/font";
            arguments[1] = newURL;
        }

        this._interceptedUrl = url;
        return open.apply(this, arguments);
    };

    XMLHttpRequest.prototype.send = function (body) {
        this.addEventListener("readystatechange", function () {
            if (this.readyState === 4 && this._interceptedUrl.includes("api/MAdults/MonsterMAdults/")) {
                const lastPartOfUrl = this._interceptedUrl.split("/").pop();
                if (this.responseType === "arraybuffer") {
                    const textDecoder = new TextDecoder();
                    const textEncoder = new TextEncoder();

                    try {
                        const originalText = textDecoder.decode(this.response);
                        let originalJson = JSON.parse(originalText);
                        const translationJsonUrl = "https://pub-8c5e69e127a7478d9f9bec549ff7d8d5.r2.dev/MAdults_CN/" + lastPartOfUrl + ".json";
                        const translationData = loadTranslationJsonSync(translationJsonUrl);

                        if (translationData) {
                            originalJson = replaceUsingTranslation(originalJson, translationData);
                        } else {
                            console.warn("[拦截] 未加载到译文 JSON,跳过替换。");
                        }
                        const modifiedText = JSON.stringify(originalJson);
                        const modifiedArrayBuffer = textEncoder.encode(modifiedText).buffer;
                        Object.defineProperty(this, "response", {
                            value: modifiedArrayBuffer
                        });
                        console.log("[拦截] 替换后的 ArrayBuffer 响应已返回给页面。");

                    } catch (e) {
                        console.error("[拦截] ArrayBuffer 转换或 JSON 解析失败:", e);
                    }
                }
            } else if (this.readyState === 4 && this._interceptedUrl.includes("api/MScenes/")) {
                const lastPartOfUrl = this._interceptedUrl.split("/").pop();
                if (this.responseType === "arraybuffer") {
                    const textDecoder = new TextDecoder();
                    const textEncoder = new TextEncoder();

                    try {
                        const originalText = textDecoder.decode(this.response);
                        let originalJson = JSON.parse(originalText);
                        const translationJsonUrl = "https://pub-8c5e69e127a7478d9f9bec549ff7d8d5.r2.dev/MScenes_CN/" + lastPartOfUrl + ".json";
                        const translationData = loadTranslationJsonSync(translationJsonUrl);

                        if (translationData) {
                            originalJson = replaceUsingTranslation(originalJson, translationData);
                        } else {
                            console.warn("[拦截] 未加载到译文 JSON,跳过替换。");
                        }
                        const modifiedText = JSON.stringify(originalJson);
                        const modifiedArrayBuffer = textEncoder.encode(modifiedText).buffer;
                        Object.defineProperty(this, "response", {
                            value: modifiedArrayBuffer
                        });
                        console.log("[拦截] 替换后的 ArrayBuffer 响应已返回给页面。");

                    } catch (e) {
                        console.error("[拦截] ArrayBuffer 转换或 JSON 解析失败:", e);
                    }
                }
            } else if (this.readyState === 4 && this._interceptedUrl.includes("api/Episode/MStory")) {
                const lastPartOfUrl = this._interceptedUrl.split("/").pop();
                if (this.responseType === "arraybuffer") {
                    const textDecoder = new TextDecoder();
                    const textEncoder = new TextEncoder();

                    try {
                        const originalText = textDecoder.decode(this.response);
                        let originalJson = JSON.parse(originalText);
                        const translationJsonUrl = "https://raw.githubusercontent.com/kureinaikai/otogi_frontier_translate/refs/heads/main/Mstory/" + lastPartOfUrl + ".json";
                        const translationData = loadTranslationJsonSync(translationJsonUrl);

                        if (translationData) {
                            originalJson = replaceUsingTranslation(originalJson, translationData);
                        } else {
                            console.warn("[拦截] 未加载到译文 JSON,跳过替换。");
                        }
                        const modifiedText = JSON.stringify(originalJson);
                        const modifiedArrayBuffer = textEncoder.encode(modifiedText).buffer;
                        Object.defineProperty(this, "response", {
                            value: modifiedArrayBuffer
                        });
                        console.log("[拦截] 替换后的 ArrayBuffer 响应已返回给页面。");

                    } catch (e) {
                        console.error("[拦截] ArrayBuffer 转换或 JSON 解析失败:", e);
                    }
                }
            }
        });
        return send.apply(this, arguments);
    };

    function loadTranslationJsonSync(url) {
        const xhr = new XMLHttpRequest();
        xhr.open("GET", url, false);
        try {
            xhr.send();
            if (xhr.status >= 200 && xhr.status < 300) {
                console.log("[拦截] 同步加载译文 JSON 成功:", url);
                return JSON.parse(xhr.responseText);
            } else {
                console.error(`[拦截] 同步加载译文 JSON 失败,HTTP 状态码:${xhr.status}`);
                return null;
            }
        } catch (error) {
            console.error("[拦截] 同步加载译文 JSON 过程中出错:", error);
            return null;
        }
    }

    function replaceUsingTranslation(data, translationDict) {
        if (typeof data === "string" && translationDict[data]) {
            return translationDict[data]; // 替换为译文 JSON 中的对应值
        } else if (Array.isArray(data)) {
            return data.map((item) => replaceUsingTranslation(item, translationDict));
        } else if (typeof data === "object" && data !== null) {
            const newData = {};
            for (const key in data) {
                newData[key] = replaceUsingTranslation(data[key], translationDict);
            }
            return newData;
        }
        return data;
    }
})();

QingJ © 2025

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