bacground.js
chrome.tabs.create({url: "http://www.google.com", "active":true}, function(tab) {
console.log(tab.id);// 315
chrome.tabs.sendMessage(tab.id, {greeting: "hello"}, function(response) {
console.log(response.farewell);
});
});
contentscript.js
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"});
});
});
日志:
Port: Could not establish connection. Receiving end does not exist.
如何解决?
答案 0 :(得分:2)
这个错误似乎正在发生,因为当后台脚本发送消息时,内容脚本尚未注入页面。因此,“接收端不存在。”
我假设(因为我没有超过50个代表能够对您的问题发表评论并首先澄清这一点,所以如果我错了就纠错我)在manifest.json文件中,您指定它通过以下方式:
"content_scripts": [{
"matches": ["*://xyz.com/*"],
"js": ["contentscript.js"]
}]
如果您确实是如何注入内容脚本,那么您需要知道内容脚本仅在DOM完成呈现后才会被注入。 (在以下链接中搜索“run_at”:http://developer.chrome.com/extensions/content_scripts.html)这意味着当您从后台脚本发送该消息时,内容脚本仍在“加载”。
好消息是,您可以通过向manifest.json文件中的content_scripts参数添加第三个键值对来指定何时应加载内容脚本,如下所示:
"content_scripts": [{
"matches": ["*://xyz.com/*"],
"js": ["contentscript.js"],
"run_at": "document_start"
}]
这告诉扩展名你想在构造DOM或运行任何其他脚本之前注入contentscript.js(即尽早)。
如果上述技术仍然给你相同的错误,那表明即使document_start还不够早。在这种情况下,让我们完全考虑另一种方法。您目前要做的是让后台脚本连接到内容脚本。为什么不将内容脚本连接到后台脚本而不是成功注入页面?后台页面始终正在运行,因此可以保证能够从内容脚本接收消息而不会抱怨“接收端不存在”。您将如何做到这一点:
在background.js中:
chrome.runtime.onConnect.addListener(function(port) {
console.log("background: received connection request from
content script on port " + port);
port.onMessage.addListener(function(msg) {
console.log("background: received message '" + msg.action + "'");
switch (msg.action) {
case 'init':
console.log("background script received init request
from content script");
port.postMessage({action: msg.action});
break;
}
});
});
在contentscript.js中:
var port_to_bg = chrome.runtime.connect({name: "content_to_bg"});
port_to_bg.postMessage({action: 'init'});
port_to_bg.onMessage.addListener(function(msg) {
switch (msg.action) {
case 'init':
console.log("connection established with background page!");
break;
}
}
随意提出更多问题以便澄清!我很想知道第一种方法是否奏效。如果没有,第二种方法肯定会赢。