无名杀【自动测试与精确报错】合并版扩展分享(v3.6.16)
日期: 2026-08-09
作者: 路克斯
最新全文: https://stlux.art/noname-precision-error-reporting-and-automated-testing
下载链接:链接里日期最近的就是最新版 https://pan.baidu.com/s/5zbY_l3oF8zU1v-eBIPjPJQ
前言
(一)这个扩展是给"无名杀"的开发者用的工具,解决两个问题:
第一,游戏运行出错时,原来的部分报错信息太模糊,只告诉你"出错了"但不告诉你在哪个文件、哪一行、什么原因;
第二,检查错误、提取错误信息、修完再验证的整个过程太麻烦,需要人工反复操作。
合并版扩展 v3.6.16(原名分两个:精确报错 + 自动测试,现已合并为单个扩展「自动测试与精确报错」)同时解决这两个问题:它在角色代码加载前先做语法检查,发现错误时精确指出是哪个文件、第几行、第几个字符、大概是什么原因(比如少了逗号、引号没配对、括号不匹配),开发者在游戏运行前就知道问题在哪;然后让游戏进入 AI 自动对战模式,打完一局自动重开下一局,全程自动循环,期间遇到报错或卡死自动记录日志并重启,玩家可以让 agent 读日志、AI 自己修,这样玩家不需要一直盯着屏幕手动操作,甚至不用读报错日志。
建议用万能导入法导入,扩展内的 README.MD 是说明书。简单点说,就是安装这一个扩展后,游戏里点【托管】就行了。
(二)我时间比较少,只负责发布,不负责售后- -建议想 diy 的玩家搜索学习使用 claude code 之类的 ai agent 工具,做扩展、修报错、让扩展跟随本体升级版本,都不需要学代码,跟 ai 许愿就可以了。我扩展做了 600 +角色,都靠 ai 迁移适配了无名杀最新版本~
Agent 接入 deepseek v4 够用了,又便宜~
我以往做的扩展:
在三国杀里玩影之诗是什么体验?用三国杀机制还原林德沃姆觉醒【影之诗】
用三国杀的机制体验 fate-stay-night英灵卫宫无限剑制【Fate/stay night 】
用三国杀的机制使用fgo旧剑excalibur是什么体验?【Fate/stay night 】
用三国杀的机制还原 赫拉克勒斯 VS 阿尔托莉雅alter【Fate/stay night 】看前 27 秒即可
放下我做的【三界圣战】扩展对局截图,界面、手牌填充等问题还在优化- -:


杀、雷杀、火杀、冰杀,我都做了区分:


