MixedContentExtractor   A
last analyzed

Complexity

Total Complexity 9

Size/Duplication

Total Lines 65
Duplicated Lines 0 %

Coupling/Cohesion

Components 0
Dependencies 3

Importance

Changes 0
Metric Value
wmc 9
lcom 0
cbo 3
dl 0
loc 65
rs 10
c 0
b 0
f 0

3 Methods

Rating   Name   Duplication   Size   Complexity  
B extract() 0 32 6
A getSearchNodes() 0 18 1
A isShortLink() 0 10 2
1
<?php
2
3
namespace Spatie\MixedContentScanner;
4
5
use Exception;
6
use GuzzleHttp\Psr7\Uri;
7
use Illuminate\Support\Collection;
8
use Symfony\Component\DomCrawler\Crawler as DomCrawler;
9
10
class MixedContentExtractor
11
{
12
    public static function extract(string $html, string $currentUri): array
13
    {
14
        return static::getSearchNodes()
15
            ->mapSpread(function ($tagName, $attribute) use ($html, $currentUri) {
16
                return (new DomCrawler($html, $currentUri))
17
                    ->filterXPath("//{$tagName}[@{$attribute}]")
18
                    ->reduce(function (DomCrawler $node) {
19
                        return ! self::isShortLink($node);
20
                    })
21
                    ->each(function (DomCrawler $node) use ($tagName, $attribute) {
22
                        try {
23
                            $url = new Uri($node->attr($attribute));
24
25
                            if ($tagName === 'link' && $attribute === 'href') {
26
                                if ($node->attr('rel') !== 'stylesheet') {
27
                                    return;
28
                                }
29
                            }
30
31
                            return $url->getScheme() === 'http' ? [$tagName, $url] : null;
32
                        } catch (Exception $e) {
33
                            // ignore invalid links
34
                        }
35
                    });
36
            })
37
            ->flatten(1)
38
            ->filter()
39
            ->mapSpread(function ($tagName, $mixedContentUrl) use ($currentUri) {
40
                return new MixedContent($tagName, $mixedContentUrl, new Uri($currentUri));
41
            })
42
            ->toArray();
43
    }
44
45
    protected static function getSearchNodes(): Collection
46
    {
47
        return collect([
48
            ['audio', 'src'],
49
            ['embed', 'src'],
50
            ['form', 'action'],
51
            ['link', 'href'],
52
            ['iframe', 'src'],
53
            ['img', 'src'],
54
            ['img', 'srcset'],
55
            ['object', 'data'],
56
            ['param', 'value'],
57
            ['script', 'src'],
58
            ['source', 'src'],
59
            ['source', 'srcset'],
60
            ['video', 'src'],
61
        ]);
62
    }
63
64
    protected static function isShortLink(DomCrawler $node): bool
65
    {
66
        $relAttribute = $node->getNode(0)->attributes->getNamedItem('rel');
67
68
        if (is_null($relAttribute)) {
69
            return false;
70
        }
71
72
        return strtolower($relAttribute->nodeValue) === 'shortlink';
73
    }
74
}
75