某个同事说,现有的Electron
内置浏览器在F12
的性能测试里,发现JS文件无法定位,或者定位错误,问我怎么办。
看了下,在MacOS
中是没问题的,只有Windows
下莫名其妙有。但我就这点儿能耐,又能怎么办?
只能升级Electron
试试呗。于是,将electron
的依赖包从v31
升级到最新稳定版本v32
。
开始以为挺顺利,没想到看到项目的网络里报错了:
控制台也是提示本地资源文件加载失败:
这就有点儿让人懵逼了。
我下意识以为是浏览器改变了什么安全策略,但追踪后发现浏览器中直接加载的file:///
是没问题的,只是WebAssembly(wasm)
加载的有毛病。
为什么有的资源会用
wasm
加载呢?原因是这些资源进行了加密,用wasm
进行解密,可以有效增加外界破解难度。
再看了下,Electron v31
用的126
的Chromium
内核,v32
用的是128
的内核(在这里看Chromium
内核版本)。
但其实在浏览器里是无法直接加载本地文件的,这个功能只有Electron
或Tauri
这种App
才能做到,所以一时无法确定是浏览器的锅,还是Electron
的锅。
走投无路之际,我问了下GPT
:
GPT
说的这句看着是有道理的:
在新版本的 Electron 中,可能对
file://
或其他自定义URL scheme
的支持做了一些修改。例如,WebAssembly
加载本地文件可能涉及到资源路径的解析,而 Electron 132 版本可能对非标准的 URL scheme 进行了更严格的验证,导致无法正确识别file://
。
下面第三条其实我开始Google
搜索见到过,确实可以拦截到file:///
的文件请求:
但给的示例是用的interceptFileProtocol
,导致所有file
请求都报错了:
protocol.interceptFileProtocol('file', (req, callback) => { const url = req.url.substr(8) callback(decodeURI(url)) })
现在修改成registerFileProtocol
,试上一下:
protocol.registerFileProtocol('file', (request, callback) => { const filePath = request.url.replace(/^file:\/\//, '') callback({ path: filePath }) })
居然好了!
由于这个API已经被提示不推荐使用:
所以又找了下替代方案,这样看起来优雅多了:
protocol.handle('file', (req) => { return net.fetch(req.url, { bypassCustomProtocolHandlers: true }) })
问题解决了,但回到我们开始的问题,到底是Chromium
的锅,还是Electron
的锅呢?
我还是不确定。去掉这段代码,尝试将Electron
降到v32
的第一个版本32.0.0
,仍然是报错;降到v31
的最后一个版本31.6.0
,是没问题的。
看Electron v32
的发版日志里,破坏性变更仅有移除上传文件File
的不标准的path
:
而看Chromium
v127 的发版日志 和 v128 的发版日志也没看出个所以然来,有安全层面的更新,不清楚是否有关。希望有大佬解答下。
搞客户端开发有时候不得不升级依赖,但一升级又可能有这样那样的问题,无奈。