从内容脚本同步获取存储数据
我目前正在开发chrome扩展程序,Github上提供了源代码。 目标是将自定义Javascript注入网页。
目前,我将每个自定义Javascript Inject存储在localStorage中 ,并从内容scipts中调用它们。 我已将run_at设置为document_start 。
我使用它,从后台脚本获取存储的注入 :
chrome.extension.sendMessage({method:"get_injects"},function(injects){ for(index in injects){ if(/^items\./.test(index)){ itemJSON = injects[index]; //if(window.location.host.toString().indexOf(itemJSON.url)){ if(window.location.host.toString().match(itemJSON.url + '$')){ var js = itemJSON.js.toString(); eval(js); } } } });
问题
我想在文档加载之前准确运行Inject脚本 。 但是使用提出的方法,控件将通过chrome.extension.sendMessage
并且不会等待获得响应injects
。 所以, eval(js);
将在页面加载的中间执行。 我该如何解决这个问题,这样我才能在页面加载之前注入?
在Chrome中,每个标签都在自己的流程中运行。 后台页面在扩展过程中运行,该过程与您正在挂钩的选项卡不同。 所以我担心没有真正的同步解决方案。
即使使用chrome.storage (它没有原始限制,因此不需要背景页面)也是异步的。
但这是一个适用于大多数页面的解决方案:
- 如果您需要的数据位于页面的localStorage中,请转到6
- 从页面中删除所有内容
- 做你的异步数据请求
- 当你有数据时,将它存储在页面的localStorage中(而不是后台)
- 使用相同的URL刷新页面
- 利润
有一种方法可以从后台页面到当前内容脚本同步获取任意数量的数据。 您应该避免同步阻止扩展中的代码,因此我不会提供示例代码,以阻止在生产代码中将其复制粘贴。
流程是:
- 在内容脚本中使用同步
XMLHttpRequest
(到伪URL)以启动这些步骤。 - 在后台页面中,使用
chrome.webRequest.onBeforeRequest
事件拦截此请求。 - 同步获取数据,例如从
localStorage
或背景页面上的局部变量,将其转换为blob,然后使用var url = URL.createObjectURL(new Blob([ 'data chunks here' ]));
将其转换为URLvar url = URL.createObjectURL(new Blob([ 'data chunks here' ]));
。 - 使用
return {redirectUrl: url};
在onBeforeRequest
事件中发回数据。 - 确保最终使用
URL.revokeObjectURL(url);
释放数据使用的资源。
最后,尽可能避免同步,阻止代码!!