我正在动态创建iframe,并且我想阻止不是来自iframes来源的脚本。这甚至可能(通过JavaScript / jQuery)?例如,如果我的网页从example.com
加载iframe,内容为:
<script src="http://example.com/foo.js"></script>
<script src="http://something-else.com/bar.js"></script>
我希望运行example.com
脚本,但我希望阻止something-else.com
脚本而不是运行。
我正在使用NW.js(以前称为Node-Webkit),因此我对iframe的内容具有完全的读写权限,就好像它们是同源的一样。
我尝试过使用插件(比如那些带有白名单的CORS的插件),但我尝试过的都没有。
除了iframe的起源之外,理想的解决方案还允许我将特定的其他来源列入白名单。
编辑:
以下是我尝试在https://github.com/IdeasNeverCease/Aries
中实现此功能的浏览器项目以下是iframe加载的代码部分:https://github.com/IdeasNeverCease/Aries/blob/master/app.nw/resources/scripts/aries.js#L376-L687
答案 0 :(得分:4)
我想阻止不是来自iframes的源
的脚本
这正是Content Security Policy(CSP)的用途。 CSP可以指定脚本,插件,样式,媒体等允许哪些来源。您需要使每个iframe都有一个CSP,以防止脚本加载到当前源之外;这可以使用简单的策略script-src 'self' 'unsafe-inline';
完成(unsafe-inline
允许iframe具有内联脚本,而self
仅限制加载到同源资源)
传统上,您需要服务器在提供页面时发送Content-Security-Policy
响应标头。但是,如果您无法控制服务器发送的响应标头(但执行可以控制页面内容),您可以模仿带有<meta>
标记的HTTP响应标头,如此:
<meta http-equiv="Content-Security-Policy" content="script-src 'self' 'unsafe-inline';">
您可以通过编程方式注入(但请继续阅读以解决问题):
var m = document.createElement("meta");
m.httpEquiv = "content-security-policy";
m.content = "script-src 'self' 'unsafe-inline';";
iframeElem.contentDocument.documentElement.appendChild(m);
但是,这个基于脚本的注入可能不适合您,因为在从HTML源解析DOM之后,您只能使用DOM。那时,任何(非async
)<script>
元素的脚本都已经被提取并运行。您可能需要直接操作HTML,但我对NW.js的了解不足以告诉您最佳方法。
如果您想禁止所有外部脚本资源(即使是来自同一来源的资源),您可以使用script-src 'none' 'unsafe-inline';
。要禁止所有脚本,包括加载的脚本和内联脚本,请使用script-src 'none';
为了将特定来源列入白名单,只需将它们作为未引用的项目添加到CSP中:
Content-Security-Policy: script-src 'self' *.twitter.com https://api.facebook.com
前导*.
允许所有子域,前导https://
限制该域的白名单仅保护https://
地址。