使用window.open但阻止使用window.opener

Mac*_*ity 20 javascript cross-domain

过了一会儿,我遇到了一个有趣的安全漏洞

<a href="http://someurl.here" target="_blank">Link</a>
Run Code Online (Sandbox Code Playgroud)

看起来很无害,但是有一个漏洞,因为默认情况下,正在打开的页面允许打开的页面通过它回调它window.opener.有一些限制,是跨域的,但仍然有一些可以做的恶作剧

window.opener.location = 'http://gotcha.badstuff';
Run Code Online (Sandbox Code Playgroud)

现在,HTML有一个解决方法

<a href="http://someurl.here" target="_blank" rel="noopener noreferrer">Link</a>
Run Code Online (Sandbox Code Playgroud)

这可以防止新窗口window.opener传递给它.这对HTML很好,但是如果你使用的话window.open怎么办?

<button type="button" onclick="window.open('http://someurl.here', '_blank');">
    Click Me
</button>
Run Code Online (Sandbox Code Playgroud)

你会如何阻止window.opener被传递到这里?

G0B*_*LiN 26

window.open()呼叫现在支持 "noopener"功能.
所以调用window.open('https://www.your.url','_blank','noopener') 应该打开一个null的新窗口/选项卡window.opener.

我无法找到支持浏览器(和版本)的可靠列表 - MDN 在此声明

现代浏览器支持此功能,包括Chrome和Firefox 52+.

从我的实验中,我发现它适用于:

  • Chrome 61
  • FireFox 56
  • Safari 11.1(感谢Jiayi Hu为此)

但不起作用:

  • IE 11.608
  • 边缘 40

(在运行Windows 10的PC上进行的所有测试......)

为了向后兼容,最好将它与t3__rry的答案结合起来.

  • 等等,实际上它确实有效 - 但它不会在标签中打开它.它是一个没有框架的新窗口.很奇怪.在你的控制台中试试吧. (4认同)
  • @Chet正如Chrome问题中提到的,您可以执行 window.open(url,'_blank','toolbar=1,menubar=1,location=1,status=1,scrollbars=1,noopener') 作为解决方法让它在选项卡中打开。https://bugs.chromium.org/p/chromium/issues/detail?id=596068#c15 (2认同)

t3_*_*rry 21

使用

var yourWindow = window.open();
yourWindow.opener = null;
yourWindow.location = "http://someurl.here";
Run Code Online (Sandbox Code Playgroud)

感谢Mathias Bynens:https://mathiasbynens.github.io/rel-noopener/

  • 如链接文章中所述,此方法可能会触发浏览器的弹出窗口阻止程序.我只是尝试了代码,事实上,黄色栏"Firefox阻止了这个网站打开一个弹出窗口." (2认同)

I.G*_*ual 19

指出它是逗号分隔的功能列表(没有空格),因此您可以设置'noopener,noreferrer,resizable'ie:

window.open('http://sensible.url', '_blank', 'noopener,noreferrer,resizable')
Run Code Online (Sandbox Code Playgroud)

来自Mozilla 文档

windowFeatures 选修的

一个 DOMString,包含以逗号分隔的窗口功能列表,并以“name=value”的形式给出相应的值。[...]

  • @AshD,您可以在[示例](https://developer.mozilla.org/en-US/docs/Web/API/Window/open#toolbar_and_ui_parts_features)中看到工具栏和UI部分是键值功能,`status =yes、status=1 和 status 具有相同的结果。`,但是 `noopener` 和 `noreferrer` 是功能特性,因此它们存在或不存在,但没有额外的价值 (2认同)

Vin*_*ier 8

根据文档(https://developer.mozilla.org/en/docs/Web/API/Window/open),在以下代码中

window.open('https://www.your.url','_blank','noopener')
Run Code Online (Sandbox Code Playgroud)

第三个参数包含“WindowFeatures”(参见https://developer.mozilla.org/en-US/docs/Web/API/Window/open#Window_features)所以它在新窗口中打开目标是有意义的


Che*_*het 7

这对我有用:

const a = document.createElement("a")
a.href = args.url
a.target = "_blank"
a.rel = "noopener"
a.click()
Run Code Online (Sandbox Code Playgroud)

  • 我知道了。我以为你的目标只是功能。 (5认同)
  • 您所做的就是使用 JS DOM 创建一个锚标记,它与问题中的 HTML 执行相同的操作。你没有使用`window.open`,这就是我问这个的原因 (3认同)