根据此处的交叉帖子,问题确实在于打开的窗口具有独特的来源。这是有意为之,因为标准工作组 (SWG) 的成员认为,对于继承沙盒起源的 about:blank 页面不做例外处理会更安全。
但是,为了解决这个问题,至少出于我的目的,我可以使用以下方法。首先,忘记沙盒。此解决方法使用嵌入在背景页面中的 iframe,并将 src url 设置为data:text/html,...
. 这为 iframe 提供了一个独特的来源,因此它不再位于扩展空间中。这意味着可以使用 eval 而无法访问 chrome api。与沙盒不同,从 iframe 打开的窗口与 iframe 共享相同的来源,允许访问创建的窗口。例如:
在后台 html 页面中:
<html>
<head>
...
<script src="background.js"></script>
...
</head>
<body>
...
<iframe id="myframe"></iframe>
...
</body>
</html>
在 background.js 中:
...
document.getElementById('myframe').setAttribute('src', 'data:text/html,'+
encodeURI('<html><head>'+
'<script src='+chrome.extension.getURL('jquery.js')+'></script>'+
'<script src='+chrome.extension.getURL('myscript.js')+'></script>'+
...
'</head><body></body></html>'
));
...
在 myscript.js 中
jQuery(document).ready(function(){
...
// To receive messages from background.js.
window.addEventListener('message', function(e){ ... } );
// To send messages to background.js.
parent.postMessage({...}, '*');
// To open AND ACCESS a window.
var win = window.open();
win.document.write('Hello'); // Fails in sandbox, works here.
// Eval code, if you want. Can't do this from an extension
// page loaded normally unless you allow eval in your manifest.
// Here, it's okay!
eval( 'var x = window.open(); x.document.write("Hi!")' );
// No chrome apis.
chrome.log( chrome.extension ); // -> undefined
chrome.log( chrome.windows ); // -> undefined
// No direct access to background page (e.g., parent).
chrome.log( parent ); // -> Window with no properties.
...
});