一、新版架构与优势
1.1 合并为一个扩展
旧版是两个独立扩展(精确报错 v1.1.0 + 自动测试 v2.4.0),各有一套代码、配置和加载逻辑。v3.2.0 起合并为单个扩展「自动测试与精确报错」,装一个替代两个:
- 单一扩展入口、单一配置系统、单一 localStorage 命名空间
- 诊断与自动测试共享同一套运行时状态、日志系统、卡死检测
- 扩展管理菜单只占一个位置
1.2 模块化架构(src/10 模块)
合并版采用模块化目录结构,代码拆成 10 个职责单一的文件。单个模块加载失败不阻断其余模块(每个模块独立 try/catch):
| 模块 | 职责 |
|---|---|
| 01-init | 运行时状态、看门狗/心跳/状态超时统一读取、双延迟配置、自身错误守卫 |
| 02-log | 预期 404 白名单(11 条)、运行时日志、行数截断、缓冲去重 |
| 03-char | 角色测试状态追踪、localStorage+文件双写持久化、角色对话框补丁 |
| 04-diag | 日志写入、模板抑制、错误签名(文件:行号:列号)、crash-report 段裁剪、天级日志轮替、弹窗信号分级 |
| 05-loop | 诊断信息构建、强制重启、主循环、game.over 补丁、开局看门狗 |
| 06-stack | 堆栈采样、状态日记、弹窗处理、closeAndRestart 重启链 |
| 07-popup | alert/confirm 拦截、全局调试函数、状态面板 UI(名单管理 UI 已移除 v3.6.1,改 char-list.md 明文编辑) |
| 08-guard | game.me.group 拦截器、chooseButton 守卫、error/unhandledrejection 捕获、console 覆写 |
| 09-syntax | 语法验证器(vm.Script + 5 类启发式)、9 个 check 诊断函数、编辑距离模糊匹配 |
| 10-entry | 配置系统、田字格面板、扩展工厂函数、FIX 补丁安装 |
1.3 零构建 + 纯 ESM + 可调试
- 零构建:extension.js 为纯 ESM 引导入口(fetch + eval 运行时加载 src/),改 src/ 下任意 .js 直接生效,无需运行构建脚本(build.js 自 v3.4.0 起废弃)
- 纯 ESM 入口:
export var type+export default工厂包装,src/ 模块通过fetch()+(0,eval)运行时加载,零 Node.js 依赖(fs/path/require/vm 全不需要),修复 Electron HTTP 加载兼容 - DevTools 可调试:每个模块末尾
//# sourceURL=src/xxx.js,浏览器 DevTools 能映射回实际源文件,断点调试跟开发时一样 - 加载可观测:工厂函数未找到时列出 window 上所有 autotest/precise 前缀键,方便定位
1.4 对比旧版优势
| 维度 | 旧版(两个独立扩展) | 合并版 v3.6.16 |
|---|---|---|
| 安装 | 装两个 | 装一个 |
| 架构 | 单文件堆叠 | src/10 模块 |
| 加载 | 构建产物,改代码要重新构建 | fetch+eval 运行时加载,改 src/ 直接生效 |
| Node 依赖 | 依赖 fs/path/vm | 零 |
| DevTools | 无法映射源码 | sourceURL 可调试 |
| 模块隔离 | 一处崩全崩 | 单模块失败不阻断 |
| 自身防护 | 无 | 自身错误计数 + 降级模式 |
二、诊断与防护
2.1 启动时自动诊断(9 项检查)
游戏启动后几秒钟,扩展自动执行以下检查,结果直接显示在控制台。每项可独立开关(扩展管理菜单或右下角 🔍 面板):
| 诊断函数 | 功能 |
|---|---|
checkMissingSkills |
运行时技能缺失——角色挂载的技能名在 lib.skill 中是否有定义 |
checkMissingSkillsDetailed |
文件级扫描(含行号),并给出编辑距离 ≤3 的相近技能名建议 |
checkBraceBalance |
括号平衡检测——{} 是否成对(字符串/注释过滤);v3.6.15 起 async 异步分片,每文件处理完让出主线程、大文件内部每 512KB 让出,消除开局主线程冻结;同步 O(n²) 行号计算已改为行号变量跟踪(单文件提速约 3000 倍) |
checkTranslateCompletion |
翻译完整性——技能 name + _info 双检;async |
checkImportErrors |
导入错误——按子包分组,定位分包 import() 静默失败 |
checkPartFileLoad |
part 文件加载状态——共享目录 fallback 是否成功 |
checkMissingImages |
角色翻译缺失——角色名在语言表中是否有翻译条目 |
checkInfoPollution |
_info 非对象值污染检测 |
checkBackupContent |
backup 函数 content 字段检测——防止 compiled 崩;v6 增强:兼容 ES6 方法简写 + viewAs 豁免 + get.copy 降级提示 + 引用模式豁免(return lib.skill[..] / return get.copy(..) / var x=lib.skill[..]; return x 中转模式返回引用对象含 content 视为正常);async |
💡 v3.6.15 起三个大库扫描函数(checkBraceBalance / checkTranslateCompletion / checkBackupContent)均为 async,控制台手动调用返回 Promise,日志照常输出,不再阻塞游戏主线程。
除 9 个 check 外,还有语法验证器:
validateExtension('三界圣战')/validateSingleFile('三界圣战/character/xxx.js'):对 JS 文件做 vm.Script 语法检查- 5 类启发式检测(动态 import 的 SyntaxError 不含文件/行号,这 5 类专门补漏):
- 单引号内嵌代码:
'...(' x'+y)...'字符串提前闭合 - 双单引号开头:翻译条目值以
''开头 - 对象缺逗号:前项
}闭合后缺逗号 - skills 数组逗号错误:
"skill_a,skill_b"应为"skill_a", "skill_b" - step 标签同行:
'step N'与return;/goto同行
- 单引号内嵌代码:
- 每类错误附带修复建议 + 源码上下文(▶ 标记出错行),并给出编辑距离相近名辅助定位
2.2 运行时日志落盘
游戏运行中的报错(TypeError、ReferenceError、动态 import 失败、Promise 异常等)自动拦截写入文件。日志文件位于 resources/app/log/:
| 文件 | 内容 |
|---|---|
runtime-errors.log |
运行时错误日志 |
console-export.log |
控制台总日志 |
console-errors.log / console-warnings.log / console-info.log |
分级别日志 |
hang-*.log |
卡死诊断快照(最多保留 5 个) |
auto-test-errors.log |
自动测试专用错误日志 |
self-errors.log |
扩展自身异常日志 |
error-popup.log |
弹窗错误(角色名+文件名+控制台上下文,去重机制仍引用) |
crash-report-*.log |
卡死报告(完整诊断上下文,v3.5.9 起全类型签名去重) |
日志策略:
- 每个文件上限 2000 行(
_trimLogFile截头留尾) - 启动时追加 session 分隔线(
_appendSessionMarkers),不轮转不产生.bak - 连续相同行去重:只记首次 +
[DEDUP:N total]计数 - v3.5.9 起:勾选「仅输出有效信息」时不再写 SESSION 分隔线、重复模板折叠(每 20 次一条计数)、三份错误记录合并
⚠️
resources/app/log/(扩展实际写入)≠resources/app/log改错区/(人工搬运的分析副本)。代码只写log/;log改错区/是手动复制用于改错区分析的目录,不随扩展更新,勿混用。
2.3 预期 404 白名单(11 条)
无名杀框架启动时会正常产生一些 404(预加载环境检测的 preload.js、可选背景图/音乐等)。扩展内置 11 条 404 白名单正则,匹配到的 404 静默过滤并附加文件存在性诊断,避免刷屏掩盖真实错误。
2.4 多通道卡死检测
旧版是"三层看门狗",合并版升级为多通道并行检测,覆盖不同卡死场景:
| 通道 | 检测对象 | 阈值 |
|---|---|---|
| 开局看门狗 | 开局 N 秒未触发 game.over | 默认 600s(5-3600 可配) |
| 开局卡死快速失败(v3.6.16) | reload 后 players 已建但游戏未开始(_status 未创建、无弹窗,其余检测全部失效) | 默认 300s(60-900 可配) |
| 双通道心跳 | rAF 循环 + 事件变更 | 心跳阈值默认 30s(5-120) |
| 状态卡死 | 事件名+步骤号持续不变 | 状态超时默认 25s(5-120) |
| chooseCharacter 卡死 | 角色选择 >30s | 30s |
| 事件进度停滞 | 事件引用(name|step)持续不变 | 30s |
| 技能循环 | 10s 窗口内同技能触发 ≥N 次 | N 默认 20(1-100 可配) |
| 弹窗卡死 | 无取消按钮且无合法目标 | 20s |
| Web Worker 心跳 | Worker 心跳停止 | 15s |
看门狗超时设为 <60s 时为"短超时调试模式"(供开发期快速验证)。初始化期间(game.phase 未出现)自动使用更长超时(300s)避免误判。
2.5 无限循环检测
拦截技能的 trigger 流程,每次触发计数,10 秒窗口内同一技能触发超过阈值(默认 20 次,1-100 可配)判定为死循环,自动报错并重启游戏。这是防止 bug 技能无限循环的最后防线(典型如女猎手蕾娜)。
2.6 错误弹窗处理
- alert/confirm 拦截:错误内容 → 写日志 + crash-report + 关闭并重启;Noname 系统对话框("游戏似乎未正常载入"/"是否关闭此扩展")特殊处理——返回 false 拒绝禁用扩展
- 信号分级:强信号(SyntaxError/ReferenceError/TypeError/Uncaught/
xxx.js:行号等)单命中即触发;弱信号(is not defined/is not a function/Cannot read properties 等)需 ≥2 命中 - 防假阳性:DOM 弹窗高度 <250px 且文本 <100 字跳过;纯 UI 词(确定/取消/关闭/是/否等)弹窗跳过
- 弹窗扫描:每秒扫描 ui.dialog 模态框 + DOM 兜底层,发现错误弹窗自动写日志并重启
- 弹窗卡死 combo 检测:有取消按钮但弹窗 >60s 且事件未变,判定卡死
- 温和关门:弹窗卡死先注入
{bool:false, control:"cancel2"}+ game.resume() + 关闭弹窗,观察 5 秒仍卡再 forceReload
2.7 【历史亮点(v3.5.8 引入)】「🔇 仅输出有效信息」过滤器
改错区日志 84% 是噪音(框架自身的 LOG/INFO/DEBUG 刷屏、模板重复、固定弹窗段)。勾选「仅输出有效信息」后:
- LOG/INFO/DEBUG 全丢
- WARN 白名单:只保留关键告警——降级、报错弹窗、自身错误、卡死、恢复、补丁安装超时
- ERROR 黑名单:丢弃噪音——括号检测、翻译差异、扩展已加载、看门狗初始化等(v3.6.16 起「已标记卡死角色 / 120s兜底」移出黑名单,卡死定位信息不再被丢)
- 模板型错误抑制:看门狗/卡死模板块首写全量,之后每 20 次写一条计数(localStorage 持久,跨重启生效)
- crash-report 段裁剪:控制台段只留真实错误行、堆栈 top5 跳过采样器自帧、游戏状态全 N/A 则跳过
- error-chars 签名含
文件:行号:列号:避免不同错误被合并成同一条
🔧 v3.6.16 过滤误杀修复:勾选「仅输出有效信息」后曾误杀卡死诊断必要记录——① crash-report / hang 控制台段只认 JS 错误模板(TypeError 等),而卡死(HANG/WATCHDOG)非 JS 错误,导致补丁状态/防护状态/上一局结果/看门狗配置全部丢失;
MARKDOWN_HASH7cc933279109c66235343d380ba25d39MARKDOWNHASH追加诊断上下文模式(FIX-/补丁/防护安装状态/看门狗初始化/已标记卡死角色/120s兜底/测试池/对局结果/WATCHDOG/HANG)后保留;②_warnKeep追加补丁丢失 / 120s兜底 / 测试池 / 锁超时 / applyGameOverPatch 失败;③_logBlacklist移除已标记卡死角色 / 120s兜底;④ hang 日志 console buffer(_bufNoise)同步保留补丁/防护/看门狗/兜底/卡死标记行,翻译差异/同步等纯噪音仍滤
2.8 v3.5.9 → v3.6.16 后续版本演进要点
日志去重与噪音治理(v3.5.9 → v3.6.5):
- v3.5.9 统一错误签名:
_autotest_errorSig(优先文件:行:列)跨 console.error 堆栈与 unhandledrejection 去重(实测 runtime-errors 276→184);crash-report 全类型签名去重(popup 291→64 文件);会话标记抑制 + 全局模板折叠(每 20 次一条计数);无害错误双通道过滤(audio 缺失等) - v3.6.2 日志精简 O1-O9:跨局持久化去重(localStorage 存 100 个签名 hash)、隔离签名正则 bug 修复、双打印去重、diag 结果 hash 缓存、数字 key 归一(
reading '436275014'→reading '<num>')、backup 假阳性修正等;隔离机制保护:去重只压日志不压隔离 - v3.6.5 console-errors.log 去重:同一 rejection 三监听器(三界圣战 extension.js / 08-guard / 框架 error.js)同错 4 行 → 同签名 60s 窗口吞重复 + 跨局计数行(B1-B4 四项修复)
- v3.6.11 die audio 噪音无条件过滤:
_isHarmlessError与 ERROR 黑名单从配置门控中解放,audio 缺失类框架噪音(原版 Content.die → tryDieAudio 对 player.name undefined 无守卫,68 次/天)不再写入 console-errors.log / runtime-errors.log(控制台仍显示) - v3.6.12 die audio 诊断增强:捕获时附加当前事件链+玩家名,定位到具体死亡角色
FIX 补丁安装可靠性(v3.6.3 → v3.6.14):
- v3.6.3 E1/E3/E4:FIX-B cancel MISS 根因诊断(typeof ui.click 等三值);StepCompiler 事件链定位(unhandledrejection 栈含 StepCompiler 帧时遍历
_status.event链最多 8 级,定位 step 式 content 裸 src 变量错误所属技能);启动后 9 个全局函数自检 - v3.6.4 FIX-B cancel 根因修复:入口捕获的 ui 可能是 undefined 快照 →
_fbResolveUi()每次轮询动态解析window.ui,补丁永不 MISS - v3.6.6 FIX-B 重装轮询解绑旧引用:2s 持续重装优先
window.ui→ 全局 ui → 才 fallback 旧快照;堆栈采样 eval 帧过滤(at eval/<anonymous>/ 扩展自帧统一过滤,定位真实卡死行);HANG 诊断增强(init status/game 快照、主循环多次重启提示) - v3.6.7 HANG 结束态守卫修复:game.over 后框架清空
_status(undefined)导致 eventIdle 假性增长误判 HANG → 结束态/选人界面/初始化间隙不误报,真卡死(rAF 也停)仍触发 - v3.6.8 FIX-1 轮询动态解析:入口捕获 game 快照可能 undefined → 每轮询动态解析
window.game;30s 超时降为每 2s 低频持续重试(FIX-1/5/B 统一模式);lib 不可用噪音降级为 console.log - v3.6.14 诊断补丁安装机制修复:getName 补丁 + 玩家健康检查移到 console override 之后(安装日志/运行时 warn 均落盘,带 ISO 时间戳);轮询 120→600 次 + 300s 后降 2s 低频永久重试;全局 error 监听新增 groupBorder 崩溃事件链诊断(附加事件链+pid,WARN 白名单无条件写入)
无身份角色诊断(v3.6.9 → v3.6.13):
- v3.6.9 getName 诊断增强(isNull 预检):get.character 返回 isNull/无 group 对象时 warn 输出真实角色名(定位 bordergroup 崩溃根因:框架 getName→bordergroup 对无 group/isNull 角色防御缺失)
- v3.6.13 无身份角色诊断全覆盖:getName 诊断去掉 forDialog 限制(正常玩家名显示路径也检测 name 空/未注册/unknown);新增玩家身份健康检查(30s 轮询 game.players);三个诊断(getName name 为空 / get.character 无定义 / 玩家身份异常)加入 WARN 白名单无条件写入 console-warnings.log
名单与测试池(v3.6.0 → v3.6.1):
- v3.6.0 🎯 优先未测试角色(默认开):三级测试池 untested → failed → passed,黑名单角色软排除;非 dev 模式 window.lib 不暴露时通过工厂闭包捕获真实对象(
__autotest_libRef/__autotest_uiRef)+ fs 提取兜底构建三界圣战包映射;空池逐级撤回过滤防卡死 - v3.6.1 名单管理改为 char-list.md 明文编辑:移除游戏内名单 UI,
resources/app/log/char-list.md为权威,启动读取 + 主循环每秒轮询 mtime,保存约 1 秒生效;md 三区结构(手动/灰/黑名单)+ 分组显示 + 自我写入防回环 + fs 降级
性能(v3.6.15):
- 启动诊断异步分片化:三检测(括号 72 文件 4.8s + backup 135 文件 3.2s)同步 fs.readFileSync 遍历全库曾冻结开局主线程数秒 → 改 async 分片让出主线程,UI 全程流畅,检测功能与结果不变;括号检测行号计算 O(n²) → 行号变量跟踪(单文件提速约 3000 倍)
卡死快速恢复与过滤误杀修复(v3.6.16):
- 开局卡死快速失败(P1):reload 后新局卡在选角/开局阶段(players 已建、_status 未创建、无弹窗)时,dialogHang 检测(
_status.auto!==true 直接 return)、状态监控(依赖 s.event)、chooseCharacter 检测(依赖 event.name)全部失效,只能等 3600s 看门狗。新增独立检测:players>0 且 phase 空/N/A 持续超时(默认 300s,可配)→ 完整诊断 + forceReload,卡死恢复 1 小时缩至 5 分钟 - FIX-B cancel 主循环自愈(P2):ui.click.cancel 补丁被界面重建替换后,2s 轮询可能因对象解析不一致漏装 → 主循环 tick 内兜底重装(动态解析 window.ui → 全局 ui)
- Precontent 超时降级(P3):60s 未装 game.over 补丁时区分——game 未就绪(时序噪音)降 info,game 就绪但补丁未装(真失败)warn+立即重试
- MODE 回退(P4):lib.config.mode 早期为空时回退 localStorage
configprefix+"mode"(game.saveConfig 持久化键) - HANG 诊断增强(P5):[hang diagnostics] 增 FIX-B 实时状态(status + live patched/raw),[init status] 增开局卡死计时
- 「仅输出有效信息」误杀修复:
MARKDOWN_HASH7cc933279109c66235343d380ba25d39MARKDOWNHASH追加卡死诊断上下文模式(FIX-/补丁/防护/看门狗/卡死标记/测试池/对局结果/WATCHDOG/HANG)——crash-report/hang 控制台段不再丢弃补丁/防护上下文(卡死非 JS 错误,原正则只认 JS 错误模板);_warnKeep追加 补丁丢失/120s兜底/测试池/锁超时/applyGameOverPatch 失败;_logBlacklist移除 已标记卡死角色/120s兜底;05-loop_bufNoise同步保留补丁/防护/看门狗/兜底/卡死标记行
📌 v3.6.10 为三界圣战技能修复轮(DIY_xuxie / dcxiaoren 全量异步重写、DIY_yingyang trigger.player.forResult 误用、rejieyin chooseControl forResult、lihun2 存储键对齐、reluanwu target 未定义),扩展侧无代码变更,版本号随动;v3.6.9 附带 lihun2 存储键对齐修复(三界版 lihun.content 只写 storage.lihun 单值,原版衍生 lihun2 读 storage.lihun2 markAuto 数组 → 键不匹配
undefined.sortBySeat()崩)。
三、自动测试
3.1 自动对战循环 + game.over 智能处理
游戏开始后 AI 自动托管双方。一局结束触发 game.over,扩展等待设定秒数(默认 5 秒,1-60 可配)后自动 game.reload() 重开,全程无限循环。
v3.6.0 起测试池三级推进(🎯 优先未测试角色,默认开):自动测试优先测三界圣战未测试角色,池顺序 untested →(耗尽)→ failed →(耗尽)→ 全部测完也重测? → passed;黑名单角色软排除(归入 passed,仅重测开启且 untested/failed 耗尽时入池)。池聚焦通过 characterFilter 实现(AI 自动选角 lib.sort.character 无效),池内批窗口 24 个按名单序推进(批内 randomSort 打乱)。关闭时行为与 v3.5.x 一致。
game.over 补丁实例级可靠安装:
- 通过 gameRef 闭包缓存拿稳定引擎实例,防 window.game 被替换
- 补丁未就绪时无限重试(每秒),丢失后自愈重打并输出诊断
- reloading 锁:防止重载期间重复触发,锁超时 60s 自动强清
- 重开后同步预填
continue_name、保活 auto 模式、清除禁用残留
3.2 重载降级链
无论哪种触发路径(卡死/弹窗/看门狗),重启都走五层降级链,逐级尝试直到成功:
game.reload()— 最温和的游戏重载location.reload(true)— 浏览器级强制刷新(带show_splash_off)@electron/remote— 框架级重载location.href = location.href— 导航重载window.close()— 标记 Worker 崩溃,交给外部监控重启
game.reload() 后还有 3s 验证:若 2.5s 内页面未刷新则降级 location.reload。
3.3 崩溃指数退避 + 自禁用
防止游戏反复崩溃进入死循环:
- 指数退避:连续崩溃重启延迟逐步加重
[5, 10, 20, 30]s - 10 分钟窗口:10 分钟内连续崩溃 ≥ 阈值(默认 5 次,1-50 可配)→ 自禁用,停止自动重启
- 看门狗重启豁免:用户主动配置的看门狗重启(WATCHDOG_*)不累计崩溃计数,避免短超时调试误触发自禁用
- 3 分钟自动恢复:禁用/冷却标志超 3 分钟自动清除并重新启用
- 面板提供「🔓 立即恢复」按钮,控制台
__autotest_reenable()也可手动恢复
3.4 弹窗扫描
每秒扫描一次对话框(1s tick,自适应退避):错误弹窗 → 写日志 → 关闭 → 重启;chooseUseTarget 等弹窗无合法目标超时 20s 强制重启。
3.5 角色测试状态追踪
自动测试记录每个角色在测试中的表现:
- 角色参与一局全程无报错 → 该局标记通过(gamesPassed+1)
- 出过报错 → 标记失败,错误次数+1,记录错误签名
- 一个角色连续通过 N 局(默认 2,1-100 可配)→ 标记"已通过"
- 已通过 + 手动跳过角色不出现在下一局候选框
- 报错角色优先排在候选框靠前位置(重写 characterDialog 排序)
- 卡死角色过滤(FIX-D V4):卡死角色的 30 分钟窗口内自动过滤,防反复卡死
双写持久化:localStorage + JSON 文件(checked-chars.json / error-chars.json / checked-packages.json)同时保存,文件系统跨 localStorage 清除保留;原子写入(先写 tmp 再 rename)防写一半崩溃损坏。还记录小包(子包)检查进度。
v3.6.1 起名单以 char-list.md 明文为权威:
- 报错角色自动进灰名单(仅标记)、通过角色(达「通过局数」阈值)自动进黑名单(软排除),由
_autotest_syncAutoLists()从 charStatus 派生(仅三界圣战角色),脏检查后写 md 防每局 IO - md 文件
resources/app/log/char-list.md:启动读取 + 主循环每秒轮询 mtime,编辑保存约 1 秒自动生效并刷新角色过滤;删除 md → 名单重置为空(空=全部可测) - 三区结构:
# === 手动名单(可编辑)/# === 灰名单(自动)/# === 黑名单(自动);# mode: white|black头切换模式(缺省 white);角色行支持中文名(id)/ 纯 id / 纯中文名反查三种格式,自动按# [母包 · 势力]分组显示 - 手动编辑灰/黑名单区会被下次状态同步覆盖;需手动调整请编辑手动名单区,或用控制台
__autotest_resetChar('角色ID')后执行_autotest_syncAutoLists()
3.6 状态面板
- 右上角进度浮窗:
自动测试: 已测 N/M | 通过 X | 报错 Y,点击展开 - 右侧 4 Tab 面板:全部 / ✅通过 / ❌报错 / ⏳待测(默认显示「报错」),列表截断前 50 条
- 底部统计:总角色 / 已追踪 / 通过 / 报错
3.7 堆栈采样 + 状态日志
- 堆栈采样:卡死时每 250ms 采集一次 JS 调用堆栈(最多 80 样本),分析出 Top 5 高频帧写入
hang-*.log,定位卡死发生在哪个函数 - 状态日记:每 3s 记录游戏状态快照(事件名/步骤/嵌套深度/触发技能/卡片),最多 100 条,写入 crash-report 用于复盘
- 三层诊断信息:卡死时输出完整诊断——事件树、状态日记、堆栈 top5、弹窗摘要、控制台缓冲、pause 状态、choose 事件上下文
四、配置系统
4.1 田字格面板
右下角 🔍 悬浮按钮,点击打开 2x2 田字格浮动面板,四分组:
- 📊 诊断开关:启动诊断、技能/导入/翻译/括号/info/backup/part/图片检测、name 空值诊断
- ⚙️ 配置参数:自动测试启用、看门狗、心跳、状态、循环、角色过滤、通过局数、优先/跳过角色、崩溃自禁用、双延迟
- 📋 日志开关:总日志/错误/警告/信息、控制台导出、仅输出有效信息
- 🛠️ 工具/调试:重置日志路径、导出使用说明、自检
- 🔄 运行状态区:禁用状态 / 崩溃计数 / 主循环状态 + 「🔓 立即恢复」按钮
面板由 MutationObserver 防删除保护(被移除自动恢复)。所有配置存 localStorage 精确报错与自动测试_* 前缀,与扩展管理菜单双向同步(打开面板时刷新 checkbox)。控制台也可用 show精确报错与自动测试Panel() / hide精确报错与自动测试Panel()。
4.2 全部配置项(数值范围)
| 配置 | 默认 | 范围 |
|---|---|---|
| 看门狗超时 | 600s | 5-3600 |
| 开局卡死超时(v3.6.16) | 300s | 60-900 |
| 心跳阈值 | 30s | 5-120 |
| 状态超时 | 25s | 5-120 |
| 自动测试延迟(游戏结束重启) | 5s | 1-60 |
| 卡死重启延迟 | 5s | 1-60 |
| 通过局数 | 2 局 | 1-100 |
| 循环阈值 | 20 次 | 1-100 |
| 自禁用阈值 | 5 次 | 1-50 |
另含 20+ 布尔开关(启动诊断、各检测项、日志开关、控制台导出、仅输出有效信息、自动测试启用、心跳检测、状态监控、角色过滤、循环检测、崩溃自禁用、开局自动托管、自检等)+ 2 个字符串配置(优先角色、跳过角色)。
v3.6.0 新增开关:
| 配置 | 默认 | 说明 |
|---|---|---|
| 🎯 优先未测试角色 | 开 | 三级测试池 untested → failed → passed,黑名单软排除;关闭时行为与 v3.5.x 一致 |
| 🔄 全部测完也重测 | 关 | 未测试角色耗尽后已通过角色重新入池;关闭时三界圣战角色交给基础过滤(passed 剔除) |
名单管理(v3.6.1 起):直接编辑 resources/app/log/char-list.md,保存约 1 秒内自动生效(主循环每秒轮询 mtime)。char-list.json / localStorage 降级为回退种子(md 不存在时迁移)。
4.3 全局调试函数(F12 控制台)
| 函数 | 作用 |
|---|---|
__autotest_showStatus() |
显示所有角色测试状态汇总(含优先/跳过列表) |
__autotest_showPanel() |
切换状态面板 |
__autotest_reenable() |
清除禁用/冷却/崩溃计数并 3s 后自动重启 |
__autotest_resetChar('角色ID') |
重置单个角色记录(移出灰/黑名单,配合 _autotest_syncAutoLists() 立即生效) |
__autotest_resetAll() |
重置所有角色记录 |
__autotest_setPriority('角色ID', true/false) |
设置/取消优先测试角色 |
名单控制台速查(v3.6.1 起,写操作会同步回写 md):
| 方式 | 命令/操作 |
|---|---|
| 查看当前名单 | console.table(_autotest_charList.list); console.log("grey:", _autotest_charList.grey, "black:", _autotest_charList.black); |
| 控制台改手动名单并写回 md | _autotest_charList = { mode: "white", list: ["角色ID1", "角色ID2"] }; _autotest_saveCharList(); _autotest_applyCharFilters(); |
| 手动同步灰/黑名单 | _autotest_syncAutoLists(); |
| 重置某角色(移出灰/黑名单) | __autotest_resetChar("角色ID"); _autotest_syncAutoLists(); |
| 一键重置全部状态(内存+localStorage+文件+名单) | __autotest_resetAll() |
| 清空名单 | _autotest_charList = { mode: "white", list: [], grey: [], black: [] }; _autotest_saveCharList(); _autotest_applyCharFilters(); |
角色 ID 获取:Object.keys(_autotest_getSanjieAll());中文名反查 lib.translate 自动匹配。
另含诊断函数:validateExtension / validateSingleFile / 9 个 checkXxx / levenshtein(a,b) / getLogPath / setLogPath / checkLogNoise。
五、界面展示
游戏界面右下角有该面板就是生效了,点右下角的放大镜即可收齐面板。不过该扩展主要是自动挂机测试时才打开,所以一般不用收起面板。
-

