问题描述
使用以下 (GreaseMonkey) 用户脚本,我尝试查找(并稍后访问)一个 JavaScript 对象(即“Blazor”):
// ==UserScript==
// @name Test
// @version 1
// @grant none
// @run-at document-end
// ==/UserScript==
window.addEventListener ("load",doStuff);
function doStuff() {
setTimeout(function() {
console.log("window.hasProperty('Blazor'): " + window.hasOwnProperty("Blazor"));
console.log("'Blazor' in window: " + ('Blazor' in window));
console.log(window);
},2000);
}
当我运行脚本(即重新加载页面)时,我在 Firefox 的控制台中得到以下输出:
因此无法找到 window.Blazor
。但是,当我检查(单击)window
对象时,我可以看到 Blazor
属性:
在控制台中调用 'Blazor' in window
也会返回 true
。
为什么 window
的这个属性(还?)不可用,我怎样才能找到和访问它?
更新:
基于 madalinivascu's answer,我尝试了以下操作:
function doStuff() {
console.log("<doStuff>");
var promise = new Promise(function(resolve,reject) {
var interval = setInterval(function() {
console.log("checking for Blazor");
if ('Blazor' in window) {
console.log("Blazor found");
clearInterval(interval);
resolve(window.Blazor);
}
},1000);
});
promise.then(successCallback,failureCallback);
console.log("</doStuff>");
}
function failureCallback(error) {
console.log("failure: " + error);
}
function successCallback(result) {
console.log("success: " + result);
}
结果如下:
所以检查 Blazor 的函数被无限期调用,但没有成功找到它。
解决方法
解决方案是使用 script injection,因为 GreaseMonkey 脚本在另一个上下文中运行,从而获得另一个 window
对象。
更准确地说,将函数 doStuff
附加到 that answer (addJS_Node
) 中定义的 addJS_Node (null,null,doStuff);
而不是使用 window.addEventListener ("load",doStuff);
有效。
您可以使用 setInterval 和 promise 来测试变量
function doStuff() {
var promise = new Promise(function(resolve,reject) {
var interval = setInterval(function() {
if(window.Blazor || window.hasOwnProperty('Blazor')) {
clearInterval(interval);
resolve(window.Blazor);//rezolve promise with the balzor variable
}
},200);//check every 200ms for the blazor variable
})
promise.then(function(blazor) {
console.log(blazor);//do other stuf with the blazor variable
})
}