From 0bf0ed55c92f817fb09c9637a82d6ed9965a22d5 Mon Sep 17 00:00:00 2001 From: boomzero Date: Mon, 27 Jul 2026 09:04:51 +0800 Subject: [PATCH 1/5] fix: pin Monaco to 0.52.2 to stop intermittent load failures Monaco 0.53.0 declares its minified helper variables with `var` at the top level of every chunk file. AMD chunks are plain scripts rather than modules, so those helpers land on `window`: a live load leaks h, m, r, o, p, s, i, f, u, w, M, y and C. Different chunks give the same name different meanings -- `m` is the field-setter helper in language/css/monaco.contribution.js but is Object.defineProperty in yaml.contribution.6f43d486.js -- so whichever chunk script evaluates last wins. When yaml wins, the css chunk's `r(this, "_options")` call resolves to Object.defineProperty(this, "_options", undefined) and throws "Property description must be an object: undefined". The editor.main callback then never fires, ensureMonaco() times out after 30s, and submitpage.php falls back to the bare textarea. Evaluation order depends on network timing, which is why it only reproduces on some page loads. This is upstream microsoft/monaco-editor#5015, fixed in 0.54.0. cdnjs has no stable release newer than 0.53.0, and the rest of the script sources from cdnjs, so pin back to 0.52.2 -- it ships as a single bundle and leaks no globals at all. Also make ensureMonaco() single-flight. Overlapping callers (submit editor, merge view, freopen snippets) each appended their own loader.js, and the second loader resets the AMD registry while the first is still resolving modules. A failed load clears the cached promise so later calls can retry. Closes #991 Co-Authored-By: Claude Opus 5 --- XMOJ.user.js | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/XMOJ.user.js b/XMOJ.user.js index 9ab9ad5c..fc6ab7e6 100644 --- a/XMOJ.user.js +++ b/XMOJ.user.js @@ -551,7 +551,11 @@ let _earlyObs = null; })(); const CaptchaSiteKey = "0x4AAAAAAALBT58IhyDViNmv"; -const MonacoCDN = "https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.53.0/min/vs"; +// 0.53.0 leaks its minified helper variables (m, r, o, ...) into the global scope from every +// chunk file, so whichever chunk happens to be evaluated last clobbers the others and the +// editor randomly fails to load (microsoft/monaco-editor#5015). 0.52.2 ships a single bundle +// and is not affected. cdnjs has no fixed release newer than 0.53.0 yet. +const MonacoCDN = "https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.52.2/min/vs"; const AdminUserList = ["zhuchenrui2", "shanwenxiao", "chenlangning", "admin"]; // Pre-declared so that closures defined before the async init block can reference them @@ -751,8 +755,19 @@ let GetUserBadge = async (Username) => { } } }; +let MonacoLoadPromise = null; async function ensureMonaco() { if (typeof monaco !== 'undefined') return; + // Callers can overlap (submit page editor, merge view, freopen snippets). Without this guard + // each of them appends its own loader.js, and the second loader resets the AMD registry while + // the first one is still resolving modules. + if (MonacoLoadPromise === null) { + MonacoLoadPromise = loadMonaco(); + MonacoLoadPromise.catch(() => { MonacoLoadPromise = null; }); + } + return MonacoLoadPromise; +} +async function loadMonaco() { const loaderUrl = MonacoCDN + '/loader.js'; if (typeof require === 'undefined' || typeof require.config === 'undefined') { await new Promise((resolve, reject) => { From 38738d371051d9efe27eca717b52dbb52de2007c Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 27 Jul 2026 01:05:52 +0000 Subject: [PATCH 2/5] 3.5.4 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index d94bfece..c0a7cbf0 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "xmoj-script", - "version": "3.5.3", + "version": "3.5.4", "description": "an improvement script for xmoj.tech", "main": "AddonScript.js", "scripts": { From f0a882608bdce5fd46c246dea2cae6b7d17a896d Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 27 Jul 2026 01:05:58 +0000 Subject: [PATCH 3/5] Update version info to 3.5.4 --- Update.json | 11 +++++++++++ XMOJ.user.js | 2 +- 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/Update.json b/Update.json index 3cc9edb0..7f8f039a 100644 --- a/Update.json +++ b/Update.json @@ -3649,6 +3649,17 @@ } ], "Notes": "修复了 MonochromeUI / NewBootstrap 新界面在深色模式下加载时出现的白色闪烁(FOUC/CLS)问题。" + }, + "3.5.4": { + "UpdateDate": 1785114353055, + "Prerelease": true, + "UpdateContents": [ + { + "PR": 997, + "Description": "fix: pin Monaco to 0.52.2 to stop intermittent editor load failures" + } + ], + "Notes": "修复了提交代码页面上 Monaco 编辑器有时无法加载、退化为纯文本框的问题(Monaco 0.53.0 的上游 bug)。" } } } \ No newline at end of file diff --git a/XMOJ.user.js b/XMOJ.user.js index fc6ab7e6..fc6781e5 100644 --- a/XMOJ.user.js +++ b/XMOJ.user.js @@ -1,6 +1,6 @@ // ==UserScript== // @name XMOJ -// @version 3.5.3 +// @version 3.5.4 // @description XMOJ增强脚本 // @author @XMOJ-Script-dev, @langningchen and the community // @namespace https://github/langningchen From 3155ea1fd15e7eb468c33d8d586a5c72c77c2a69 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 27 Jul 2026 02:06:24 +0000 Subject: [PATCH 4/5] 3.6.0 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index c0a7cbf0..c257181d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "xmoj-script", - "version": "3.5.4", + "version": "3.6.0", "description": "an improvement script for xmoj.tech", "main": "AddonScript.js", "scripts": { From a8af10a1f4df6df7d36fa2a0cf6b5d0998a7cc46 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 27 Jul 2026 02:06:25 +0000 Subject: [PATCH 5/5] Update to release 3.6.0 --- Update.json | 23 +++++++++++++++++++++++ XMOJ.user.js | 2 +- 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/Update.json b/Update.json index 7f8f039a..65786d44 100644 --- a/Update.json +++ b/Update.json @@ -3660,6 +3660,29 @@ } ], "Notes": "修复了提交代码页面上 Monaco 编辑器有时无法加载、退化为纯文本框的问题(Monaco 0.53.0 的上游 bug)。" + }, + "3.6.0": { + "UpdateDate": 1785117984532, + "Prerelease": false, + "UpdateContents": [ + { + "PR": 986, + "Description": "Fix Violentmonkey SyntaxError: wrap async init block in IIFE" + }, + { + "PR": 989, + "Description": "Use Monaco Editor and save code in submitpage.php when edit the content" + }, + { + "PR": 992, + "Description": "fix: eliminate dark-mode flash in MonochromeUI/NewBootstrap" + }, + { + "PR": 997, + "Description": "fix: pin Monaco to 0.52.2 to stop intermittent editor load failures" + } + ], + "Notes": "本次发布将 3.5.0 之后的四个预发布版本合并为正式版 3.5.4:\n\n- **#986** 修复 Violentmonkey 下因顶层 `await` 导致的 `SyntaxError`(将异步初始化包进 IIFE)。\n- **#989** 提交代码页面(submitpage.php)改用 Monaco Editor,并支持编辑时保存代码。\n- **#992** 修复 MonochromeUI / NewBootstrap 新界面在深色模式下加载时的白色闪烁(FOUC/CLS)问题。\n- **#997** 将 Monaco 固定到 0.52.2,修复编辑器有时无法加载、退化为纯文本框的问题(0.53.0 上游 bug)。" } } } \ No newline at end of file diff --git a/XMOJ.user.js b/XMOJ.user.js index fc6781e5..69d0d77d 100644 --- a/XMOJ.user.js +++ b/XMOJ.user.js @@ -1,6 +1,6 @@ // ==UserScript== // @name XMOJ -// @version 3.5.4 +// @version 3.6.0 // @description XMOJ增强脚本 // @author @XMOJ-Script-dev, @langningchen and the community // @namespace https://github/langningchen