首页 > 解决方案 > Chrome 扩展:未捕获的 ReferenceError:未定义函数

问题描述

我正在写一个 Chrome 扩展程序,我有这个页面:

<html>
  <body>
    <button id="changeColor"></button>
    <script src="popup.js"></script>
  </body>
</html>

使用这个 JS(popup.js):

let changeColor = document.getElementById("changeColor");

chrome.storage.sync.get("color", ({ color }) => {
  changeColor.style.backgroundColor = color;
});

changeColor.addEventListener("click", async () => {
    let [tab] = await chrome.tabs.query({ active: true, currentWindow: true });
  
    chrome.scripting.executeScript({
      target: { tabId: tab.id },
      function: setPageBackgroundColor,
    });

});
  
function setPageBackgroundColor() {
  chrome.storage.sync.get("color", ({ color }) => {
    document.body.style.backgroundColor = color;
  });
  // Here, it says: Uncaught ReferenceError: getElementByXpath is not defined
  console.log(getElementByXpath("xpath").textContent);
}
  
function getElementByXpath(path) {
  return document.evaluate(path, document, null, XPathResult.FIRST_ORDERED_NODE_TYPE, null).singleNodeValue;
}

为什么?

标签: javascriptgoogle-chrome-extension

解决方案


问题:没有注入外部函数的代码。

这是 executeScript 的作用:

  • 它将函数的代码作为纯文本 IIFE 即(function foo() { ... })()
  • 它将文本传输到网页,
  • 它选择运行扩展的所有内容脚本的“孤立世界”环境,
  • 它将文本作为 JavaScript 代码执行。

解决方案:将所有必要的代码和函数放入您注入的函数中。

在您的情况下,getElementByXpath 定义应该移到 setPageBackgroundColor 中。

PS 自然,注入的代码也可以通过 manifest.json 使用先前注入的内容脚本的全局变量/函数content_scripts(假设它们的run_at已经发生)或executeScript.


推荐阅读