Javascript 如何在Chrome打包应用程序中与沙盒窗口通信?

Javascript 如何在Chrome打包应用程序中与沙盒窗口通信?,javascript,iframe,google-chrome-extension,security,sandbox,Javascript,Iframe,Google Chrome Extension,Security,Sandbox,最近谷歌推出了沙盒来增强其安全模型。他们使用postMessage作为与沙盒窗口通信的方式。但是要发布消息,我需要从后台页面发送第一条消息: // in background page: chrome.app.runtime.onLaunched.addListener(function() { chrome.app.window.create('index.html', { // index.html is sandboxed 'width': 800, 'height':

最近谷歌推出了沙盒来增强其安全模型。他们使用postMessage作为与沙盒窗口通信的方式。但是要发布消息,我需要从后台页面发送第一条消息:

// in background page:
chrome.app.runtime.onLaunched.addListener(function() {
  chrome.app.window.create('index.html', { // index.html is sandboxed
    'width': 800,
    'height': 500
  }, function(myWin) {
      // myWin is ready, I want to post a message
      console.log(myWin); // This is never called after version 23.0.1246, an error is thrown
  });
});
这在版本
23.0.1246
中运行良好,但在下一次更新中停止工作,并且从未返回。现在,这种技术在dev和beta中都会抛出错误(在
24.0.1284
23.0.1271.17
上测试)

我已经准备了一个最小的Chrome打包应用程序,显示错误(启动应用程序后在后台页面控制台中):

我已经提交了一个应用程序,但不能再等几个月才有人阅读,我需要在一个月内使用该应用程序。我如何解决这个问题?我可以看出,使用沙盒iframe仍然有效。有没有一种方法可以在不使用iFrame的情况下使用沙盒,并且仍然能够与页面通信

这是舱单:

{
  "name": "Sandbox test",
  "description": "Sandbox test",
  "manifest_version": 2,
  "minimum_chrome_version": "23",
  "version": "0.0.1",
  "app": {
    "background": {
      "scripts": ["background.js"]
    }
  },
  "sandbox": {
     "pages": ["index.html"]
  },
  "permissions": [
    "app.window"
  ]
}
以及index.html页面:

<!doctype html>
<html lang="cs">
<head>
  <meta charset="UTF-8">
</head>
<body>
    Hi
</body>
</html>
// register a postmessage listener in index.html sandbox
window.addEventListener("message", function(event) {
    console.info("message received in sandbox: " + event.data.message);    
});

你好

在Chrome打包的应用程序中,可以使用带有弹出窗口的postMessage。但是,您尝试使用的方法只适用于非沙盒页面,因为您依赖于受保护的ChromeAPI

相反,技巧是使用window.open打开沙盒弹出窗口。更重要的是,这不是一个侥幸,根据这一点,window.open应该在沙盒页面中工作,它确实可以

manifest.json:

在清单中,我不确定你试图用app.window做什么。它没有列在列表中,所以我删除了它。此外,您没有启用“后台”权限。我不确定这是否是您尝试执行的操作所必需的,但如果您需要应用程序在后台运行并持续运行,文档确实会要求您使用它:

{
  "name": "Sandbox test",
  "description": "Sandbox test",
  "manifest_version": 2,
  "minimum_chrome_version": "21",
  "version": "0.0.1",
  "app": {
    "background": {
      "scripts": ["background.js"]
    }
  },
  "sandbox": {
     "pages": ["index.html"]
  },
  "permissions": [
    "background"
  ]
}
index.html:

记住,沙盒页面无法访问ChromeAPI,因此我们包含sandbox.js来注册postmessage侦听器。见下一节

<!doctype html>
<html lang="cs">
<head>
  <meta charset="UTF-8">
  <script type="text/javascript" src="sandbox.js"></script>
</head>
<body>
    Hi. This page is sandboxed and cannot access chrome APIs! 
</body>
</html>
background.js:

记住,你不能依靠ChromeAPI与沙箱通信!因此,我们必须使用window.open而不是chrome.app.*API:

console.log("running in background... waiting for you to click the Sandbox App icon in chrome://newtab");    

// as soon as the launch icon is clicked, this fires
window.addEventListener("DOMContentLoaded", function() {

    // use window.open to create a popup
    sandboxWin = window.open("index.html","SANDBOXED!","height=800,width=500");       

    // fire a postMessage event to the sandbox. Inspect the sandbox and see the 
      // message in the console.
    sandboxWin.postMessage({"message":"It works!!"}, "*");

});
这是在Ubuntu 10.04版本24.0.1309.0(164508)上的Chromium每日版本上测试的。这应该非常接近用于Windows/Mac Canary版本的版本,这也是基本上重新命名的每日版本

我怀疑您引用的那些建议使用这种方法的文档可能会被弃用。谷歌似乎正朝着一个不同的方向发展。请参阅,在与沙盒iFrame通信时,他们使用了与使用DOM postMessage API而不是Chrome API相同的技术

我只是把它放在一起,它允许RPC在
沙盒未沙盒
之间来回移动。(也就是说,任何一个都可以公开方法)

它基于
JSON-RPC

享受吧


还可以查看:

你明白了吗?您实际在哪里发出postMessage请求。我在你的代码中看不到这一点。考虑通过这个链接添加。另外,请发布您的清单文件。祝你好运清单文件位于中。postMessage应该是而不是带有
console.log(myWin)的行,这只是为了表明代码甚至是不可访问的。