Javascript Chrome扩展后台页面和内容脚本同步

Javascript Chrome扩展后台页面和内容脚本同步,javascript,google-chrome-extension,Javascript,Google Chrome Extension,假设我在Chrome扩展的背景页面中有以下代码 var opts; chrome.storage.local.get(options, function(result) { opts = result[options]; }); chrome.runtime.onMessage.addListener(function(request, sender, response) { if (request.message === 'getOpts') response

假设我在Chrome扩展的背景页面中有以下代码

var opts;
chrome.storage.local.get(options, function(result) {
    opts = result[options];
});

chrome.runtime.onMessage.addListener(function(request, sender, response) {
    if (request.message === 'getOpts')
        response(opts);
});
在我的内容脚本中,我通过消息传递访问
opts

chrome.runtime.sendMessage({'message': 'getOpts'}, function(response) {
    console.log(opts);
});
是否可以保证在运行内容脚本之前定义OPT?例如,启动浏览器时,后台页面将运行,并且可能会将对
chrome.storage.local.get的回调添加到后台页面的消息队列中。Chrome会在注入内容脚本之前完成对该队列的处理吗


我可以从内容脚本中调用chrome.storage.local.get,但我的问题更一般,因为我在后台页面中有额外的异步处理。目前,我的内容脚本会检查后台页面,以确保一切就绪(使用间隔来保持检查),但我不确定是否有必要进行此类检查。

您实际上可以异步回复消息

chrome.runtime.onMessage.addListener(function(request, sender, response) {
  if (request.message === 'getOpts') {
    chrome.storage.local.get('options', function(result) {
      response(result[options]);
    });
    return true; // Indicate that response() will be called asynchronously
  }
});
chrome.storage
的情况下,这确实是愚蠢的,因为API是专门设计来增加在内容脚本中使用
localStorage
+消息传递的迂回性质的;您可以直接从内容脚本进行查询


但在异步处理的一般情况下,您可以推迟对消息的应答。您只需要从监听器返回一个真值,以表明您还没有完成。

即使在测试中,也不要依赖定义的变量。一般来说,由于正常的定时,您的var应该在收到消息时设置,但要确保您应该在后台onMessage中进行检查。我通过在全局内存中记住是否已经初始化了扩展,并在需要时从onMessage初始化扩展来解决这个问题。xan给出的答案显示了在这种情况下,在异步初始化完成后如何使用“return true”来处理消息

请参见上的示例(搜索调用的
b

在这里,您可以看到我有一个sendResponse方法,它负责检测回调是否已经被调用,如果没有,则返回true(假设异步操作正在进行,稍后将调用回调)


您还可以通过在加载该变量的后台代码中假装延迟来试验和测试这一点。

然后向我们显示您的消息传递。否则很难回答。嗨,Xan,我添加了显示消息传递的代码。似乎没有保证。即使Chrome在加载内容脚本之前处理后台脚本队列中的所有消息,也有可能在后台脚本运行完毕时,对Chrome.storage.local.get的回调可能还不在队列中。嗨,Xan,谢谢你的回复。我也可以直接从我的内容脚本调用chrome.storage.local.get。然而,我的问题更一般。我想知道是否会保证在注入内容脚本之前定义OPT。内容脚本不会在扩展加载时注入。您必须在加载扩展后进行实际导航,才能获得内容脚本。所以正常情况下,有很大的时间间隔。我在帖子中特别使用了浏览器启动的例子来解释这个问题。(因为在浏览器启动时,后台页面会加载,内容脚本也会加载)。是的,我也考虑过这种情况。我不知道这方面是否有任何保证。这是一个有趣的问题,它在浏览器启动时是如何工作的。我会把这作为一个单独的、具体的问题,它可能需要有Chrome内部经验的人的回答,比如RobW。我的意思是,我明白你的意思。
addListener
是否保证在发送消息之前运行?Hi Zig,感谢您的回复。我已经有了检查一切是否准备就绪的代码,并相应地进行了处理。我很好奇这样的代码是否有必要,我将你的帖子解读为建议检查是必要的。今天可能有必要,也可能没有必要,但最好在将来或不可预见的情况下添加它。