-
如下图,在游戏里 ctrl+shift+I 打开控制台后,能看到比官方控制台更详细的日志。
我把每个技能 js 文件切分得较细,最大只有 100KB ,便于 ai 检测是哪个文件的哪行有问题,易于精准修复,特别是易于修复格式问题。
如果 js 文件太大,如 3-5MB ,当出现括号或逗号不闭合的格式问题时,那以当前的 ai 甚至检测不出来是哪里有问题。
在人肉写程序时代,所有信息汇总到一个 js 可以方便地 ctrl+f 查找,但时代变啦,以当前 ai 的智力,还是得拆分到合适的文件大小,才便于 ai 处理。
-

-

-
如下图,当游戏有错误时,会在 resources/app/log/ 目录生成日志文件,错误弹窗自动写入 error-popup.log 并记录角色名+文件名,在 ai 时代便于 ai 阅读。
而以往弹窗报错时,弹窗无无法复制黏贴,需要开发者肉眼去看,如需要信息文档,则需要到控制台复制,在当下 ai 时代成为痛点。
-

-
如下图,我现在是完全不看日志,让 ai 直接读和修就能解决报错。

-
以往社区各大佬做的无名杀教程我做做成知识库放在 skills 里,每次修完报错也会汇总到 skills 里,ai agent 会随着 skills 进化而进化,所以我现在才能完全不看报错就能直接让 ai 修,我的skills 也放在网盘链接里了。
-

