Chrome扩展程序将Background.js中的值保存到存储中并显示在popup.html上

时间:2018-11-19 05:02:32

标签: javascript google-chrome google-chrome-extension

我当前正在编写一个简单的chrome扩展程序,当您单击标题中的扩展程序图标时,会将当前网页保存到本地存储中。

我已根据https://developer.chrome.com/extensions/activeTab此处的Chrome文档,使用background.js将网址成功保存到了本地存储中。

我的问题是,当我第一次点击Chrome扩展程序图标时,我的事件就触发了,但我的popup.js错误却显示为

if(_err){
   console.error(_err);
}

background.js

Uncaught TypeError: Cannot read property 'getSelected' of undefined

popup.js

chrome.browserAction.onClicked.addListener(function(tab) {

  console.log('Turning ' + tab.url + ' red!');
  var tabNew = tab.url
  chrome.storage.sync.set({ ["key" + 1]:  tabNew}, function(){
      //  A data saved callback omg so fancy
  });

  chrome.storage.sync.get(/* String or Array */["key" + 1], function(items){
      //  items = [ { "yourBody": "myBody" } ]
      console.log(items)
  });


  chrome.tabs.executeScript({
    code: 'document.body.style.backgroundColor="red"'
  });

  chrome.browserAction.setPopup({popup: 'popup.html'});


});

popup.html

chrome.tabs.getSelected(null, function(tab) {
    document.getElementById('currentLink').innerHTML = tab.url;
});



document.addEventListener('DOMContentLoaded', function() {
    var link = document.getElementById('download');
    // onClick's logic below:
    link.addEventListener('click', function() {
        chrome.storage.sync.get(null, function(items) { // null implies all items
            // Convert object to a string.
            var result = JSON.stringify(items);

            // Save as file
            chrome.downloads.download({
                url: 'data:application/json;base64,' + btoa(result),
                filename: 'filename_of_exported_file.json'
            });
        });        
    });
});

manifest.json

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml">
<head> 

    <link href='http://fonts.googleapis.com/css?family=Open+Sans' rel='stylesheet' type='text/css'> 
    <link href='style.css' rel='stylesheet' type='text/css'> 

    <title>Discoveroo</title> 

    <!-- <script type="text/javascript" src="https://www.google.com/jsapi"></script>  -->
    <base target="_blank">

</head>

<body>
<p id="currentLink">Loading ...</p>
<hr />
<ul id="savedLinks"></ul>
<script type="text/javascript" src="popup.js"></script>

<button id="download">Download All</button>
</body>
</html>

1 个答案:

答案 0 :(得分:3)

  1. 请勿将popup.js用作内容脚本。您不需要内容脚本。请参见architecture overview。内容脚本只能访问chrome API,并且只能在网页中运行,而不能在browserAction弹出窗口中运行,后者是一个完全独立的完整扩展页面,具有自己的chrome-extension:// URL和{{3 }}等,与网页无关。
  2. browserAction.onClicked无法同时与弹出html一起使用,因此您应该选择一个。在这种情况下,由于您需要显示弹出页面,因此请在manifest.json中声明它,然后删除browserAction.onClicked,并将其内部代码放入您的popup.js中。
  3. 因此,不需要后台脚本
  4. 可能不需要<all_urls>权限,因为您已经拥有activeTab,可以在单击扩展图标后完全访问活动选项卡。
  5. chrome.tabs.getSelected已过时,最终将被删除,因此请使用chrome.tabs.query({active: true, currentWindow: true}, tabs => { ... })
  6. 无需阅读chrome.storage,因为您已经在popup.js中获得了活动网址。
  7. 关于“ omg so fancy”,回调不是一个任意的怪异,而是基本事实的结果:API是异步的,因此回调在以后的某个时间点被调用,就像一次“ onload”事件监听器。关于异步JavaScript的教程很多。​​
  8. 使用安全的textContent属性而不是可能不安全的innerHTML来显示纯文本字符串,例如URL。

manifest.json

  • 删除"background"
  • 删除"content_scripts"
  • 添加"default_popup"

    "browser_action": {
      "default_title": "Add this page to my list",
      "default_popup": "popup.html"
    },
    

background.js

删除它。

popup.js

您可能只需要执行旧的后台脚本,就是executeScript和sync.set调用。

chrome.tabs.executeScript({
  code: 'document.body.style.backgroundColor="red"'
});

chrome.tabs.query({active: true, currentWindow: true}, ([tab]) => {
  document.getElementById('currentLink').textContent = tab.url;
  chrome.storage.sync.set({key1: tab.url});
});

您还可以加载own devtools console(在popup.js之前在popup.html中使用<script>标签)并切换为异步/等待语法,而不是回调:

(async () => {
  const [tab] = await browser.tabs.query({active: true, currentWindow: true});
  document.getElementById('currentLink').textContent = tab.url;
  await chrome.storage.sync.set({key1: tab.url});
})();