将数组变量从background.js传递到content.js

Pass array variable from background.js to content.js

本文关键字:js content background 数组 变量      更新时间:2023-09-26

我真的很难从我的background.js传递一个数组到我的content.js。在开始之前,我将列出我的脚本。

manifest.json

{
"manifest_version": 2,
"name": "Tab Highlighter",
"description": "Highlight already open tabs in a google search query",
"version": "1.0",
"content_scripts":[
{
  "matches": [ "http://www.google.com/*", "https://www.google.com/*", "https://*/*", "http://*/*" ],
  "js": ["content.js"],
  "run_at": "document_end"
}
],
"background": {
    "persistent": false,
    "scripts": ["background.js"]
 },
 "permissions":[ "tabs" ]
}

content.js

chrome.runtime.sendMessage({data: "getTabs"}, function(response) {
var tabs = response.data;
    if(!tabs) {
        console.log("No Tabs could be found!!");
    }
    else {
        console.log("TABS FOUND");
        console.log(tabs);
        for(var k = 0; k < tabs.length; k++) {
            console.log(tabs[k]);   
        }
        var links = document.getElementsByTagName("a");
        for(var i = 0; i < links.length; i++) {
            var link = links[i];
            var real_href = link.getAttribute("href");
            if(real_href) {
                //console.log(real_href);
                for(var j = 0; j < tabs.length; j++) {
                    if(i == 0) {
                        console.log("tab open: ", tabs[j]);
                    }
                    if(real_href == tabs[j]) {
                        console.log("duplicate found: ", real_href);
                        link.innerHTML = "Already Open";
                    }
                }
            }
        }
        console.log("End printing tabs");
    }
});

background.js

chrome.runtime.onMessage.addListener(
function(request, sender, sendResponse) {
if(request.data === "getTabs"){
var fourmTabs = new Array();
chrome.tabs.query({}, 
        function(t) {
            for (var i = 0; i < t.length; i++) {
                fourmTabs[i] = t[i].url;
            }
            // Moved code inside the callback handler
            for (var i = 0; i < fourmTabs.length; i++) {
                if (fourmTabs[i] != null)
                    console.log(fourmTabs[i]);
                else {
                    console.log("??" + i);
                }
            }
        }
    );
    if(!fourmTabs) {
        console.log("Tabs could not be generated!!");
    }
    else {
        for(i = 0; i < fourmTabs.length; i++) {
            console.log(fourmTabs[i]);
        }
    }
    sendResponse({data: fourmTabs});
    //return true;    used to see if this was asynchronous or not
}
});

更新background.js

chrome.runtime.onMessage.addListener(
function(request, sender, sendResponse) {
if(request.data === "getTabs"){
var fourmTabs = new Array();
chrome.tabs.query({}, 
        function(t) {
            for (var i = 0; i < t.length; i++) {
                fourmTabs[i] = t[i].url;
            }
            // Moved code inside the callback handler
            for (var i = 0; i < fourmTabs.length; i++) {
                if (fourmTabs[i] != null)
                    console.log(fourmTabs[i]);
                else {
                    console.log("??" + i);
                }
            }
            if(!fourmTabs) {
                console.log("Tabs could not be generated!!");
            }
            else {
                for(i = 0; i < fourmTabs.length; i++) {
                    console.log("fourmtabs is here: ", fourmTabs[i]);
                }
            }
            sendResponse({data: fourmTabs});
        }
    );
}
});

目前,从content.js打印的只是一个空数组,我相信。它显示为"[]"(没有引号)。每当我在background.js中将sendresponse更改为{data: "Test"}时,content.js就会打印出我所期望的内容,然后是Test,然后是每个字母。希望一切都在这里,我已经尝试了很多事情来让它工作。我还有一个小时才起床,所以如果我没有回复,我明天就回来。谢谢你的帮助!

我在脑海中看到的是这样的。页面加载完成后,将运行content.js。content.js发送消息到background.js,并得到它的响应(我有麻烦的数组)。然后,从页面中获取所有链接,并检查页面上的任何链接是否与在另一个选项卡中打开的任何页面相等。然后我想改变这个链接的风格是一个不同的颜色或一些东西,以表明它已经打开。我计划只在谷歌搜索上工作,我认为我会通过摆脱manifest.json的"matches"部分中的最后两个元素来做到这一点。

另一个快速编辑:我试图遵循这种问题,然而,我被卡在发送数组从background.js到content.js

如果您需要更多的信息,请告诉我

sendResponsefourmTabs被填充之前被调用,所以当你发送它时它仍然是一个空白数组。从if(!fourmTabs)sendResponse调用的所有代码都应该移动到tabs.query的回调中。

编辑:您需要在addListener回调的最后几行之前添加return true;—最后三行应该看起来像:

return true;
}
});

这不是特别好的文档,我不确定我解释得很好,但是因为tabs.query是异步的,你需要在得到响应之前运行它,用于消息传递的端口在tabs.query完成之前被关闭,因此在sendResponse实际上被调用之前,所以内容脚本认为它得到了一个非响应。

主要来自这个chrome扩展线程,具有类似但不同的场景(在调用sendResponse之前等待AJAX调用完成)

您是否尝试过存储值并使用chrome存储方法调用它?我不确定这是否是最好的方法,但我确信这将打开交叉沟通。下面是一个例子:

var setArray = [1, 2, 3, 5, [1, 2, 3]];
chrome.storage.local.set({'storageObjectName': setArray}, function () {
    /* optional callback */
});

从你的其他脚本

chrome.storage.local.get('storageObjectName', function (data) {
    console.log(data);
});

结合两者的例子:

var setArray = ['my new data']; /* setting array in script 1 */
chrome.storage.local.set({'storageObjectName': setArray}, function (){
    chrome.storage.local.get('storageObjectName', function (data) {
        otherScriptFunction(data); /* call your other function from script 2 */
    });
});