六、版本演进(v3.2.0 → v3.6.16)
| 版本 | 新特性 |
|---|---|
| v3.2.0 | 合并为单扩展;模块化 src/10 模块;自身错误计数+降级模式(1 分钟 ≥3 次降级);双延迟配置;console.error 递归守卫 |
| v3.3.0 | 面板田字格 2x2 四分组;配置双入口同步;崩溃指数退避 [5,10,20,30]s;自身错误日志 self-errors.log |
| v3.4.0 | 运行时模块加载(extension.js 35 行引导);零构建;DevTools sourceURL 可调试 |
| v3.4.1 | game.over 补丁状态追踪;主循环死锁修复;降级标志自动恢复;game.reload 三层降级验证;FIX 补丁安装可观测性(4 标志变量);noReload 标志同步 |
| v3.5.1 | 去 vm 依赖(已废弃,被 v3.5.2 推翻) |
| v3.5.2 | vm + eval 双路径;单模块独立 try/catch |
| v3.5.3 | 修复 arguments.callee 导致 FIX 补丁静默失败 |
| v3.5.5 | 旧目录名「精确报错与自动测试」残留自动迁移清理 |
| v3.5.7 | 纯 ESM 入口 + fetch/eval 加载,零 Node.js 依赖,修复 Electron HTTP 加载兼容 |
| v3.5.8 | 「仅输出有效信息」过滤器——改错区日志 84% 噪音,LOG/INFO/DEBUG 全丢、WARN 白名单、ERROR 黑名单、模板每 20 次计数、crash-report 段裁剪、error-chars 签名含文件:行号:列号 |
| v3.5.9 | 统一错误签名跨 type 去重(runtime-errors 276→184);会话标记抑制;全局模板折叠(159→~9);无害错误双通道过滤;crash-report 全类型签名去重(popup 291→64 文件) |
| v3.6.0 | 🎯 优先未测试角色(三级测试池,默认开);「🔄 全部测完也重测」(默认关);名单管理面板;三界圣战识别(工厂闭包捕获 + fs 提取兜底);空池逐级撤回过滤;过滤恢复 |
| v3.6.1 | 名单管理改为 char-list.md 明文编辑(移除游戏内名单 UI);md 三区结构(手动/灰/黑)+ 分组显示 + 自我写入防回环 + fs 降级 |
| v3.6.2 | 日志精简 O1-O9(跨局持久化去重、隔离签名 bug 修复、数字 key 归一、backup 假阳性修正等);隔离机制保护 |
| v3.6.3 | FIX-B cancel MISS 根因诊断;StepCompiler 事件链定位(8 级);启动后 9 全局函数自检 |
| v3.6.4 | FIX-B cancel 根因修复(动态解析 window.ui);FIX-B MISS 根因 warn 进白名单 |
| v3.6.5 | console-errors.log 去重(同错 4 行 → 同签名 60s 吞重复 B1-B4);getName 诊断补丁(forDialog 空 name 检测) |
| v3.6.6 | 堆栈采样 eval 帧过滤;FIX-B 重装轮询解绑旧引用;HANG 诊断增强;console buffer 噪音过滤(19 条正则);results 日志降频 |
| v3.6.7 | HANG 结束态守卫修复(_status 清空不再误报;真卡死仍触发) |
| v3.6.8 | FIX-1 chooseCharacter 轮询动态解析;FIX-5 超时降级(2s 低频持续重试);lib 不可用噪音降级;warn 白名单 |
| v3.6.9 | getName 诊断增强(isNull 预检,定位 bordergroup 崩溃角色);lihun2 存储键对齐修复(三界侧) |
| v3.6.10 | 三界圣战技能修复轮(扩展侧无代码变更,版本号随动):DIY_xuxie / dcxiaoren 全量异步重写、DIY_yingyang forResult 误用、rejieyin chooseControl forResult、lihun2 存储键对齐、reluanwu target 未定义 |
| v3.6.11 | die audio 噪音无条件过滤(68 次/天框架噪音不再写错误日志,控制台仍显示) |
| v3.6.12 | die audio 诊断增强(附加事件链+玩家名,定位具体死亡角色) |
| v3.6.13 | 无身份角色诊断全覆盖(getName 去掉 forDialog 限制;玩家身份健康检查 30s 轮询;三诊断进 WARN 白名单无条件写入) |
| v3.6.14 | 诊断补丁安装机制修复(getName 补丁移至 console override 后;轮询 120→600 次 + 300s 后 2s 低频永久重试;groupBorder 崩溃事件链诊断) |
| v3.6.15 | 启动诊断异步分片化(消除开局主线程冻结,UI 全程流畅;括号检测 O(n²) → 行号变量跟踪,单文件提速约 3000 倍;三函数返回 Promise) |
| v3.6.16 | 开局卡死快速失败(players 已建但 _status 未创建时 dialogHang/状态监控/chooseCharacter 检测全部失效,只能等 3600s 看门狗 → 新增独立检测默认 300s 快速重启);FIX-B cancel 主循环自愈(ui.click.cancel 被界面重建替换后 2s 轮询漏装 → tick 内兜底重装);Precontent 超时噪音降级(game 未就绪=时序噪音降 info,就绪未装=真失败 warn+重试);MODE 回退读取(lib.config.mode 早期为空时回退 localStorage);HANG 诊断增强(FIX-B 实时状态 status+live);「仅输出有效信息」误杀修复(_isRealErrorLine 追加卡死上下文模式、_warnKeep 追加 5 项、_logBlacklist 移除 2 项、_bufNoise 同步) |
七、对扩展作者/官方项目的价值
对扩展作者:
- 写角色代码 → 开游戏自动跑 9 项诊断,语法错误精确到文件+行号+列号+原因,不用反复开关游戏试错
- 诊断面板全绿可快速确认代码基础正确
- 写了死循环技能 → 循环检测 20 次后自动重启,不用强关进程
- 看门狗在代码 bug 卡住时自动解挂
- 把每个技能 js 文件切分得较细(最大只有 100KB),便于 AI 检测是哪个文件哪行有问题、精准修复格式问题。文件太大(3-5MB)时括号/逗号不闭合的格式问题连 AI 都检测不出来
- AI 时代工作流:完全不用看日志,让 agent 直接读日志文件就能修——日志含角色名、文件名、错误时间、堆栈、错误签名
对官方项目:
- 所有扩展作者的报错统一拦截落盘,反馈问题直接发日志文件即可
- 常见错误类型被量化(什么错误最多、哪个文件出错最多),指导框架加防御
- 诊断结果写入 JSON(
v17-diag-results.json),可被外部脚本解析,构成自动化质量门控:提交代码 → 自动诊断 → 解析 JSON → 判定 - 数百角色批量回归测试的基础设施,卡死检测同时暴露框架本身的模式 bug
八、限制
- 诊断只能发现代码层面的问题(语法、缺失、污染),无法发现逻辑错误(技能写错了但语法正确)
- 自动测试只能测试 AI 能触发的技能效果;需要玩家手动选择的技能,AI 不一定能选出最优解,某些分支可能覆盖不到
- 角色候选框过滤基于多局统计,不是每局必测所有角色
- 所有功能依赖无名杀扩展系统的加载时序。扩展自身加载失败(被禁用、文件损坏)时全部失效
九、总结
合并版扩展把「发现问题」和「暴露问题」两条链路合成一条完整的开发工具链:
代码写完 → 自动 9 项语法诊断 → 自动 AI 对战测试 → 多通道卡死检测自动解挂/重启 → 日志落盘(仅输出有效信息)→ agent 读日志自动修复 → 重新验证
开发过程中完全不需要人工盯屏:v3.5.8 的「仅输出有效信息」过滤器让日志干净到 AI 可以直接读,v3.6.2/v3.6.5 的去重与跨局持久化进一步压噪,多通道卡死检测 + 崩溃退避自禁用让无人值守测试可以安全长期运行,角色状态追踪(v3.6.1 起名单 md 明文可编辑)让数百角色批量测试按"通过/报错/待测"收敛,v3.6.15 异步分片让开局诊断不再冻结主线程,v3.6.16 开局卡死快速失败让卡死恢复从 1 小时缩至 5 分钟、过滤规则不再误杀卡死定位信息。
当前版本:合并版 v3.6.16(单扩展「自动测试与精确报错」),个人 ai 开发,问我代码问题我也不懂,抱歉- -。。。
v3.6.16 重点:开局卡死恢复从 1 小时缩至 5 分钟(快速失败+完整诊断),FIX-B 补丁自愈,过滤规则不再误杀卡死定位信息(补丁状态/防护状态/卡死角色/120s兜底全保留)。

