javascript - NW.js 未正确清除缓存

标签 javascript module nw.js

环境

问题

新窗口从父窗口打开。 Webchimera 模块已加载,但由于其 window 对象指向父窗口而崩溃。那是因为 NW.js caches its modules

家长

<div id="chimera_container"></div>

...
var gui; // global variable for parent object
var wjs; // global variable for parent object
....
gui = require('nw.gui');
wjs = wjs = require('wcjs-player');
....
video_emit = gui.Window.open('video_emit.html',{
    "window" : {
        "focus": true,
        "toolbar": true,
        "frame": true,
        "width" : 640,
        "height" : 640
    },
    "dependencies": {
        "require-new": "^1.1.0",
        "wcjs-player": "^0.5.6"
    },  
});

video_emit 窗口

<div id="vid"></div>

....
var wjs; // global variable for new window object
wjs = require('wcjs-player');  
video_container = new wjs("#vid"); <---- CRASHES **** !!!

node_modules\wcjs-player\index.js第82行中我添加了

console.log(window.document);

家长控制台输出

#document
...
<div id="chimera_container"></div>

video_emit 控制台输出

#document
...
<div id="chimera_container"></div>  

尝试过的解决方案

手动清除缓存

video_emit 窗口上请求'wcjs-player'模块之前调用函数clearRequiredModules

var clearRequiredModules = function(){
    // clear wcjs-player from require cache to force new load
    var clearModules = [
        "wcjs-player",
        "jquery" // https://github.com/jaruba/wcjs-player/issues/38
    ];
    for (var i in clearModules) {
        for (var module in global.require.cache) {
            if ( global.require.cache.hasOwnProperty(module) 
                 && module.indexOf(clearModules[i]) > -1
                )
                delete global.require.cache[module];
        }
    }
};

不工作。同样的问题,就好像我根本没有清除一样。仍然指向父窗口对象。

使用 require-new 模块

这段代码没有科学性,我加载模块并在 video_emit 窗口中使用它。

var req_new = require('require-new');
wjs = req_new('wcjs-player');

仍然崩溃。

<小时/>

我知道将 ** new-instance: true** 添加到 gui.Window.open父窗口可以解决此问题,但我需要父窗口和新窗口通过 global 变量进行通信,仅当它们位于同一渲染上时才可用。

------------------------ 解决方案 -------------- --------------------------

单独清除缓存不起作用,为了使其有效,必须从窗口完成以下操作。

video_emit = gui.Window.open('video_emit.html',{
    ...
});
video_emit .on('document-start', function() {
    video_emit .reload(3);
});

在子窗口中:

clearRequiredModules(); //Same code as protrayed above
wjs = require('wcjs-player');  
video_container = new wjs("#vid");

问题

注意,这样做会渲染全局变量(用于在窗口之间共享信息的变量,无用。因此,这与在父窗口中执行此操作相同(而不是清除子窗口中的缓存):

video_emit = gui.Window.open('video_emit.html',{
        "window" : {
            "focus": true,
            "toolbar": true,
            "frame": true,
            "width" : 640,
            "height" : 640
        },
        "new-instance" : true // <---- That right there
    });

此问题的一个可能的解决方案是使用localStorage来代替,在窗口之间进行通信。

最佳答案

wcjs-player严重依赖于能够访问 window.documentNW.js v0.12.3 有一个错误,会泄露父级的 window子窗口对象。

我已经看到这会产生许多问题,包括将所有错误和日志推送到主窗口,并且它总是会破坏依赖于 window 的所有模块。 .

解决此问题的方法是在创建子窗口后对其进行 node.js 级别的重新加载。

Proof of Concept

Discussion

用法示例:

var new_win = require('nw.gui').Window.open('index.html');
new_win.on('document-start', function() {
    new_win.reload(3);
});

注释:

  • 还应该提到的是,这是一个 NW.js具体问题,Electron新窗口不存在此问题。

  • 由于这是高级页面重新加载,global对象也将被清除,将信息传递到此新窗口的替代解决方案是使用 localStorage (即持久性),或者用于更复杂的 websocket 需求。

关于javascript - NW.js 未正确清除缓存,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36093215/

相关文章:

javascript - 从服务器端发送消息到React前端(NodeJS)

java - 后端模块需要来自表示层的 URL - 如何避免循环依赖?

json - 在 mac 上显示我的工具栏 (Node-Webkit)

javascript - 为表 'tbody' 产生水平滚动

javascript - CSS 跨度 :hover doesn't work in IE but works in Firefox

php - 如何使用 php 或 javascript 编写一个函数来确定 16 位整数的人口数?

performance - Fortran 模块性能

模块中的 python 导入类抛出 ImportError

desktop-application - 桌面 Web 应用程序中的丰富 HTML 托盘菜单

javascript - 如何在 nw.js 中开始使用 angular2