Completed
Branch TemplateNormalizations (ae42e4)
by Josh
33:16
created

linkTargetCanAccessOpener()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 16
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 6
nc 3
nop 1
dl 0
loc 16
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
/**
4
* @package   s9e\TextFormatter
5
* @copyright Copyright (c) 2010-2017 The s9e Authors
6
* @license   http://www.opensource.org/licenses/mit-license.php The MIT License
7
*/
8
namespace s9e\TextFormatter\Configurator\TemplateNormalizations;
9
10
use DOMElement;
11
12
/**
13
* Adds rel="noreferrer" on links that open in a new context that would allow window.opener to be
14
* accessed.
15
*
16
* @link https://mathiasbynens.github.io/rel-noopener/
17
* @link https://wiki.whatwg.org/wiki/Links_to_Unrelated_Browsing_Contexts
18
*/
19
class SetRelNoreferrerOnTargetedLinks extends AbstractNormalization
20
{
21
	/**
22
	* {@inheritdoc}
23
	*/
24
	protected $queries = ['//a', '//area'];
25
26
	/**
27
	* Add a rel="noreferrer" attribute to given element
28
	*
29
	* @param  DOMElement $element
30
	* @return void
31
	*/
32
	protected function addRelAttribute(DOMElement $element)
33
	{
34
		$rel = $element->getAttribute('rel');
35
		if (preg_match('(\\S$)', $rel))
36
		{
37
			$rel .= ' ';
38
		}
39
		$rel .= 'noreferrer';
40
41
		$element->setAttribute('rel', $rel);
42
	}
43
44
	/**
45
	* Test whether given link element will let the target access window.opener
46
	*
47
	* @param  DOMElement $element
48
	* @return bool
49
	*/
50
	protected function linkTargetCanAccessOpener(DOMElement $element)
51
	{
52
		// Can't access window.opener if the link doesn't have a target
53
		if (!$element->hasAttribute('target'))
54
		{
55
			return false;
56
		}
57
58
		// Can't access window.opener if the link already has rel="noopener" or rel="noreferrer"
59
		if (preg_match('(\\bno(?:open|referr)er\\b)', $element->getAttribute('rel')))
60
		{
61
			return false;
62
		}
63
64
		return true;
65
	}
66
67
	/**
68
	* {@inheritdoc}
69
	*/
70
	protected function normalizeElement(DOMElement $element)
71
	{
72
		if ($this->linkTargetCanAccessOpener($element))
73
		{
74
			$this->addRelAttribute($element);
75
		}
76
	}
77
}