84669 人学习
152542 人学习
20005 人学习
5487 人学习
7821 人学习
359900 人学习
3350 人学习
180660 人学习
48569 人学习
18603 人学习
40936 人学习
1549 人学习
1183 人学习
32909 人学习
我正在编写一个 Chrome 扩展程序,并尝试在 popup.html 文件中单击按钮后立即在当前网页上覆盖
当我从 popup.html 中访问document.body.insertBefore方法时,它会覆盖弹出窗口上的
document.body.insertBefore
我是否必须在background.html 和popup.html 之间使用消息传递才能访问网页的DOM?我想在 popup.html 中完成所有操作,并且如果可能的话也使用 jQuery。
使用编程注入来添加该 div 的扩展弹出脚本的一些示例。
不要忘记在manifest.json中添加权限,请参阅其他答案以获取更多信息。
简单调用:
(async () => { const [tab] = await chrome.tabs.query({active: true, currentWindow: true}); await chrome.scripting.executeScript({ target: {tabId: tab.id}, func: inContent1, }); })(); // executeScript runs this code inside the tab function inContent1() { const el = document.createElement('div'); el.style.cssText = 'position:fixed; top:0; left:0; right:0; background:red'; el.textContent = 'DIV'; document.body.appendChild(el); }
注意:在 Chrome 91 或更早版本中,func:应为function:。
func:
function:
使用参数调用并接收结果
需要 Chrome 92,因为它实现了args。
args
示例1:
res = await chrome.scripting.executeScript({ target: {tabId: tab.id}, func: (a, b) => { return [window[a], window[b]]; }, args: ['foo', 'bar'], });
示例2:
(async () => { const [tab] = await chrome.tabs.query({active: true, currentWindow: true}); let res; try { res = await chrome.scripting.executeScript({ target: {tabId: tab.id}, func: inContent2, args: [{ foo: 'bar' }], // arguments must be JSON-serializable }); } catch (e) { console.warn(e.message || e); return; } // res[0] contains results for the main page of the tab document.body.textContent = JSON.stringify(res[0].result); })(); // executeScript runs this code inside the tab function inContent2(params) { const el = document.createElement('div'); el.style.cssText = 'position:fixed; top:0; left:0; right:0; background:red'; el.textContent = params.foo; document.body.appendChild(el); return { success: true, html: document.body.innerHTML, }; }
// uses inContent1 from ManifestV3 example above chrome.tabs.executeScript({ code: `(${ inContent1 })()` });
使用参数调用并接收结果:
// uses inContent2 from ManifestV3 example above chrome.tabs.executeScript({ code: `(${ inContent2 })(${ JSON.stringify({ foo: 'bar' }) })` }, ([result] = []) => { if (!chrome.runtime.lastError) { console.log(result); // shown in devtools of the popup window } });
此示例使用inContent函数的代码自动转换为字符串,这样做的好处是 IDE 可以应用语法突出显示和 linting。明显的缺点是浏览器会浪费时间来解析代码,但通常不到 1 毫秒,因此可以忽略不计。
inContent
问题:扩展页面(弹出窗口、选项、MV2 中的背景页面等)与网页分离,它们有自己的 DOM、document、window 和chrome-extension://URL。
document
chrome-extension://
解决方案:使用内容脚本访问网络页面或与其内容交互。
manifest.json:
"content_scripts": [{ "matches": ["*://*.example.com/*"], "js": ["contentScript.js"] }],
它将在页面加载时运行一次。之后,请使用消息传递。
警告!它不能发送 DOM 元素、Map、Set、ArrayBuffer、类、函数等。它只能发送与 JSON 兼容的简单对象和类型,因此您需要手动提取所需的数据并将其作为简单数组或对象传递。
ManifestV3:
在扩展脚本(如弹出窗口)可根据需要将内容脚本/函数注入选项卡。
此方法的结果是内容脚本中的最后一个表达式,因此可用于提取数据。数据必须与 JSON 兼容,请参阅上面的警告。
manifest.json 中所需的权限:
权限
“脚本”
"activeTab"
如果理想情况不可能,请将允许的站点添加到manifest.json 中的host_permissions:
host_permissions
“*://*.example.com/”以及您想要的任何其他网站。
“*://*.example.com/”
" " 或"*://*/"这些会将您的扩展程序置于 Chrome 网上应用店中超慢审核队列中由于广泛的主机权限。
" "
"*://*/"
ManifestV2 与上述的差异:
使用编程注入来添加该 div 的扩展弹出脚本的一些示例。
清单V3
不要忘记在manifest.json中添加权限,请参阅其他答案以获取更多信息。
简单调用:
注意:在 Chrome 91 或更早版本中,
func:
应为function:
。使用参数调用并接收结果
需要 Chrome 92,因为它实现了
args
。示例1:
示例2:
清单V2
简单调用:
使用参数调用并接收结果:
此示例使用
inContent
函数的代码自动转换为字符串,这样做的好处是 IDE 可以应用语法突出显示和 linting。明显的缺点是浏览器会浪费时间来解析代码,但通常不到 1 毫秒,因此可以忽略不计。问题:扩展页面(弹出窗口、选项、MV2 中的背景页面等)与网页分离,它们有自己的 DOM、
document
、window 和chrome-extension://
URL。解决方案:使用内容脚本访问网络页面或与其内容交互。
方法1.声明式
manifest.json:
它将在页面加载时运行一次。之后,请使用消息传递。
警告!它不能发送 DOM 元素、Map、Set、ArrayBuffer、类、函数等。它只能发送与 JSON 兼容的简单对象和类型,因此您需要手动提取所需的数据并将其作为简单数组或对象传递。
方法 2. 程序化
ManifestV3:
在扩展脚本(如弹出窗口)可根据需要将内容脚本/函数注入选项卡。
此方法的结果是内容脚本中的最后一个表达式,因此可用于提取数据。数据必须与 JSON 兼容,请参阅上面的警告。
manifest.json 中所需的
权限
:“脚本”
- 强制;"activeTab"
- 理想场景,适合对用户操作的响应(通常是单击工具栏中的扩展图标)。安装扩展程序时不显示任何权限警告。如果理想情况不可能,请将允许的站点添加到manifest.json 中的
host_permissions
:“*://*.example.com/”
以及您想要的任何其他网站。"
"
或"*://*/"
这些会将您的扩展程序置于 Chrome 网上应用店中超慢审核队列中由于广泛的主机权限。ManifestV2 与上述的差异:
权限
中指定网站。