Translator: kayson

The original link

Update: Instagram has fixed the issue, most likely because of this post. Facebook and Twitter remain unresolved. I use Instagram as a basic example, but the main takeaway is that security breaches are extremely common. Every Web developer should be aware of it, and browsers should consider modifying this behavior.

If you use target=””_blank”” and don’t include rel=””noopener”” on your links, you leave the user open to a very simple phishing attack. To inform users from unprotected sites, we run a script that exploits this flaw.

if (window.opener) { window.opener.location = ""https://dev.to/phishing? referrer=""+document.referrer; }Copy the code

I’m sure most sites don’t address this issue properly, but I’m surprised Instagram.com is one of them. We recently created the @ThePracticalDev Instagram account and discovered this. If you click on the dev.to link on our profile page and go back to the original page, you’ll see what I mean. Twitter did not protect against the security flaw in Safari, nor did Chrome and Firefox. They didn’t use rel=””noopener””, so it looks like the security script they used didn’t work on Safari.

Update: Since Instagram fixed the issue after this post was published, I changed the example below to a Facebook page.

Find out why

  1. Visit The Practical Dev Facebook page.
  2. Click on the resources pagedev.toLink. This opens a new page card or window.
  3. Notice that the original page has been redirected to this page.

When a site uses target=””_blank”” in a link to open a new page card or window, the site gives the new page access to the original window and grants some permissions through the window.opener API. Some of these permissions are blocked by cross-domain restrictions, but window.location is a catch.

Don’t worry, there’s more

This is not only a phishing attack issue, but also a privacy issue, since the newly opened site has continuous access to the browsing address of the original page card. It can poll for this information and get results. Fortunately, this behavior seems to be prevented by cross-domain restrictions, so even though I may be able to keep accessing information you don’t want me to know, the full specification should contain robust restrictions.

Update: When I first wrote this, I proposed a browser spying scenario where bad actors could more thoroughly detect a user’s browsing history. Now I don’t think that’s accurate, so I changed the statement.

To limit window.opener’s access behavior, the original page needs to add a rel=””noopener” attribute to every link that uses target=””_blank””. However, Firefox doesn’t support this property value, so you’ll actually have to use rel=””noopener noreferrer”” to completely override it. While some precautions can be scripted, as seen on Twitter, this doesn’t work on Safari.

var  otherWindow  =  window.open();
otherWindow.opener  =  null;
otherWindow.location  =  url;

Copy the code

This suggested script comes from a good article on the subject.

The problem is not well known and completely underestimated. It was mentioned on the Web Hypertext Application Technology Working Group mailing list. In my opinion, the risks of this browser behavior far outweigh the potential benefits. Either way, there’s no excuse for Facebook and Instagram to ignore the issue.

I’ll talk more about this in the future. You can follow me on Twitter(@bendhalpern) or @ThepracticalDev.