进行 chrome 扩展和 chrome.runtime.onMessage 没有收到消息

Making chrome extension and chrome.runtime.onMessage isn't receiving the message

这是我的活动页面中的代码:

chrome.runtime.onInstalled.addListener(function (){
    chrome.contextMenus.create
        ({
            "title": "Test",
            "contexts": ["all"],
            "id": "menu"
        });
    chrome.contextMenus.create
        ({
            "title": "Dummy",
            "contexts": ["all"],
            "id": "dummy",
            "parentId": "menu"
        });
});

chrome.contextMenus.onClicked.addListener(onClickHandler);

function onClickHandler (info, tab) {
    if(info.menuItemId == "dummy"){
        chrome.tabs.sendMessage(tab.id, {greeting: "hello"}, function(response) {
            console.log(response.farewell);
        });  
    }
}

这里是我的内容脚本中直接来自 chrome 消息传递文档的代码:

chrome.runtime.onMessage.addListener(
  function(request, sender, sendResponse) {
    console.log(sender.tab ?
                "from a content script:" + sender.tab.url :
                "from the extension");
    if (request.greeting == "hello")
      sendResponse({farewell: "goodbye"});
  });

事件页面中的onClickHandler被触发了,但是好像sendMessage方法没有起作用。 onMessage 侦听器没有收到任何信息,因此它不会向控制台记录任何内容,甚至不会发送响应。这会导致原始 sendMessage 回调抛出异常,因为 response.farewell 甚至没有定义。有谁知道为什么代码似乎不起作用。

错误:

Error in event handler for (unknown): TypeError: Cannot read property 'farewell' of undefined

事实证明,内容脚本或活动页面中的代码没有问题。

本帖:Chrome extension Content Script not loaded until page is refreshed

帮助我意识到内容脚本不是 运行 因为我正在测试它的网站,而且因为它不是 运行 它显然无法监听任何事件.

对于其他遇到问题的人,我的问题是尝试使用 chrome.runtime API.

向内容脚本发送消息

为了向内容脚本发送消息,您必须使用 chrome.tabs,而不是像这样:chrome.tabs.sendMessage(tabId, message, options, response):

Sending a request from the extension to a content script looks very similar, except that you need to specify which tab to send it to.

Sends a single message to the content script(s) in the specified tab, with an optional callback to run when a response is sent back.

API 文档:https://developer.chrome.com/extensions/tabs#method-sendMessage

我遇到了发送消息的工作代码停止工作的问题。

我意识到问题出在标签上。打开了多个 windows 浏览器,但我缺少 activeWindow 属性来获取活动标签。

以下代码片段对我有用。

const fetchTabs = () => {
 return new Promise((resolve, reject) => {
  chrome.tabs.query({ active: true, currentWindow: true }, resolve);
 });
};

注意 activeWindow 属性。